gnu: Add julia-compilersupportlibraries-jll.
[jackhill/guix/guix.git] / gnu / services / desktop.scm
index 7940f28..265cf9f 100644 (file)
@@ -1,13 +1,17 @@
 ;;; GNU Guix --- Functional package management for GNU
-;;; Copyright © 2014, 2015, 2016, 2017, 2018, 2019 Ludovic Courtès <ludo@gnu.org>
+;;; Copyright © 2014, 2015, 2016, 2017, 2018, 2019, 2020 Ludovic Courtès <ludo@gnu.org>
 ;;; Copyright © 2015 Andy Wingo <wingo@igalia.com>
 ;;; Copyright © 2015 Mark H Weaver <mhw@netris.org>
 ;;; Copyright © 2016 Sou Bunnbu <iyzsong@gmail.com>
-;;; Copyright © 2017 Maxim Cournoyer <maxim.cournoyer@gmail.com>
-;;; Copyright © 2017 Nils Gillmann <ng0@n0.is>
-;;; Copyright © 2018 Efraim Flashner <efraim@flashner.co.il>
+;;; Copyright © 2017, 2020 Maxim Cournoyer <maxim.cournoyer@gmail.com>
+;;; Copyright © 2017 Nikita <nikita@n0.is>
+;;; Copyright © 2018, 2020 Efraim Flashner <efraim@flashner.co.il>
 ;;; Copyright © 2018 Ricardo Wurmus <rekado@elephly.net>
 ;;; Copyright © 2017, 2019 Christopher Baines <mail@cbaines.net>
+;;; Copyright © 2019 Tim Gesthuizen <tim.gesthuizen@yahoo.de>
+;;; Copyright © 2019 David Wilson <david@daviwil.com>
+;;; Copyright © 2020 Tobias Geerinckx-Rice <me@tobias.gr>
+;;; Copyright © 2020 Reza Alizadeh Majd <r.majd@pantherx.org>
 ;;;
 ;;; This file is part of GNU Guix.
 ;;;
@@ -34,7 +38,7 @@
   #:use-module (gnu services networking)
   #:use-module (gnu services sound)
   #:use-module ((gnu system file-systems)
-                #:select (%elogind-file-systems))
+                #:select (%elogind-file-systems file-system))
   #:use-module (gnu system)
   #:use-module (gnu system shadow)
   #:use-module (gnu system pam)
   #:use-module (gnu packages xfce)
   #:use-module (gnu packages avahi)
   #:use-module (gnu packages xdisorg)
+  #:use-module (gnu packages scanner)
   #:use-module (gnu packages suckless)
   #:use-module (gnu packages linux)
   #:use-module (gnu packages libusb)
+  #:use-module (gnu packages lxqt)
   #:use-module (gnu packages mate)
+  #:use-module (gnu packages nfs)
   #:use-module (gnu packages enlightenment)
   #:use-module (guix deprecation)
   #:use-module (guix records)
@@ -83,6 +90,7 @@
             udisks-service
             udisks-service-type
 
+            colord-service-type
             colord-service
 
             geoclue-application
             geoclue-service
             geoclue-service-type
 
+            bluetooth-service-type
+            bluetooth-configuration
+            bluetooth-configuration?
             bluetooth-service
 
             elogind-configuration
             elogind-service
             elogind-service-type
 
+            %fontconfig-file-system
+            fontconfig-file-system-service
+
             accountsservice-service-type
             accountsservice-service
 
+            cups-pk-helper-service-type
+            sane-service-type
+
             gnome-desktop-configuration
             gnome-desktop-configuration?
             gnome-desktop-service
             mate-desktop-service
             mate-desktop-service-type
 
+            lxqt-desktop-configuration
+            lxqt-desktop-configuration?
+            lxqt-desktop-service-type
+
             xfce-desktop-configuration
             xfce-desktop-configuration?
             xfce-desktop-service
             enlightenment-desktop-configuration?
             enlightenment-desktop-service-type
 
