diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/Makefile.am | 50 | ||||
-rw-r--r-- | src/accounts-service-user.xml | 689 | ||||
-rw-r--r-- | src/accounts-service.xml | 194 | ||||
-rw-r--r-- | src/display-manager.xml | 17 | ||||
-rw-r--r-- | src/gdm-local-display-factory.xml | 20 | ||||
-rw-r--r-- | src/session-service.c | 73 | ||||
-rw-r--r-- | src/users-service-dbus.c | 561 | ||||
-rw-r--r-- | src/users-service-dbus.h | 15 | ||||
-rw-r--r-- | src/users-service.list | 1 | ||||
-rw-r--r-- | src/users-service.xml | 56 |
10 files changed, 1076 insertions, 600 deletions
diff --git a/src/Makefile.am b/src/Makefile.am index db49fa7..df0ec0f 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -14,7 +14,8 @@ libsession_la_SOURCES = \ gen-session-dbus.xml.h \ dbus-shared-names.h \ dbusmenu-shared.h \ - users-service-client.h + accounts-service-client.h \ + accounts-service-user-client.h libsession_la_CFLAGS = \ $(APPLET_CFLAGS) \ -Wall -Werror \ @@ -36,19 +37,26 @@ consolekit-session-client.h: $(srcdir)/consolekit-session.xml --output=consolekit-session-client.h \ $(srcdir)/consolekit-session.xml -gdm-local-display-factory-client.h: $(srcdir)/gdm-local-display-factory.xml +display-manager-client.h: $(srcdir)/display-manager.xml dbus-binding-tool \ --prefix=_gdm_local_display_factory_client \ --mode=glib-client \ - --output=gdm-local-display-factory-client.h \ - $(srcdir)/gdm-local-display-factory.xml + --output=display-manager-client.h \ + $(srcdir)/display-manager.xml -users-service-client.h: $(srcdir)/users-service.xml +accounts-service-client.h: $(srcdir)/accounts-service.xml dbus-binding-tool \ - --prefix=_users_service_client \ + --prefix=_accounts_service_client \ --mode=glib-client \ - --output=users-service-client.h \ - $(srcdir)/users-service.xml + --output=accounts-service-client.h \ + $(srcdir)/accounts-service.xml + +accounts-service-user-client.h: $(srcdir)/accounts-service-user.xml + dbus-binding-tool \ + --prefix=_accounts_service_user_client \ + --mode=glib-client \ + --output=accounts-service-user-client.h \ + $(srcdir)/accounts-service-user.xml upower-client.h: $(srcdir)/upower.xml dbus-binding-tool \ @@ -57,16 +65,6 @@ upower-client.h: $(srcdir)/upower.xml --output=upower-client.h \ $(srcdir)/upower.xml -users-service-marshal.h: $(srcdir)/users-service.list - glib-genmarshal --header \ - --prefix=_users_service_marshal $(srcdir)/users-service.list \ - > users-service-marshal.h - -users-service-marshal.c: $(srcdir)/users-service.list - glib-genmarshal --body \ - --prefix=_users_service_marshal $(srcdir)/users-service.list \ - > users-service-marshal.c - gen-%.xml.c: %.xml @echo "Building $@ from $<" @echo "const char * _$(subst -,_,$(subst .,_,$(basename $(notdir $<)))) = " > $@ @@ -91,8 +89,7 @@ indicator_session_service_SOURCES = \ dbusmenu-shared.h \ gconf-helper.c \ users-service-dbus.h \ - users-service-dbus.c \ - users-service-marshal.c + users-service-dbus.c indicator_session_service_CFLAGS = \ $(SESSIONSERVICE_CFLAGS) \ $(GCONF_CFLAGS) \ @@ -134,22 +131,21 @@ gtk_logout_helper_LDADD = \ BUILT_SOURCES = \ consolekit-manager-client.h \ consolekit-session-client.h \ - gdm-local-display-factory-client.h \ + display-manager-client.h \ gen-session-dbus.xml.c \ gen-session-dbus.xml.h \ upower-client.h \ - users-service-client.h \ - users-service-marshal.h \ - users-service-marshal.c + accounts-service-client.h \ + accounts-service-user-client.h EXTRA_DIST = \ consolekit-manager.xml \ consolekit-session.xml \ - gdm-local-display-factory.xml \ + display-manager.xml \ session-dbus.xml \ upower.xml \ - users-service.xml \ - users-service.list + accounts-service.xml \ + accounts-service-user.xml CLEANFILES = \ $(BUILT_SOURCES) diff --git a/src/accounts-service-user.xml b/src/accounts-service-user.xml new file mode 100644 index 0000000..bd4cb21 --- /dev/null +++ b/src/accounts-service-user.xml @@ -0,0 +1,689 @@ +<!DOCTYPE node PUBLIC +"-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" +"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd" > +<node name="/" xmlns:doc="http://www.freedesktop.org/dbus/1.0/doc.dtd"> + <interface name="org.freedesktop.Accounts.User"> + + <method name="SetUserName"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="name" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new username. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users username. Note that it is usually not allowed + to have multiple users with the same username. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the username of any user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetRealName"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="name" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new name, typically in the form "Firstname Lastname". + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users real name. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.change-own-user-data</doc:term> + <doc:definition>To change his own name</doc:definition> + </doc:item> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the name of another user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetEmail"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="email" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new email address. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users email address. + </doc:para> + <doc:para> + Note that setting an email address in the AccountsService is + not the same as configuring a mail client. Mail clients might + default to email address that is configured here, though. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.change-own-user-data</doc:term> + <doc:definition>To change his own email address</doc:definition> + </doc:item> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the email address of another user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetLanguage"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="language" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new language, as a locale specification like "de_DE.UTF-8". + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users language. + </doc:para> + <doc:language> + The expectation is that display managers will start the + users session with this locale. + </doc:language> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.change-own-user-data</doc:term> + <doc:definition>To change his own language</doc:definition> + </doc:item> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the language of another user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetLocation"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="location" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new location as a freeform string. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users location. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.change-own-user-data</doc:term> + <doc:definition>To change his own location</doc:definition> + </doc:item> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the location of another user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetHomeDirectory"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="homedir" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new homedir as an absolute path. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users home directory. + </doc:para> + <doc:para> + Note that changing the users home directory moves all the content + from the old location to the new one, and is potentially an + expensive operation. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the home directory of a user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetShell"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="shell" direction="in" type="s"> + <doc:doc> + <doc:summary> + The new user shell. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users shell. + </doc:para> + <doc:para> + Note that setting the shell to a non-allowed program may + prevent the user from logging in. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the shell of a user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetIconFile"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="filename" direction="in" type="s"> + <doc:doc> + <doc:summary> + The absolute filename of a png file to use as the users icon. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets the users icon. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.change-own-user-data</doc:term> + <doc:definition>To change his own icon</doc:definition> + </doc:item> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the icon of another user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetLocked"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="locked" direction="in" type="b"> + <doc:doc> + <doc:summary> + Whether to lock or unlock the users account. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Locks or unlocks a users account. + </doc:para> + <doc:para> + Locking an account prevents the user from logging in. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To lock or unlock user accounts</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetAccountType"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="accountType" direction="in" type="i"> + <doc:doc> + <doc:summary> + The new account type, encoded as an integer: + <doc:list> + <doc:item> + <doc:term>0</doc:term> + <doc:definition>Standard user</doc:definition> + </doc:item> + <doc:item> + <doc:term>1</doc:term> + <doc:definition>Administrator</doc:definition> + </doc:item> + <doc:item> + <doc:term>2</doc:term> + <doc:definition>Supervised user</doc:definition> + </doc:item> + </doc:list> + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Changes the users account type. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change an account type</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetPasswordMode"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="mode" direction="in" type="i"> + <doc:doc> + <doc:summary> + The new password mode, encoded as an integer: + <doc:list> + <doc:item> + <doc:term>0</doc:term> + <doc:definition>Regular password</doc:definition> + </doc:item> + <doc:item> + <doc:term>1</doc:term> + <doc:definition>Password must be set at next login</doc:definition> + </doc:item> + <doc:item> + <doc:term>2</doc:term> + <doc:definition>No password</doc:definition> + </doc:item> + </doc:list> + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Changes the users password mode. + </doc:para> + <doc:para> + Note that changing the password mode has the side-effect of + unlocking the account. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change a users password mode</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetPassword"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="password" direction="in" type="s"> + <doc:doc> + <doc:summary> + The crypted password. + </doc:summary> + </doc:doc> + </arg> + <arg name="hint" direction="in" type="s"> + <doc:doc> + <doc:summary> + The password hint. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Sets a new password for this user. + </doc:para> + <doc:para> + Note that setting a password has the side-effect of + unlocking the account. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.user-administration</doc:term> + <doc:definition>To change the password of a user</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="SetAutomaticLogin"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="enabled" direction="in" type="b"> + <doc:doc> + <doc:summary> + Whether to enable automatic login for this user. + </doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Enables or disables automatic login for a user. + </doc:para> + <doc:para> + Note that usually only one user can have automatic login + enabled, so turning it on for a user will disable it for + the previously configured autologin user. + </doc:para> + </doc:description> + <doc:permission> + The caller needs one of the following PolicyKit authorizations: + <doc:list> + <doc:item> + <doc:term>org.freedesktop.accounts.set-login-option</doc:term> + <doc:definition>To change the login screen configuration</doc:definition> + </doc:item> + </doc:list> + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <property name="Uid" type="t" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The uid of the user. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="UserName" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The username of the user. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="RealName" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users real name. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="AccountType" type="i" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users account type, encoded as an integer: + <doc:list> + <doc:item> + <doc:term>0</doc:term> + <doc:definition>Standard user</doc:definition> + </doc:item> + <doc:item> + <doc:term>1</doc:term> + <doc:definition>Administrator</doc:definition> + </doc:item> + <doc:item> + <doc:term>2</doc:term> + <doc:definition>Supervised user</doc:definition> + </doc:item> + </doc:list> + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="HomeDirectory" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users home directory. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="Shell" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users shell. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="Email" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The email address. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="Language" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users language, as a locale specification like "de_DE.UTF-8". + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="Location" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The users location. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="LoginFrequency" type="t" access="read"> + <doc:doc> + <doc:description> + <doc:para> + How often the user has logged in. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="IconFile" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The filename of a png file containing the users icon. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="Locked" type="b" access="read"> + <doc:doc> + <doc:description> + <doc:para> + Whether the users account is locked. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="PasswordMode" type="i" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The password mode for the user account, encoded as an integer: + <doc:list> + <doc:item> + <doc:term>0</doc:term> + <doc:definition>Regular password</doc:definition> + </doc:item> + <doc:item> + <doc:term>1</doc:term> + <doc:definition>Password must be set at next login</doc:definition> + </doc:item> + <doc:item> + <doc:term>2</doc:term> + <doc:definition>No password</doc:definition> + </doc:item> + </doc:list> + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="PasswordHint" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The password hint for the user. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <property name="AutomaticLogin" type="b" access="read"> + <doc:doc> + <doc:description> + <doc:para> + Whether automatic login is enabled for the user. + </doc:para> + </doc:description> + </doc:doc> + </property> + + <signal name="Changed"> + <doc:doc> + <doc:description> + <doc:para> + Emitted when the user is changed. + </doc:para> + </doc:description> + </doc:doc> + </signal> + + </interface> +</node> diff --git a/src/accounts-service.xml b/src/accounts-service.xml new file mode 100644 index 0000000..9c19761 --- /dev/null +++ b/src/accounts-service.xml @@ -0,0 +1,194 @@ +<!DOCTYPE node PUBLIC +"-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" +"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd" > +<node name="/" xmlns:doc="http://www.freedesktop.org/dbus/1.0/doc.dtd"> + <interface name="org.freedesktop.Accounts"> + + <!-- ************************************************************ --> + + <method name="ListCachedUsers"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="users" direction="out" type="ao"> + <doc:doc><doc:summary>Object paths of cached users</doc:summary></doc:doc> + </arg> + + <doc:doc> + <doc:description> + <doc:para> + Lists users which have logged into the system locally before. + This is not meant to return an exhaustive list of all users. + It is possible for <doc:ref type="method" to="Accounts.FindUserByName">FindUserByName()</doc:ref> + to return a user that's not on the list. + </doc:para> + </doc:description> + </doc:doc> + </method> + + <method name="FindUserById"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="id" direction="in" type="x"> + <doc:doc><doc:summary>The uid to look up</doc:summary></doc:doc> + </arg> + <arg name="user" direction="out" type="o"> + <doc:doc><doc:summary>Object path of user</doc:summary></doc:doc> + </arg> + + <doc:doc> + <doc:description> + <doc:para> + Finds a user by uid. + </doc:para> + </doc:description> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if no user with the given uid exists</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="FindUserByName"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="name" direction="in" type="s"> + <doc:doc><doc:summary>The username to look up</doc:summary></doc:doc> + </arg> + <arg name="user" direction="out" type="o"> + <doc:doc><doc:summary>Object path of user</doc:summary></doc:doc> + </arg> + + <doc:doc> + <doc:description> + <doc:para> + Finds a user by its username. + </doc:para> + </doc:description> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if no user with the given username exists</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="CreateUser"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="name" direction="in" type="s"> + <doc:doc><doc:summary>The username for the new user</doc:summary></doc:doc> + </arg> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="fullname" direction="in" type="s"> + <doc:doc><doc:summary>The real name for the new user</doc:summary></doc:doc> + </arg> + <arg name="user" direction="out" type="o"> + <doc:doc><doc:summary>Object path of the new user</doc:summary></doc:doc> + </arg> + <arg name="accountType" direction="in" type="i"> + <doc:doc> + <doc:summary>The account type, encoded as an integer</doc:summary> + </doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Creates a new user account. + </doc:para> + <doc:para> + The accountType argument can take the following values: + </doc:para> + <doc:list> + <doc:item> + <doc:term>0</doc:term> + <doc:definition>Standard user</doc:definition> + </doc:item> + <doc:item> + <doc:term>1</doc:term> + <doc:definition>Administrator</doc:definition> + </doc:item> + <doc:item> + <doc:term>2</doc:term> + <doc:definition>Supervised user</doc:definition> + </doc:item> + </doc:list> + </doc:description> + <doc:permission> + The caller needs the org.freedesktop.accounts.user-administration PolicyKit authorization. + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <method name="DeleteUser"> + <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> + <arg name="id" direction="in" type="x"> + <doc:doc><doc:summary>The uid to delete</doc:summary></doc:doc> + </arg> + <arg name="removeFiles" direction="in" type="b"> + <doc:doc><doc:summary>Whether to remove the users files</doc:summary></doc:doc> + </arg> + + <doc:doc> + <doc:description> + <doc:para> + Deletes a user account. + </doc:para> + </doc:description> + <doc:permission> + The caller needs the org.freedesktop.accounts.user-administration PolicyKit authorization. + </doc:permission> + <doc:errors> + <doc:error name="org.freedesktop.Accounts.Error.PermissionDenied">if the caller lacks the appropriate PolicyKit authorization</doc:error> + <doc:error name="org.freedesktop.Accounts.Error.Failed">if the operation failed</doc:error> + </doc:errors> + </doc:doc> + </method> + + <signal name="UserAdded"> + <arg name="user" type="o"> + <doc:doc><doc:summary>Object path of the user that was added.</doc:summary></doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Emitted when a user is added. + </doc:para> + </doc:description> + </doc:doc> + </signal> + + <signal name="UserDeleted"> + <arg name="user" type="o"> + <doc:doc><doc:summary>Object path of the user that was deleted.</doc:summary></doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Emitted when a user is deleted. + </doc:para> + </doc:description> + </doc:doc> + </signal> + + <signal name="UserChanged"> + <arg name="user" type="o"> + <doc:doc><doc:summary>Object path of the user that was changed.</doc:summary></doc:doc> + </arg> + <doc:doc> + <doc:description> + <doc:para> + Emitted when a user is changed. + </doc:para> + </doc:description> + </doc:doc> + </signal> + + <property name="DaemonVersion" type="s" access="read"> + <doc:doc> + <doc:description> + <doc:para> + The version of the running daemon. + </doc:para> + </doc:description> + </doc:doc> + </property> + + </interface> +</node> diff --git a/src/display-manager.xml b/src/display-manager.xml new file mode 100644 index 0000000..004eca1 --- /dev/null +++ b/src/display-manager.xml @@ -0,0 +1,17 @@ +<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" "http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd"> +<node> + <interface name="org.freedesktop.DisplayManager"> + + <!-- Show greeter to allow new login / switch users --> + <method name="ShowGreeter"/> + + <!-- Switch to a user, starting a new display if required --> + <method name="SwitchToUser"> + <arg name="username" direction="in" type="s"/> + </method> + + <!-- Switch to the guest user --> + <method name="SwitchToGuest"/> + + </interface> +</node> diff --git a/src/gdm-local-display-factory.xml b/src/gdm-local-display-factory.xml deleted file mode 100644 index 66fb77c..0000000 --- a/src/gdm-local-display-factory.xml +++ /dev/null @@ -1,20 +0,0 @@ -<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" "http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd"> -<node name="/org/gnome/DisplayManager/LocalDisplayFactory"> - <interface name="org.gnome.DisplayManager.LocalDisplayFactory"> - <method name="CreateProductDisplay"> - <arg name="parent_display_id" direction="in" type="o"/> - <arg name="relay_address" direction="in" type="s"/> - <arg name="id" direction="out" type="o"/> - </method> - <method name="CreateTransientDisplay"> - <arg name="id" direction="out" type="o"/> - </method> - <method name="StartGuestSession"> - <arg name="id" direction="out" type="o"/> - </method> - <method name="SwitchToUser"> - <arg name="username" direction="in" type="s"/> - <arg name="id" direction="out" type="o"/> - </method> - </interface> -</node> diff --git a/src/session-service.c b/src/session-service.c index 9cd7800..1c59bce 100644 --- a/src/session-service.c +++ b/src/session-service.c @@ -57,8 +57,6 @@ with this program. If not, see <http://www.gnu.org/licenses/>. #define EXTRA_LAUNCHER_DIR "/usr/share/indicators/session/applications" -#define GUEST_SESSION_LAUNCHER "/usr/share/gdm/guest-session/guest-session-launch" - #define LOCKDOWN_DIR "/desktop/gnome/lockdown" #define LOCKDOWN_KEY_USER LOCKDOWN_DIR "/disable_user_switching" #define LOCKDOWN_KEY_SCREENSAVER LOCKDOWN_DIR "/disable_lock_screen" @@ -73,8 +71,6 @@ struct _ActivateData UserData *user; }; -static DBusGConnection *system_bus = NULL; -static DBusGProxy *gdm_proxy = NULL; static UsersServiceDbus *dbus_interface = NULL; static SessionDbus *session_dbus = NULL; @@ -395,7 +391,7 @@ show_dialog (DbusmenuMenuitem * mi, guint timestamp, gchar * type) return; } -/* Checks to see if we should show the guest suession item */ +/* Checks to see if we should show the guest session item */ static gboolean check_guest_session (void) { @@ -404,11 +400,7 @@ check_guest_session (void) this would be the case of the guest user itself. */ return FALSE; } - if (!g_file_test(GUEST_SESSION_LAUNCHER, G_FILE_TEST_IS_EXECUTABLE)) { - /* It doesn't appear that the Guest session stuff is - installed. So let's not use it then! */ - return FALSE; - } + // FIXME: Ask DisplayManager return TRUE; } @@ -417,49 +409,18 @@ check_guest_session (void) static void activate_guest_session (DbusmenuMenuitem * mi, guint timestamp, gpointer user_data) { - GError * error = NULL; - lock_if_possible(); - if (dbusmenu_menuitem_property_get_bool(mi, USER_ITEM_PROP_LOGGED_IN)) { - if (users_service_dbus_activate_guest_session(USERS_SERVICE_DBUS(user_data))) { - return; - } - g_warning("Unable to activate guest session, falling back to command line activation."); - } - - if (!g_spawn_command_line_async(GUEST_SESSION_LAUNCHER " --no-lock", &error)) { - g_warning("Unable to start guest session: %s", error->message); - g_error_free(error); - } + if (!users_service_dbus_activate_guest_session(USERS_SERVICE_DBUS(user_data))) + g_warning("Unable to activate guest session"); return; } -/* Checks to see if we can create sessions and get a proxy - to the display manager (GDM) */ +/* Checks to see if we can create sessions */ static gboolean check_new_session (void) { - if (system_bus == NULL) { - system_bus = dbus_g_bus_get(DBUS_BUS_SYSTEM, NULL); - } - - if (system_bus == NULL) { - return FALSE; - } - - if (gdm_proxy == NULL) { - gdm_proxy = dbus_g_proxy_new_for_name(system_bus, - "org.gnome.DisplayManager", - "/org/gnome/DisplayManager/LocalDisplayFactory", - "org.gnome.DisplayManager.LocalDisplayFactory"); - } - - if (gdm_proxy == NULL) { - return FALSE; - } - return TRUE; } @@ -467,14 +428,9 @@ check_new_session (void) static void activate_new_session (DbusmenuMenuitem * mi, guint timestamp, gpointer user_data) { - GError * error = NULL; - lock_if_possible(); - if (!g_spawn_command_line_async("gdmflexiserver --startnew", &error)) { - g_warning("Unable to start new session: %s", error->message); - g_error_free(error); - } + users_service_dbus_show_greeter (USERS_SERVICE_DBUS(user_data)); return; } @@ -631,7 +587,7 @@ rebuild_user_items (DbusmenuMenuitem *root, dbusmenu_menuitem_property_set (switch_menuitem, DBUSMENU_MENUITEM_PROP_TYPE, MENU_SWITCH_TYPE); dbusmenu_menuitem_property_set (switch_menuitem, MENU_SWITCH_USER, g_get_user_name()); dbusmenu_menuitem_child_append (root, switch_menuitem); - g_signal_connect (G_OBJECT (switch_menuitem), DBUSMENU_MENUITEM_SIGNAL_ITEM_ACTIVATED, G_CALLBACK (activate_new_session), NULL); + g_signal_connect (G_OBJECT (switch_menuitem), DBUSMENU_MENUITEM_SIGNAL_ITEM_ACTIVATED, G_CALLBACK (activate_new_session), service); } GList * users = NULL; @@ -650,6 +606,7 @@ rebuild_user_items (DbusmenuMenuitem *root, /* Hide me from the list */ continue; } + g_debug ("%i %s", (gint)user->uid, user->user_name); if (g_strcmp0(user->user_name, "guest") == 0) { /* Check to see if the guest has sessions and so therefore should @@ -676,8 +633,8 @@ rebuild_user_items (DbusmenuMenuitem *root, dbusmenu_menuitem_property_set (mi, USER_ITEM_PROP_NAME, user->real_name); } dbusmenu_menuitem_property_set_bool (mi, USER_ITEM_PROP_LOGGED_IN, user->sessions != NULL); - if (user->icon_url != NULL && user->icon_url[0] != '\0' && g_str_has_prefix(user->icon_url, "file://")) { - dbusmenu_menuitem_property_set(mi, USER_ITEM_PROP_ICON, user->icon_url + strlen("file://")); + if (user->icon_file != NULL && user->icon_file[0] != '\0') { + dbusmenu_menuitem_property_set(mi, USER_ITEM_PROP_ICON, user->icon_file); } else { dbusmenu_menuitem_property_set(mi, USER_ITEM_PROP_ICON, USER_ITEM_ICON_DEFAULT); } @@ -830,7 +787,7 @@ rebuild_session_items (DbusmenuMenuitem *root, rebuilds the menu */ static void user_change (UsersServiceDbus *service, - gint64 user, + const gchar *user_id, gpointer user_data) { DbusmenuMenuitem *root = (DbusmenuMenuitem *)user_data; @@ -911,10 +868,10 @@ main (int argc, char ** argv) textdomain (GETTEXT_PACKAGE); IndicatorService * service = indicator_service_new_version(INDICATOR_SESSION_DBUS_NAME, - INDICATOR_SESSION_DBUS_VERSION); + INDICATOR_SESSION_DBUS_VERSION); g_signal_connect(G_OBJECT(service), - INDICATOR_SERVICE_SIGNAL_SHUTDOWN, - G_CALLBACK(service_shutdown), NULL); + INDICATOR_SERVICE_SIGNAL_SHUTDOWN, + G_CALLBACK(service_shutdown), NULL); session_dbus = session_dbus_new(); @@ -927,7 +884,6 @@ main (int argc, char ** argv) rebuild_session_items (session_root_menuitem, dbus_interface); - DbusmenuServer * server = dbusmenu_server_new(INDICATOR_SESSION_DBUS_OBJECT); dbusmenu_server_set_root(server, session_root_menuitem); @@ -943,6 +899,7 @@ main (int argc, char ** argv) users_root_menuitem); setup_restart_watch(); + setup_up(); DbusmenuServer * users_server = dbusmenu_server_new (INDICATOR_USERS_DBUS_OBJECT); diff --git a/src/users-service-dbus.c b/src/users-service-dbus.c index 07a81b1..087378c 100644 --- a/src/users-service-dbus.c +++ b/src/users-service-dbus.c @@ -31,10 +31,9 @@ #include <dbus/dbus-glib-lowlevel.h> #include "dbus-shared-names.h" -#include "gdm-local-display-factory-client.h" +#include "display-manager-client.h" #include "users-service-dbus.h" -#include "users-service-client.h" -#include "users-service-marshal.h" +#include "accounts-service-client.h" #include "consolekit-manager-client.h" #include "consolekit-session-client.h" @@ -46,21 +45,17 @@ static void users_service_dbus_class_init (UsersServiceDbusClass *kl static void users_service_dbus_init (UsersServiceDbus *self); static void users_service_dbus_dispose (GObject *object); static void users_service_dbus_finalize (GObject *object); -static void create_gdm_proxy (UsersServiceDbus *self); +static void create_display_manager_proxy (UsersServiceDbus *self); +static void create_accounts_service_proxy (UsersServiceDbus *self); static void create_seat_proxy (UsersServiceDbus *self); static void create_ck_proxy (UsersServiceDbus *self); static void create_cksession_proxy (UsersServiceDbus *self); static gchar *get_seat (UsersServiceDbus *service); -static void users_loaded (DBusGProxy *proxy, - gpointer user_data); static void user_added (DBusGProxy *proxy, - gint64 uid, - gpointer user_data); -static void user_removed (DBusGProxy *proxy, - gint64 uid, + const gchar *user_id, gpointer user_data); -static void user_updated (DBusGProxy *proxy, - guint uid, +static void user_deleted (DBusGProxy *proxy, + const gchar *user_id, gpointer user_data); static void seat_proxy_session_added (DBusGProxy *seat_proxy, const gchar *session_id, @@ -68,6 +63,7 @@ static void seat_proxy_session_added (DBusGProxy *seat_ static void seat_proxy_session_removed (DBusGProxy *seat_proxy, const gchar *session_id, UsersServiceDbus *service); +static void sync_users (UsersServiceDbus *self); static gboolean do_add_session (UsersServiceDbus *service, UserData *user, const gchar *ssid); @@ -85,8 +81,8 @@ struct _UsersServiceDbusPrivate DBusGConnection *system_bus; - DBusGProxy *gdm_proxy; - DBusGProxy *gdm_local_proxy; + DBusGProxy *accounts_service_proxy; + DBusGProxy *display_manager_proxy; DBusGProxy *ck_proxy; DBusGProxy *seat_proxy; DBusGProxy *session_proxy; @@ -102,10 +98,8 @@ struct _UsersServiceDbusPrivate /* Signals */ enum { - USERS_LOADED, USER_ADDED, - USER_REMOVED, - USER_UPDATED, + USER_DELETED, LAST_SIGNAL }; @@ -124,37 +118,21 @@ users_service_dbus_class_init (UsersServiceDbusClass *klass) object_class->dispose = users_service_dbus_dispose; object_class->finalize = users_service_dbus_finalize; - signals[USERS_LOADED] = g_signal_new ("users-loaded", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (UsersServiceDbusClass, users_loaded), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - signals[USER_ADDED] = g_signal_new ("user-added", G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST, G_STRUCT_OFFSET (UsersServiceDbusClass, user_added), NULL, NULL, - _users_service_marshal_VOID__INT64, - G_TYPE_NONE, 1, G_TYPE_INT64); + g_cclosure_marshal_VOID__STRING, + G_TYPE_NONE, 1, G_TYPE_STRING); - signals[USER_REMOVED] = g_signal_new ("user-removed", + signals[USER_DELETED] = g_signal_new ("user-deleted", G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (UsersServiceDbusClass, user_removed), + G_STRUCT_OFFSET (UsersServiceDbusClass, user_deleted), NULL, NULL, - _users_service_marshal_VOID__INT64, - G_TYPE_NONE, 1, G_TYPE_INT64); - - signals[USER_UPDATED] = g_signal_new ("user-updated", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (UsersServiceDbusClass, user_updated), - NULL, NULL, - _users_service_marshal_VOID__INT64, - G_TYPE_NONE, 1, G_TYPE_INT64); + g_cclosure_marshal_VOID__STRING, + G_TYPE_NONE, 1, G_TYPE_STRING); } static void @@ -188,17 +166,10 @@ users_service_dbus_init (UsersServiceDbus *self) g_free, NULL); - dbus_g_object_register_marshaller (_users_service_marshal_VOID__INT64, - G_TYPE_NONE, - G_TYPE_INT64, - G_TYPE_INVALID); - - create_gdm_proxy (self); create_ck_proxy (self); create_seat_proxy (self); - - if (priv->gdm_proxy) - users_loaded (priv->gdm_proxy, self); + create_display_manager_proxy (self); + create_accounts_service_proxy (self); } static void @@ -221,75 +192,75 @@ users_service_dbus_finalize (GObject *object) } static void -create_gdm_proxy (UsersServiceDbus *self) +create_display_manager_proxy (UsersServiceDbus *self) { UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - GError *error = NULL; - priv->gdm_proxy = dbus_g_proxy_new_for_name_owner (priv->system_bus, - "org.gnome.DisplayManager", - "/org/gnome/DisplayManager/UserManager", - "org.gnome.DisplayManager.UserManager", - &error); + priv->display_manager_proxy = dbus_g_proxy_new_for_name (priv->system_bus, + "org.freedesktop.DisplayManager", + "/org/freedesktop/DisplayManager", + "org.freedesktop.DisplayManager"); - if (!priv->gdm_proxy) + if (!priv->display_manager_proxy) { - if (error != NULL) - { - g_warning ("Unable to get DisplayManager proxy on system bus: %s", error->message); - g_error_free (error); - } - + g_warning ("Failed to get DisplayManager proxy."); return; } +} - dbus_g_proxy_add_signal (priv->gdm_proxy, - "UsersLoaded", - G_TYPE_INVALID); +static void +create_accounts_service_proxy (UsersServiceDbus *self) +{ + UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); + GPtrArray *users = g_ptr_array_new (); + GError *error = NULL; + + priv->accounts_service_proxy = dbus_g_proxy_new_for_name (priv->system_bus, + "org.freedesktop.Accounts", + "/org/freedesktop/Accounts", + "org.freedesktop.Accounts"); - dbus_g_proxy_add_signal (priv->gdm_proxy, + dbus_g_proxy_add_signal (priv->accounts_service_proxy, "UserAdded", - G_TYPE_INT64, + DBUS_TYPE_G_OBJECT_PATH, G_TYPE_INVALID); - dbus_g_proxy_add_signal (priv->gdm_proxy, - "UserRemoved", - G_TYPE_INT64, + dbus_g_proxy_add_signal (priv->accounts_service_proxy, + "UserChanged", + DBUS_TYPE_G_OBJECT_PATH, G_TYPE_INVALID); - dbus_g_proxy_add_signal (priv->gdm_proxy, - "UserUpdated", - G_TYPE_INT64, + dbus_g_proxy_add_signal (priv->accounts_service_proxy, + "UserDeleted", + DBUS_TYPE_G_OBJECT_PATH, G_TYPE_INVALID); - dbus_g_proxy_connect_signal (priv->gdm_proxy, - "UsersLoaded", - G_CALLBACK (users_loaded), - self, - NULL); - - dbus_g_proxy_connect_signal (priv->gdm_proxy, + dbus_g_proxy_connect_signal (priv->accounts_service_proxy, "UserAdded", G_CALLBACK (user_added), self, NULL); - dbus_g_proxy_connect_signal (priv->gdm_proxy, - "UserRemoved", - G_CALLBACK (user_removed), + dbus_g_proxy_connect_signal (priv->accounts_service_proxy, + "UserDeleted", + G_CALLBACK (user_deleted), self, NULL); - dbus_g_proxy_connect_signal (priv->gdm_proxy, - "UserUpdated", - G_CALLBACK (user_updated), - self, - NULL); + if (!org_freedesktop_Accounts_list_cached_users (priv->accounts_service_proxy, + &users, + &error)) + { + g_warning ("failed to retrieve user count: %s", error->message); + g_error_free (error); - priv->gdm_local_proxy = dbus_g_proxy_new_for_name (priv->system_bus, - "org.gnome.DisplayManager", - "/org/gnome/DisplayManager/LocalDisplayFactory", - "org.gnome.DisplayManager.LocalDisplayFactory"); + return; + } + + priv->count = users->len; + g_ptr_array_free (users, TRUE); + + sync_users (self); } static void @@ -614,11 +585,9 @@ seat_proxy_session_added (DBusGProxy *seat_proxy, return; } - user = g_hash_table_lookup (priv->users, pwent->pw_name); + user = users_service_dbus_get_user_by_username (service, pwent->pw_name); if (!user) - { - return; - } + return; do_add_session (service, user, session_id); } @@ -647,7 +616,7 @@ seat_proxy_session_removed (DBusGProxy *seat_proxy, return; } - user = g_hash_table_lookup (priv->users, username); + user = users_service_dbus_get_user_by_username (service, username); if (!user) return; @@ -683,16 +652,15 @@ sync_users (UsersServiceDbus *self) if (priv->count > MINIMUM_USERS && priv->count < MAXIMUM_USERS) { - GArray *uids = NULL; - GPtrArray *users_info = NULL; + GPtrArray *users = NULL; GError *error = NULL; gint i; - uids = g_array_new (FALSE, FALSE, sizeof (gint64)); + users = g_ptr_array_new (); - if (!org_gnome_DisplayManager_UserManager_get_user_list (priv->gdm_proxy, - &uids, - &error)) + if (!org_freedesktop_Accounts_list_cached_users (priv->accounts_service_proxy, + &users, + &error)) { g_warning ("failed to retrieve user list: %s", error->message); g_error_free (error); @@ -700,374 +668,101 @@ sync_users (UsersServiceDbus *self) return; } - users_info = g_ptr_array_new (); - - if (!org_gnome_DisplayManager_UserManager_get_users_info (priv->gdm_proxy, - uids, - &users_info, - &error)) + for (i = 0; i < users->len; i++) { - g_warning ("failed to retrieve user info: %s", error->message); - g_error_free (error); + gchar *id; + DBusGProxy *proxy; + UserData *user; + GError *error = NULL; - return; - } + id = g_ptr_array_index (users, i); - for (i = 0; i < users_info->len; i++) - { - GValueArray *values; - UserData *user; + proxy = dbus_g_proxy_new_for_name (priv->system_bus, + "org.freedesktop.Accounts", + id, + "org.freedesktop.DBus.Properties"); - values = g_ptr_array_index (users_info, i); + GHashTable *properties; + if (!dbus_g_proxy_call (proxy, "GetAll", &error, + G_TYPE_STRING, "org.freedesktop.Accounts.User", G_TYPE_INVALID, + dbus_g_type_get_map ("GHashTable", G_TYPE_STRING, G_TYPE_VALUE), &properties, G_TYPE_INVALID)) + { + g_warning ("unable to retrieve user info: %s", error->message); + g_error_free (error); + + continue; + } user = g_new0 (UserData, 1); - user->uid = g_value_get_int64 (g_value_array_get_nth (values, 0)); - user->user_name = g_strdup (g_value_get_string (g_value_array_get_nth (values, 1))); - user->real_name = g_strdup (g_value_get_string (g_value_array_get_nth (values, 2))); - user->shell = g_strdup (g_value_get_string (g_value_array_get_nth (values, 3))); - user->login_count = g_value_get_int (g_value_array_get_nth (values, 4)); - user->icon_url = g_strdup (g_value_get_string (g_value_array_get_nth (values, 5))); + user->uid = g_value_get_uint64 (g_hash_table_lookup (properties, "Uid")); + user->user_name = g_strdup (g_value_get_string (g_hash_table_lookup (properties, "UserName"))); + user->real_name = g_strdup (g_value_get_string (g_hash_table_lookup (properties, "RealName"))); + user->icon_file = g_strdup (g_value_get_string (g_hash_table_lookup (properties, "IconFile"))); user->real_name_conflict = FALSE; user->menuitem = NULL; + g_hash_table_unref (properties); + g_hash_table_insert (priv->users, - g_strdup (user->user_name), + g_strdup (id), user); add_sessions_for_user (self, user); } - } -} - -static void -users_loaded (DBusGProxy *proxy, - gpointer user_data) -{ - UsersServiceDbus *service; - UsersServiceDbusPrivate *priv; - GError *error = NULL; - gint count; - - g_return_if_fail (proxy != NULL); - - service = (UsersServiceDbus *)user_data; - priv = USERS_SERVICE_DBUS_GET_PRIVATE (service); - - if (!org_gnome_DisplayManager_UserManager_count_users (proxy, - &count, - &error)) - { - g_warning ("failed to retrieve user count: %s", error->message); - g_error_free (error); - - return; - } - - priv->count = count; - - sync_users (service); -} - -static gboolean -session_is_login_window (UsersServiceDbus *self, - const char *ssid) -{ - g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), FALSE); - UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - DBusGProxy *proxy = NULL; - GError *error = NULL; - char *type = NULL; - - if (!(proxy = dbus_g_proxy_new_for_name (priv->system_bus, - CK_ADDR, - ssid, - CK_SESSION_IFACE))) - { - g_warning ("Failed to get ConsoleKit proxy"); - - return FALSE; - } - - if (!org_freedesktop_ConsoleKit_Session_get_session_type (proxy, &type, &error)) - { - g_warning ("Can't call GetSessionType: %s", error->message); - g_error_free (error); - - if (proxy) - g_object_unref (proxy); - - return FALSE; - } - - if (proxy) - g_object_unref (proxy); - - return (type && type[0] != '\0' && strcmp (type, "LoginWindow") == 0); -} - -static char * -get_login_session (UsersServiceDbus *self) -{ - g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), NULL); - UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - gboolean can_activate; - GError *error = NULL; - GPtrArray *sessions = NULL; - char *ssid = NULL; - int i; - - if (!priv->seat || priv->seat[0] == '\0') - { - return NULL; - } - - if (!dbus_g_proxy_call (priv->seat_proxy, - "CanActivateSessions", - &error, - G_TYPE_INVALID, - G_TYPE_BOOLEAN, &can_activate, - G_TYPE_INVALID)) - { - g_warning ("Failed to call CanActivateSessions: %s", error->message); - g_error_free (error); - - return NULL; - } - - if (!can_activate) - { - return NULL; - } - - error = NULL; - if (!dbus_g_proxy_call (priv->seat_proxy, - "GetSessions", - &error, - G_TYPE_INVALID, - dbus_g_type_get_collection ("GPtrArray", DBUS_TYPE_G_OBJECT_PATH), &sessions, - G_TYPE_INVALID)) - { - g_warning ("Failed to call GetSessions: %s", error->message); - g_error_free (error); - - return NULL; - } - - for (i = 0; i < sessions->len; i++) - { - char *s = g_ptr_array_index (sessions, i); - - if (session_is_login_window (self, s)) - { - ssid = g_strdup (s); - break; - } - } - - g_ptr_array_foreach (sessions, (GFunc)g_free, NULL); - g_ptr_array_free (sessions, TRUE); - - return ssid; -} - -static gboolean -activate_user_session (UsersServiceDbus *self, - const char *seat, - const char *ssid) -{ - g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), FALSE); - UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - DBusMessage *message = NULL; - DBusMessage *reply = NULL; - DBusError error; - - if (!(message = dbus_message_new_method_call ("org.freedesktop.ConsoleKit", - seat, - "org.freedesktop.ConsoleKit.Seat", - "ActivateSession"))) - { - return FALSE; - } - - if (!dbus_message_append_args (message, - DBUS_TYPE_OBJECT_PATH, &ssid, - DBUS_TYPE_INVALID)) - { - return FALSE; - } - - dbus_error_init (&error); - if (!(reply = dbus_connection_send_with_reply_and_block (dbus_g_connection_get_connection (priv->system_bus), - message, - -1, - &error))) - { - if (dbus_error_is_set (&error)) - { - g_warning ("Can't activate session: %s", error.message); - dbus_error_free (&error); - - return FALSE; - } - } - - if (message) - { - dbus_message_unref (message); - } - if (reply) - { - dbus_message_unref (reply); + g_ptr_array_free (users, TRUE); } - - return TRUE; -} - -gboolean -start_new_user_session (UsersServiceDbus *self, - UserData *user) -{ - g_return_val_if_fail (IS_USERS_SERVICE_DBUS (self), FALSE); - - UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - GError *error = NULL; - char *ssid; - - ssid = get_login_session (self); - if (ssid) - { - if (!activate_user_session (self, priv->seat, ssid)) - { - return FALSE; - } - } - - if (!g_spawn_command_line_async ("gdmflexiserver -s", &error)) - { - g_warning ("Failed to start new login session: %s", error->message); - g_error_free (error); - - return FALSE; - } - - return TRUE; } static void -user_added (DBusGProxy *proxy, - gint64 uid, - gpointer user_data) +user_added (DBusGProxy *proxy, + const gchar *user_id, + gpointer user_data) { UsersServiceDbus *service = (UsersServiceDbus *)user_data; UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (service); - UserData *user = g_new0 (UserData, 1); - GError *error = NULL; priv->count++; if (priv->count < MAXIMUM_USERS) { - if ((priv->count - g_hash_table_size (priv->users)) > 1) - { - sync_users (service); - } - else - { - if (!org_gnome_DisplayManager_UserManager_get_user_info (proxy, - uid, - &user->user_name, - &user->real_name, - &user->shell, - &user->login_count, - &user->icon_url, - &error)) - { - g_warning ("unable to retrieve user info: %s", error->message); - g_error_free (error); - - g_free (user); - - return; - } - - user->uid = uid; - - g_hash_table_insert (priv->users, - g_strdup (user->user_name), - user); - - g_signal_emit (G_OBJECT (service), signals[USER_ADDED], 0, user, TRUE); - } + sync_users (service); } } -static gboolean -compare_users_by_uid (gpointer key, - gpointer value, - gpointer user_data) -{ - return (GPOINTER_TO_UINT (value) == GPOINTER_TO_UINT (user_data)); -} - static void -user_removed (DBusGProxy *proxy, - gint64 uid, - gpointer user_data) +user_deleted (DBusGProxy *proxy, + const gchar *user_id, + gpointer user_data) { UsersServiceDbus *service = (UsersServiceDbus *)user_data; UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (service); - UserData *user; - gint size; - - size = g_hash_table_size (priv->users); priv->count--; - - if (size == 0 || (size - priv->count) > 1) - { - sync_users (service); - } - else - { - user = g_hash_table_find (priv->users, - compare_users_by_uid, - GUINT_TO_POINTER ((gint)uid)); - - if (user != NULL) - { - g_hash_table_remove (priv->users, - user->user_name); - } - } + g_hash_table_remove (priv->users, user_id); } -static void -user_updated (DBusGProxy *proxy, - guint uid, - gpointer user_data) +UserData * +users_service_dbus_get_user_by_username (UsersServiceDbus *self, + const gchar *username) { -#if 0 - // XXX - TODO - UsersServiceDbus *service = (UsersServiceDbus *)user_data; - UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (service); - UserData *user; + GHashTableIter iter; + gpointer value; - user = g_hash_table_find (priv->users, - compare_users_by_uid, - GUINT_TO_POINTER (uid)); -#endif -} - -gint -users_service_dbus_get_user_count (UsersServiceDbus *self) -{ - g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), 0); + g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), NULL); UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - return priv->count; + g_hash_table_iter_init (&iter, priv->users); + while (g_hash_table_iter_next (&iter, NULL, &value)) + { + UserData *user = value; + if (strcmp (user->user_name, username) == 0) + return user; + } + + return NULL; } GList * @@ -1080,13 +775,21 @@ users_service_dbus_get_user_list (UsersServiceDbus *self) return g_hash_table_get_values (priv->users); } +gboolean +users_service_dbus_show_greeter (UsersServiceDbus *self) +{ + g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), FALSE); + UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); + return org_freedesktop_DisplayManager_show_greeter(priv->display_manager_proxy, NULL); +} + /* Activates the guest account if it can. */ gboolean users_service_dbus_activate_guest_session (UsersServiceDbus *self) { g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), FALSE); UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - return org_gnome_DisplayManager_LocalDisplayFactory_switch_to_user(priv->gdm_local_proxy, "guest", NULL, NULL); + return org_freedesktop_DisplayManager_switch_to_guest(priv->display_manager_proxy, NULL); } /* Activates a specific user */ @@ -1096,7 +799,7 @@ users_service_dbus_activate_user_session (UsersServiceDbus *self, { g_return_val_if_fail(IS_USERS_SERVICE_DBUS(self), FALSE); UsersServiceDbusPrivate *priv = USERS_SERVICE_DBUS_GET_PRIVATE (self); - return org_gnome_DisplayManager_LocalDisplayFactory_switch_to_user(priv->gdm_local_proxy, user->user_name, NULL, NULL); + return org_freedesktop_DisplayManager_switch_to_user(priv->display_manager_proxy, user->user_name, NULL); } gboolean diff --git a/src/users-service-dbus.h b/src/users-service-dbus.h index 4798d64..c3f0171 100644 --- a/src/users-service-dbus.h +++ b/src/users-service-dbus.h @@ -42,9 +42,7 @@ struct _UserData gint64 uid; gchar *user_name; gchar *real_name; - gchar *shell; - gint login_count; - gchar *icon_url; + gchar *icon_file; GList *sessions; @@ -70,17 +68,16 @@ struct _UsersServiceDbusClass { GObjectClass parent_class; /* Signals */ - void (* users_loaded) (UsersServiceDbus *self, gpointer user_data); - - void (* user_added) (UsersServiceDbus *self, gint64 uid, gpointer user_data); - void (* user_removed) (UsersServiceDbus *self, gint64 uid, gpointer user_data); - void (* user_updated) (UsersServiceDbus *self, gint64 uid, gpointer user_data); + void (* user_added) (UsersServiceDbus *self, const gchar *user_id, gpointer user_data); + void (* user_deleted) (UsersServiceDbus *self, const gchar *user_id, gpointer user_data); }; GType users_service_dbus_get_type (void) G_GNUC_CONST; -gint users_service_dbus_get_user_count (UsersServiceDbus *self); +UserData *users_service_dbus_get_user_by_username (UsersServiceDbus *self, + const gchar *username); GList *users_service_dbus_get_user_list (UsersServiceDbus *self); +gboolean users_service_dbus_show_greeter (UsersServiceDbus *self); gboolean users_service_dbus_can_activate_session (UsersServiceDbus *self); gboolean users_service_dbus_activate_user_session (UsersServiceDbus *self, UserData *user); diff --git a/src/users-service.list b/src/users-service.list deleted file mode 100644 index 36f34ba..0000000 --- a/src/users-service.list +++ /dev/null @@ -1 +0,0 @@ -VOID:INT64 diff --git a/src/users-service.xml b/src/users-service.xml deleted file mode 100644 index c90f1e8..0000000 --- a/src/users-service.xml +++ /dev/null @@ -1,56 +0,0 @@ -<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" "http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd"> -<node name="/org/gnome/DisplayManager/UserManager"> - <interface name="org.gnome.DisplayManager.UserManager"> - - <!-- Get the number of known users --> - <method name="CountUsers"> - <arg name="user_count" direction="out" type="i"/> - </method> - - <!-- Get the list of known UIDs --> - <method name="GetUserList"> - <arg name="uids" direction="out" type="ax"/> - </method> - - <!-- Get user info for a user --> - <method name="GetUserInfo"> - <arg name="uid" direction="in" type="x"/> - <arg name="user_name" direction="out" type="s"/> - <arg name="real_name" direction="out" type="s"/> - <arg name="shell" direction="out" type="s"/> - <arg name="login_count" direction="out" type="i"/> - <arg name="icon_url" direction="out" type="s"/> - </method> - - <!-- Get user info for a list of users --> - <method name="GetUsersInfo"> - <arg name="uid" direction="in" type="ax"/> - <!-- (uid, user_name, real_name, shell, icon_url) --> - <arg name="user_info" direction="out" type="a(xsssis)"/> - </method> - - <!-- Query if the initial user list is loaded --> - <method name="GetUsersLoaded"> - <arg name="is_loaded" direction="out" type="b"/> - </method> - - <!-- Triggered when the initial user list is loaded --> - <signal name="UsersLoaded"></signal> - - <!-- Triggered when a users are added to/removed from the system. - Clients should monitor these signals as soon as they connect to - this object --> - <signal name="UserAdded"> - <arg name="uid" type="x"/> - </signal> - <signal name="UserRemoved"> - <arg name="uid" type="x"/> - </signal> - - <!-- Triggered when a user has updated information --> - <signal name="UserUpdated"> - <arg name="uid" type="x"/> - </signal> - - </interface> -</node> |