+            inputattach-configuration
+            inputattach-configuration?
+            inputattach-service-type
+
+            polkit-wheel-service
+
+            gnome-keyring-configuration
+            gnome-keyring-configuration?
+            gnome-keyring-service-type
+
             %desktop-services))
 
 ;;; Commentary:
       ((package . _) package))))
 
 
-(define (wrapped-dbus-service service program variable value)
-  "Return a wrapper for @var{service}, a package containing a D-Bus service,
-where @var{program} is wrapped such that environment variable @var{variable}
-is set to @var{value} when the bus daemon launches it."
-  (define wrapper
-    (program-file (string-append (package-name service) "-program-wrapper")
-                  #~(begin
-                      (setenv #$variable #$value)
-                      (apply execl (string-append #$service "/" #$program)
-                             (string-append #$service "/" #$program)
-                             (cdr (command-line))))))
-
-  (define build
-    (with-imported-modules '((guix build utils))
-      #~(begin
-          (use-modules (guix build utils))
-
-          (define service-directory
-            "/share/dbus-1/system-services")
-
-          (mkdir-p (dirname (string-append #$output
-                                           service-directory)))
-          (copy-recursively (string-append #$service
-                                           service-directory)
-                            (string-append #$output
-                                           service-directory))
-          (symlink (string-append #$service "/etc") ;for etc/dbus-1
-                   (string-append #$output "/etc"))
-
-          (for-each (lambda (file)
-                      (substitute* file
-                        (("Exec[[:blank:]]*=[[:blank:]]*([[:graph:]]+)(.*)$"
-                          _ original-program arguments)
-                         (string-append "Exec=" #$wrapper arguments
-                                        "\n"))))
-                    (find-files #$output "\\.service$")))))
-
-  (computed-file (string-append (package-name service) "-wrapper")
-                 build))
-
 \f
 ;;;
 ;;; Upower D-Bus service.
@@ -252,8 +243,8 @@ is set to @var{value} when the bus daemon launches it."
 (define (upower-dbus-service config)
   (list (wrapped-dbus-service (upower-configuration-upower config)
                               "libexec/upowerd"
-                              "UPOWER_CONF_FILE_NAME"
-                              (upower-configuration-file config))))
+                              `(("UPOWER_CONF_FILE_NAME"
+                                 ,(upower-configuration-file config))))))
 
 (define (upower-shepherd-service config)
   "Return a shepherd service for UPower with CONFIG."
@@ -384,8 +375,8 @@ users are allowed."
 (define (geoclue-dbus-service config)
   (list (wrapped-dbus-service (geoclue-configuration-geoclue config)
                               "libexec/geoclue"
-                              "GEOCLUE_CONFIG_FILE"
-                              (geoclue-configuration-file config))))
+                              `(("GEOCLUE_CONFIG_FILE"
+                                 ,(geoclue-configuration-file config))))))
 
 (define %geoclue-accounts
   (list (user-group (name "geoclue") (system? #t))
@@ -468,8 +459,8 @@ site} for more information."
    (requirement '(dbus-system udev))
    (documentation "Run the bluetoothd daemon.")
    (start #~(make-forkexec-constructor
-             (string-append #$(bluetooth-configuration-bluez config)
-                            "/libexec/bluetooth/bluetoothd")))
+             (list #$(file-append (bluetooth-configuration-bluez config)
+                                  "/libexec/bluetooth/bluetoothd"))))
    (stop #~(make-kill-destructor))))
 
 (define bluetooth-service-type
@@ -485,7 +476,10 @@ site} for more information."
                                `(("bluetooth"
                                   ,(bluetooth-directory config)))))
           (service-extension shepherd-root-service-type
-                             (compose list bluetooth-shepherd-service))))))
+                             (compose list bluetooth-shepherd-service))))
+   (default-value (bluetooth-configuration))
+   (description "Run the @command{bluetoothd} daemon, which manages all the
+Bluetooth devices and provides a number of D-Bus interfaces.")))
 
 (define* (bluetooth-service #:key (bluez bluez) (auto-enable? #f))
   "Return a service that runs the @command{bluetoothd} daemon, which manages
@@ -539,9 +533,15 @@ Users need to be in the @code{lp} group to access the D-Bus service.
                        (service-extension udev-service-type list)
 
                        ;; It provides polkit "actions".
-                       (service-extension polkit-service-type list)))))
+                       (service-extension polkit-service-type list)))
+                (default-value colord)
+                (description
+                 "Run @command{colord}, a system service with a D-Bus
+interface to manage the color profiles of input and output devices such as
+screens and scanners.")))
 
-(define* (colord-service #:key (colord colord))
+(define-deprecated (colord-service #:key (colord colord))
+  colord-service-type
   "Return a service that runs @command{colord}, a system service with a D-Bus
 interface to manage the color profiles of input and output devices such as
 screens and scanners.  It is notably used by the GNOME Color Manager graphical
@@ -602,65 +602,67 @@ include the @command{udisksctl} command, part of UDisks, and GNOME Disks."
 
 (define-record-type* <elogind-configuration> elogind-configuration
   make-elogind-configuration
-  elogind-configuration
-  (elogind                         elogind-package
-                                   (default elogind))
-  (kill-user-processes?            elogind-kill-user-processes?
-                                   (default #f))
-  (kill-only-users                 elogind-kill-only-users
-                                   (default '()))
-  (kill-exclude-users              elogind-kill-exclude-users
-                                   (default '("root")))
-  (inhibit-delay-max-seconds       elogind-inhibit-delay-max-seconds
-                                   (default 5))
-  (handle-power-key                elogind-handle-power-key
-                                   (default 'poweroff))
-  (handle-suspend-key              elogind-handle-suspend-key
-                                   (default 'suspend))
-  (handle-hibernate-key            elogind-handle-hibernate-key
-                                   ;; (default 'hibernate)
-                                   ;; XXX Ignore it for now, since we don't
-                                   ;; yet handle resume-from-hibernation in
-                                   ;; our initrd.
-                                   (default 'ignore))
-  (handle-lid-switch               elogind-handle-lid-switch
-                                   (default 'suspend))
-  (handle-lid-switch-docked        elogind-handle-lid-switch-docked
-                                   (default 'ignore))
-  (power-key-ignore-inhibited?     elogind-power-key-ignore-inhibited?
-                                   (default #f))
-  (suspend-key-ignore-inhibited?   elogind-suspend-key-ignore-inhibited?
-                                   (default #f))
-  (hibernate-key-ignore-inhibited? elogind-hibernate-key-ignore-inhibited?
-                                   (default #f))
-  (lid-switch-ignore-inhibited?    elogind-lid-switch-ignore-inhibited?
-                                   (default #t))
-  (holdoff-timeout-seconds         elogind-holdoff-timeout-seconds
-                                   (default 30))
-  (idle-action                     elogind-idle-action
-                                   (default 'ignore))
-  (idle-action-seconds             elogind-idle-action-seconds
-                                   (default (* 30 60)))
-  (runtime-directory-size-percent  elogind-runtime-directory-size-percent
-                                   (default 10))
-  (runtime-directory-size          elogind-runtime-directory-size
-                                   (default #f))
-  (remove-ipc?                     elogind-remove-ipc?
-                                   (default #t))
-
-  (suspend-state                   elogind-suspend-state
-                                   (default '("mem" "standby" "freeze")))
-  (suspend-mode                    elogind-suspend-mode
-                                   (default '()))
-  (hibernate-state                 elogind-hibernate-state
-                                   (default '("disk")))
-  (hibernate-mode                  elogind-hibernate-mode
-                                   (default '("platform" "shutdown")))
-  (hybrid-sleep-state              elogind-hybrid-sleep-state
-                                   (default '("disk")))
-  (hybrid-sleep-mode               elogind-hybrid-sleep-mode
-                                   (default
-                                     '("suspend" "platform" "shutdown"))))
+  elogind-configuration?
+  (elogind                          elogind-package
+                                    (default elogind))
+  (kill-user-processes?             elogind-kill-user-processes?
+                                    (default #f))
+  (kill-only-users                  elogind-kill-only-users
+                                    (default '()))
+  (kill-exclude-users               elogind-kill-exclude-users
+                                    (default '("root")))
+  (inhibit-delay-max-seconds        elogind-inhibit-delay-max-seconds
+                                    (default 5))
+  (handle-power-key                 elogind-handle-power-key
+                                    (default 'poweroff))
+  (handle-suspend-key               elogind-handle-suspend-key
+                                    (default 'suspend))
+  (handle-hibernate-key             elogind-handle-hibernate-key
+                                    ;; (default 'hibernate)
+                                    ;; XXX Ignore it for now, since we don't
+                                    ;; yet handle resume-from-hibernation in
+                                    ;; our initrd.
+                                    (default 'ignore))
+  (handle-lid-switch                elogind-handle-lid-switch
+                                    (default 'suspend))
+  (handle-lid-switch-docked         elogind-handle-lid-switch-docked
+                                    (default 'ignore))
+  (handle-lid-switch-external-power elogind-handle-lid-switch-external-power
+                                    (default 'ignore))
+  (power-key-ignore-inhibited?      elogind-power-key-ignore-inhibited?
+                                    (default #f))
+  (suspend-key-ignore-inhibited?    elogind-suspend-key-ignore-inhibited?
+                                    (default #f))
+  (hibernate-key-ignore-inhibited?  elogind-hibernate-key-ignore-inhibited?
+                                    (default #f))
+  (lid-switch-ignore-inhibited?     elogind-lid-switch-ignore-inhibited?
+                                    (default #t))
+  (holdoff-timeout-seconds          elogind-holdoff-timeout-seconds
+                                    (default 30))
+  (idle-action                      elogind-idle-action
+                                    (default 'ignore))
+  (idle-action-seconds              elogind-idle-action-seconds
+                                    (default (* 30 60)))
+  (runtime-directory-size-percent   elogind-runtime-directory-size-percent
+                                    (default 10))
+  (runtime-directory-size           elogind-runtime-directory-size
+                                    (default #f))
+  (remove-ipc?                      elogind-remove-ipc?
+                                    (default #t))
+
+  (suspend-state                    elogind-suspend-state
+                                    (default '("mem" "standby" "freeze")))
+  (suspend-mode                     elogind-suspend-mode
+                                    (default '()))
+  (hibernate-state                  elogind-hibernate-state
+                                    (default '("disk")))
+  (hibernate-mode                   elogind-hibernate-mode
+                                    (default '("platform" "shutdown")))
+  (hybrid-sleep-state               elogind-hybrid-sleep-state
+                                    (default '("disk")))
+  (hybrid-sleep-mode                elogind-hybrid-sleep-mode
+                                    (default
+                                      '("suspend" "platform" "shutdown"))))
 
 (define (elogind-configuration-file config)
   (define (yesno x)
@@ -712,6 +714,7 @@ include the @command{udisksctl} command, part of UDisks, and GNOME Disks."
    ("HandleHibernateKey" (handle-action elogind-handle-hibernate-key))
    ("HandleLidSwitch" (handle-action elogind-handle-lid-switch))
    ("HandleLidSwitchDocked" (handle-action elogind-handle-lid-switch-docked))
+   ("HandleLidSwitchExternalPower" (handle-action elogind-handle-lid-switch-external-power))
    ("PowerKeyIgnoreInhibited" (yesno elogind-power-key-ignore-inhibited?))
    ("SuspendKeyIgnoreInhibited" (yesno elogind-suspend-key-ignore-inhibited?))
    ("HibernateKeyIgnoreInhibited" (yesno elogind-hibernate-key-ignore-inhibited?))
@@ -737,8 +740,8 @@ include the @command{udisksctl} command, part of UDisks, and GNOME Disks."
 (define (elogind-dbus-service config)
   (list (wrapped-dbus-service (elogind-package config)
                               "libexec/elogind/elogind"
-                              "ELOGIND_CONF_FILE"
-                              (elogind-configuration-file config))))
+                              `(("ELOGIND_CONF_FILE"
+                                 ,(elogind-configuration-file config))))))
 
 (define (pam-extension-procedure config)
   "Return an extension for PAM-ROOT-SERVICE-TYPE that ensures that all the PAM
@@ -808,6 +811,27 @@ when they log out."
   (service elogind-service-type config))
 
 \f
+;;;
+;;; Fontconfig and other desktop file-systems.
+;;;
+
+(define %fontconfig-file-system
+  (file-system
+    (device "none")
+    (mount-point "/var/cache/fontconfig")
+    (type "tmpfs")
+    (flags '(read-only))
+    (check? #f)))
+
+;; The global fontconfig cache directory can sometimes contain stale entries,
+;; possibly referencing fonts that have been GC'd, so mount it read-only.
+;; As mentioned https://debbugs.gnu.org/cgi/bugreport.cgi?bug=36924#8 and
+;; https://debbugs.gnu.org/cgi/bugreport.cgi?bug=38046#10 and elsewhere.
+(define fontconfig-file-system-service
+  (simple-service 'fontconfig-file-system
+                  file-system-service-type
+                  (list %fontconfig-file-system)))
+\f
 ;;;
 ;;; AccountsService service.
 ;;;
@@ -823,7 +847,8 @@ when they log out."
                  (list (service-extension activation-service-type
                                           (const %accountsservice-activation))
                        (service-extension dbus-root-service-type list)
-                       (service-extension polkit-service-type list)))))
+                       (service-extension polkit-service-type list)))
+                (default-value accountsservice)))
 
 (define* (accountsservice-service #:key (accountsservice accountsservice))
   "Return a service that runs AccountsService, a system service that
@@ -850,14 +875,37 @@ accountsservice web site} for more information."
    (default-value cups-pk-helper)))
 
 \f
+;;;
+;;; Scanner access via SANE.
+;;;
+
+(define %sane-accounts
+  ;; The '60-libsane.rules' udev rules refers to the "scanner" group.
+  (list (user-group (name "scanner") (system? #t))))
+
+(define sane-service-type
+  (service-type
+   (name 'sane)
+   (description
+    "This service provides access to scanners @i{via}
+@uref{http://www.sane-project.org, SANE} by installing the necessary udev
+rules.")
+   (default-value sane-backends-minimal)
+   (extensions
+    (list (service-extension udev-service-type list)
+          (service-extension account-service-type
+                             (const %sane-accounts))))))
+
+
+\f
 ;;;
 ;;; GNOME desktop service.
 ;;;
 
 (define-record-type* <gnome-desktop-configuration> gnome-desktop-configuration
   make-gnome-desktop-configuration
-  gnome-desktop-configuration
-  (gnome-package gnome-package (default gnome)))
+  gnome-desktop-configuration?
+  (gnome gnome-package (default gnome)))
 
 (define (gnome-polkit-settings config)
   "Return the list of GNOME dependencies that provide polkit actions and
@@ -879,9 +927,12 @@ rules."
           (service-extension profile-service-type
                              (compose list
                                       gnome-package))))
+   (default-value (gnome-desktop-configuration))
    (description "Run the GNOME desktop environment.")))
 
-(define* (gnome-desktop-service #:key (config (gnome-desktop-configuration)))
+(define-deprecated (gnome-desktop-service #:key (config
+                                                 (gnome-desktop-configuration)))
+  gnome-desktop-service-type
   "Return a service that adds the @code{gnome} package to the system profile,
 and extends polkit with the actions from @code{gnome-settings-daemon}."
   (service gnome-desktop-service-type config))
@@ -891,24 +942,36 @@ and extends polkit with the actions from @code{gnome-settings-daemon}."
 
 (define-record-type* <mate-desktop-configuration> mate-desktop-configuration
   make-mate-desktop-configuration
-  mate-desktop-configuration
+  mate-desktop-configuration?
   (mate-package mate-package (default mate)))
 
+(define (mate-polkit-extension config)
+  "Return the list of packages for CONFIG's MATE package that extend polkit."
+  (let ((mate (mate-package config)))
+    (map (lambda (input)
+           ((package-direct-input-selector input) mate))
+         '("mate-system-monitor"                  ;kill, renice processes
+           "mate-settings-daemon"                 ;date/time settings
+           "mate-power-manager"                   ;modify brightness
+           "mate-control-center"                  ;RandR, display properties FIXME
+           "mate-applets"))))                     ;CPU frequency scaling
+
 (define mate-desktop-service-type
   (service-type
    (name 'mate-desktop)
    (extensions
     (list (service-extension polkit-service-type
-                             (compose list
-                                      (package-direct-input-selector
-                                       "mate-settings-daemon")
-                                      mate-package))
+                             mate-polkit-extension)
           (service-extension profile-service-type
                              (compose list
                                       mate-package))))
+   (default-value (mate-desktop-configuration))
    (description "Run the MATE desktop environment.")))
 
-(define* (mate-desktop-service #:key (config (mate-desktop-configuration)))
+(define-deprecated (mate-desktop-service #:key
+                                         (config
+                                          (mate-desktop-configuration)))
+  mate-desktop-service-type
   "Return a service that adds the @code{mate} package to the system profile,
 and extends polkit with the actions from @code{mate-settings-daemon}."
   (service mate-desktop-service-type config))
@@ -920,29 +983,68 @@ and extends polkit with the actions from @code{mate-settings-daemon}."
 
 (define-record-type* <xfce-desktop-configuration> xfce-desktop-configuration
   make-xfce-desktop-configuration
-  xfce-desktop-configuration
+  xfce-desktop-configuration?
   (xfce xfce-package (default xfce)))
 
+(define (xfce-polkit-settings config)
+  "Return the list of XFCE dependencies that provide polkit actions and
+rules."
+  (let ((xfce (xfce-package config)))
+    (map (lambda (name)
+           ((package-direct-input-selector name) xfce))
+         '("thunar"
+           "xfce4-power-manager"))))
+
 (define xfce-desktop-service-type
   (service-type
    (name 'xfce-desktop)
    (extensions
     (list (service-extension polkit-service-type
-                             (compose list
-                                      (package-direct-input-selector
-                                       "thunar")
-                                      xfce-package))
+                             xfce-polkit-settings)
           (service-extension profile-service-type
-                             (compose list
-                                      xfce-package))))))
+                             (compose list xfce-package))))
+   (default-value (xfce-desktop-configuration))
+   (description "Run the Xfce desktop environment.")))
 
-(define* (xfce-desktop-service #:key (config (xfce-desktop-configuration)))
+(define-deprecated (xfce-desktop-service #:key (config
+                                                (xfce-desktop-configuration)))
+  xfce-desktop-service-type
   "Return a service that adds the @code{xfce} package to the system profile,
 and extends polkit with the ability for @code{thunar} to manipulate the file
 system as root from within a user session, after the user has authenticated
 with the administrator's password."
   (service xfce-desktop-service-type config))
 
++\f
+;;;
+;;; Lxqt desktop service.
+;;;
+
+(define-record-type* <lxqt-desktop-configuration> lxqt-desktop-configuration
+  make-lxqt-desktop-configuration
+  lxqt-desktop-configuration?
+  (lxqt lxqt-package
+        (default lxqt)))
+
+(define (lxqt-polkit-settings config)
+  "Return the list of LXQt dependencies that provide polkit actions and
+rules."
+  (let ((lxqt (lxqt-package config)))
+    (map (lambda (name)
+           ((package-direct-input-selector name) lxqt))
+         '("lxqt-admin"))))
+
+(define lxqt-desktop-service-type
+  (service-type
+   (name 'lxqt-desktop)
+   (extensions
+    (list (service-extension polkit-service-type
+                             lxqt-polkit-settings)
+          (service-extension profile-service-type
+                             (compose list lxqt-package))))
+   (default-value (lxqt-desktop-configuration))
+   (description "Run LXQt desktop environment.")))
+
 \f
 ;;;
 ;;; X11 socket directory service
@@ -979,20 +1081,9 @@ with the administrator's password."
     (list (file-append enlightenment
                        "/lib/enlightenment/utils/enlightenment_sys")
           (file-append enlightenment
-                       "/lib/enlightenment/utils/enlightenment_backlight")
-          ;; TODO: Move this binary to a screen-locker service.
-          (file-append enlightenment
-                       "/lib/enlightenment/utils/enlightenment_ckpasswd")
+                       "/lib/enlightenment/utils/enlightenment_system")
           (file-append enlightenment
-                       (string-append
-                         "/lib/enlightenment/modules/cpufreq/"
-                         (match (string-tokenize (%current-system)
-                                                 (char-set-complement (char-set #\-)))
-                                ((arch "linux") (string-append "linux-gnu-" arch))
-                                ((arch "gnu")   (string-append "gnu-" arch)))
-                         "-"
-                         (version-major+minor (package-version enlightenment))
-                         "/freqset")))))
+                       "/lib/enlightenment/utils/enlightenment_ckpasswd"))))
 
 (define enlightenment-desktop-service-type
   (service-type
@@ -1016,13 +1107,128 @@ thumbnails and makes setuid the programs which enlightenment needs to function
 as expected.")))
 
 \f
+;;;
+;;; inputattach-service-type
+;;;
+
+(define-record-type* <inputattach-configuration>
+  inputattach-configuration
+  make-inputattach-configuration
+  inputattach-configuration?
+  (device-type inputattach-configuration-device-type
+               (default "wacom"))
+  (device inputattach-configuration-device
+          (default "/dev/ttyS0"))
+  (baud-rate inputattach-configuration-baud-rate
+             (default #f))
+  (log-file inputattach-configuration-log-file
+            (default #f)))
+
+(define inputattach-shepherd-service
+  (match-lambda
+    (($ <inputattach-configuration> type device baud-rate log-file)
+     (let ((args (append (if baud-rate
+                             (list "--baud" (number->string baud-rate))
+                             '())
+                         (list (string-append "--" type)
+                               device))))
+       (list (shepherd-service
+              (provision '(inputattach))
+              (requirement '(udev))
+              (documentation "inputattach daemon")
+              (start #~(make-forkexec-constructor
+                        (cons (string-append #$inputattach
+                                             "/bin/inputattach")
+                              (quote #$args))
+                        #:log-file #$log-file))
+              (stop #~(make-kill-destructor))))))))
+
+(define inputattach-service-type
+  (service-type
+   (name 'inputattach)
+   (extensions
+    (list (service-extension shepherd-root-service-type
+                             inputattach-shepherd-service)))
+   (default-value (inputattach-configuration))
+   (description "Return a service that runs inputattach on a device and
+dispatches events from it.")))
+
+\f
+;;;
+;;; gnome-keyring-service-type
+;;;
+
+(define-record-type* <gnome-keyring-configuration> gnome-keyring-configuration
+  make-gnome-keyring-configuration
+  gnome-keyring-configuration?
+  (keyring gnome-keyring-package (default gnome-keyring))
+  (pam-services gnome-keyring-pam-services (default '(("gdm-password" . login)
+                                                      ("passwd" . passwd)))))
+
+(define (pam-gnome-keyring config)
+  (define (%pam-keyring-entry . arguments)
+    (pam-entry
+     (control "optional")
+     (module (file-append (gnome-keyring-package config)
+                          "/lib/security/pam_gnome_keyring.so"))
+     (arguments arguments)))
+
+  (list
+   (lambda (service)
+     (case (assoc-ref (gnome-keyring-pam-services config)
+                      (pam-service-name service))
+       ((login)
+        (pam-service
+         (inherit service)
+         (auth (append (pam-service-auth service)
+                       (list (%pam-keyring-entry))))
+         (session (append (pam-service-session service)
+                          (list (%pam-keyring-entry "auto_start"))))))
+       ((passwd)
+        (pam-service
+         (inherit service)
+         (password (append (pam-service-password service)
+                           (list (%pam-keyring-entry))))))
+       (else service)))))
+
+(define gnome-keyring-service-type
+  (service-type
+   (name 'gnome-keyring)
+   (extensions (list
+                (service-extension pam-root-service-type pam-gnome-keyring)))
+   (default-value (gnome-keyring-configuration))
+   (description "Return a service, that adds the @code{gnome-keyring} package
+to the system profile and extends PAM with entries using
+@code{pam_gnome_keyring.so}, unlocking a user's login keyring when they log in
+or setting its password with passwd.")))
+
+\f
+;;;
+;;; polkit-wheel-service -- Allow wheel group to perform admin actions
+;;;
+
+(define polkit-wheel
+  (file-union
+   "polkit-wheel"
+   `(("share/polkit-1/rules.d/wheel.rules"
+      ,(plain-file
+        "wheel.rules"
+        "polkit.addAdminRule(function(action, subject) {
+    return [\"unix-group:wheel\"];
+});
+")))))
+
+(define polkit-wheel-service
+  (simple-service 'polkit-wheel polkit-service-type (list polkit-wheel)))
+
+\f
 ;;;
 ;;; The default set of desktop services.
 ;;;
 
 (define %desktop-services
   ;; List of services typically useful for a "desktop" use case.
-  (cons* (service slim-service-type)
+  (cons* (service gdm-service-type)
 
          ;; Screen lockers are a pretty useful thing and these are small.
          (screen-locker-service slock)
@@ -1031,16 +1237,39 @@ as expected.")))
          ;; Add udev rules for MTP devices so that non-root users can access
          ;; them.
          (simple-service 'mtp udev-service-type (list libmtp))
-
-         ;; The D-Bus clique.
+         ;; Add udev rules for scanners.
+         (service sane-service-type)
+         ;; Add polkit rules, so that non-root users in the wheel group can
+         ;; perform administrative tasks (similar to "sudo").
+         polkit-wheel-service
+
+         ;; Allow desktop users to also mount NTFS and NFS file systems
+         ;; without root.
+         (simple-service 'mount-setuid-helpers setuid-program-service-type
+                         (list (file-append nfs-utils "/sbin/mount.nfs")
+                               (file-append ntfs-3g "/sbin/mount.ntfs-3g")))
+
+         ;; The global fontconfig cache directory can sometimes contain
+         ;; stale entries, possibly referencing fonts that have been GC'd,
+         ;; so mount it read-only.
+         fontconfig-file-system-service
+
+         ;; NetworkManager and its applet.
          (service network-manager-service-type)
          (service wpa-supplicant-service-type)    ;needed by NetworkManager
+         (simple-service 'network-manager-applet
+                         profile-service-type
+                         (list network-manager-applet))
+         (service modem-manager-service-type)
+         (service usb-modeswitch-service-type)
+
+         ;; The D-Bus clique.
          (service avahi-service-type)
          (udisks-service)
          (service upower-service-type)
          (accountsservice-service)
          (service cups-pk-helper-service-type)
-         (colord-service)
+         (service colord-service-type)
          (geoclue-service)
          (service polkit-service-type)
          (elogind-service)
@@ -1050,6 +1279,7 @@ as expected.")))
 
          x11-socket-directory-service
 
+         (service pulseaudio-service-type)
          (service alsa-service-type)
 
          %base-services))