aboutsummaryrefslogtreecommitdiff
;;; GNU Guix --- Functional package management for GNU
;;; Copyright © 2018 Ludovic Courtès <ludo@gnu.org>
;;; Copyright © 2019 Mathieu Othacehe <m.othacehe@gmail.com>
;;;
;;; This file is part of GNU Guix.
;;;
;;; GNU Guix is free software; you can redistribute it and/or modify it
;;; under the terms of the GNU General Public License as published by
;;; the Free Software Foundation; either version 3 of the License, or (at
;;; your option) any later version.
;;;
;;; GNU Guix is distributed in the hope that it will be useful, but
;;; WITHOUT ANY WARRANTY; without even the implied warranty of
;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
;;; GNU General Public License for more details.
;;;
;;; You should have received a copy of the GNU General Public License
;;; along with GNU Guix.  If not, see <http://www.gnu.org/licenses/>.

(define-module (test-processes)
  #:use-module (guix scripts processes)
  #:use-module (guix store)
  #:use-module (guix derivations)
  #:use-module (guix packages)
  #:use-module (guix gexp)
  #:use-module ((guix utils) #:select (call-with-temporary-directory))
  #:use-module (gnu packages bootstrap)
  #:use-module (guix tests)
  #:use-module (srfi srfi-1)
  #:use-module (srfi srfi-64)
  #:use-module (rnrs bytevectors)
  #:use-module (rnrs io ports)
  #:use-module (ice-9 match)
  #:use-module (ice-9 threads))

;; When using --system argument, binfmt-misc mechanism may be used. In that
;; case, (guix script processes) won't work because:
;;
;; * ARGV0 is qemu-user and not guix-daemon.
;; * Guix-daemon won't be able to stuff client PID in ARGV1 of forked
;;   processes.
;;
;; See: https://lists.gnu.org/archive/html/bug-guix/2019-12/msg00017.html.
;;
;; If we detect that we are running with binfmt emulation, all the following
;; tests must be skipped.

(define (binfmt-misc?)
  (let ((pid (getpid))
        (cmdline (call-with-input-file "/proc/self/cmdline" get-string-all)))
    (match (primitive-fork)
      (0 (dynamic-wind
           (const #t)
           (lambda ()
             (exit
              (not (equal?
                    (call-with-input-file (format #f "/proc/~a/cmdline" pid)
                      get-string-all)
                    cmdline))))
           (const #t)))
      (x (zero? (cdr (waitpid x)))))))

(define-syntax-rule (test-assert* description exp)
  (begin
    (when (binfmt-misc?)
      (test-skip 1))
    (test-assert description exp)))

(test-begin "processes")

(test-assert* "not a client"
  (not (find (lambda (session)
               (= (getpid)
                  (process-id (daemon-session-client session))))
             (daemon-sessions))))

(test-assert* "client"
  (with-store store
    (let* ((session (find (lambda (session)
                            (= (getpid)
                               (process-id (daemon-session-client session))))
                          (daemon-sessions)))
           (daemon  (daemon-session-process session)))
      (and (kill (process-id daemon) 0)
           (string-suffix? "guix-daemon" (first (process-command daemon)))))))

(test-assert* "client + lock"
  (with-store store
    (call-with-temporary-directory
     (lambda (directory)
       (let* ((token1  (string-append directory "/token1"))
              (token2  (string-append directory "/token2"))
              (exp     #~(begin #$(random-text)
                                (mkdir #$token1)
                                (let loop ()
                                  (unless (file-exists? #$token2)
                                    (sleep 1)
                                    (loop)))
                                (mkdir #$output)))
              (guile   (package-derivation store %bootstrap-guile))
              (drv     (run-with-store store
                         (gexp->derivation "foo" exp
                                           #:guile-for-build guile)))
              (thread  (call-with-new-thread
                        (lambda ()
                          (build-derivations store (list drv)))))
              (_       (let loop ()
                         (unless (file-exists? token1)
                           (usleep 200)
                           (loop))))
              (session (find (lambda (session)
                               (= (getpid)
                                  (process-id (daemon-session-client session))))
                             (daemon-sessions)))
              (locks   (daemon-session-locks-held (pk 'session session))))
         (call-with-output-file token2 (const #t))
         (equal? (list (string-append (derivation->output-path drv) ".lock"))
                 locks))))))

(test-end "processes")
ae151e4'>services: 'fold-services' memoizes service values....Previously 'fold-services' could end up traversing the same services in the graph several times, which is what this change addresses. The hit rate on the 'add-data-to-store' cache goves from 9% to 8% on "guix system build desktop.tmpl -nd", and the number of lookups in that cache goes from 4458 to 4383. * gnu/services.scm (fold-services): Turn 'loop' into a monadic procedure in %STATE-MONAD and use it to memoize values of visited services. Ludovic Courtès 2019-08-14remote: Remove '--system' argument....* gnu/services.scm (activation-script): Return a <program-file> rather than a <scheme-file>. * gnu/deploy.scm (guix-deploy): Remove handling for '--system'. (show-help): Remove documentation for '--system'. (%default-options): Remove default setting for 'system'. Jakob L. Kreuze 2019-05-10services: 'gc-root-service-type' now has a default value....* gnu/services.scm (gc-root-service-type)[default-value]: New field. Ludovic Courtès 2018-09-07services: 'instantiate-missing-services' reaches fixed point....Fixes a bug whereby services indirectly depended on would not be automatically instantiated. * gnu/services.scm (instantiate-missing-services): Loop back when the length of ADJUSTED is greater than that of INSTANCES. * tests/services.scm ("instantiate-missing-services, indirect"): New test. Ludovic Courtès 2018-06-20services: boot: Take gexps instead of monadic gexps....* gnu/services.scm (compute-boot-script): Rename 'mexps' to 'gexps' and remove 'mlet' form. (boot-service-type): Update comment. (cleanup-gexp): Remove 'with-monad' and 'return'. (activation-script): Rewrite in non-monadic style: use 'scheme-file' instead of 'gexp->file'. (gexps->activation-gexp): Remove 'mlet', return a gexp. * gnu/services/shepherd.scm (shepherd-boot-gexp): Remove 'with-monad' and 'return'. * gnu/system.scm (operating-system-boot-script): Remove outdated comment. * gnu/tests/base.scm (%cleanup-os): For 'dirty-service', remove 'with-monad' and 'return'. Ludovic Courtès 2018-06-20services: Add description to core services....* gnu/services.scm (system-service-type, boot-service-type) (cleanup-service-type, activation-service-type) (special-files-service-type, etc-service-type) (setuid-program-service-type, profile-service-type) (firmware-service-type, gc-root-service-type): Add 'description' field. Ludovic Courtès 2018-06-20services: cleanup: Expect file names to be UTF-8-encoded....Fixes <https://bugs.gnu.org/26353>. Reported by Danny Milosavljevic <dannym@scratchpost.org>. * gnu/services.scm (cleanup-gexp): Add 'setenv' and 'setlocale' calls before 'delete-file-recursively'. * gnu/tests/base.scm (%cleanup-os, %test-cleanup): New variables. (run-cleanup-test): New procedure. Ludovic Courtès 2018-06-20services: boot: Reverse the order of boot expressions....* gnu/services.scm (compute-boot-script): Reverse MEXPS. * gnu/system.scm (essential-services): Reverse order of %SHEPHERD-ROOT-SERVICE, %ACTIVATION-SERVICE, and CLEANUP-SERVICE-TYPE. Ludovic Courtès 2018-04-08discovery: Remove dependency on (guix ui)....This reduces the closure of (guix discovery) from 28 to 8 modules. * guix/discovery.scm (scheme-files): Use 'format' instead of 'warning'. (scheme-modules): Add #:warn parameter. Use it instead of 'warn-about-load-error'. (fold-modules): Add #:warn and pass it to 'scheme-modules'. (all-modules): Likewise. * gnu/bootloader.scm (bootloader-modules): Pass #:warn to 'all-modules'. * gnu/packages.scm (fold-packages): Likewise. * gnu/services.scm (all-service-modules): Likewise. * guix/upstream.scm (importer-modules): Likewise. Ludovic Courtès 2018-03-29gnu: Refactor boot-service-type and activation-service-type....* gnu/services.scm (boot-service-type) <compose>: Use the "identity" procedure instead of the "append" procedure because it more accurately reflects the intent, which is to simply return the single list of extensions to which fold-services applies the "compose" procedure. (activation-service-type) <compose>: Likewise. Chris Marusich 2018-01-21services: Missing services are automatically instantiated....This simplifies OS configuration: users no longer need to be aware of what a given service depends on. See the discussion at <https://lists.gnu.org/archive/html/guix-devel/2018-01/msg00114.html>. * gnu/services.scm (missing-target-error): New procedure. (service-back-edges): Use it. (instantiate-missing-services): New procedure. * gnu/system.scm (operating-system-services): Call 'instantiate-missing-services'. * tests/services.scm ("instantiate-missing-services") ("instantiate-missing-services, no default value"): New tests. * gnu/services/version-control.scm (cgit-service-type)[extensions]: Add FCGIWRAP-SERVICE-TYPE. * gnu/tests/version-control.scm (%cgit-os): Remove NGINX-SERVICE-TYPE and FCGIWRAP-SERVICE-TYPE instances. * doc/guix.texi (Log Rotation): Remove 'mcron-service-type' in example. (Miscellaneous Services): Remove 'nginx-service-type' and 'fcgiwrap-service-type' in Cgit example. Ludovic Courtès 2017-12-17services: cleanup: Remove "/run/udev/watch.old" directory....* gnu/services.scm (cleanup-gexp): Remove "/run/udev/watch.old" directory. Danny Milosavljevic 2017-11-08services: Add 'lookup-service-types'....* gnu/services.scm (lookup-service-types): New procedure. * tests/services.scm ("lookup-service-types"): New test. Ludovic Courtès 2017-11-08services: 'fold-service-types' includes (gnu services)....* gnu/services.scm (all-service-modules): New procedure. (fold-service-types): Use it for the default MODULES value. Ludovic Courtès 2017-11-08services: 'fold-service-types' honors its seed....* gnu/services.scm (fold-service-types): Use SEED instead of '(). Ludovic Courtès 2017-10-22gexp: Add 'directory-union'....* gnu/services.scm (directory-union): Move to... * guix/gexp.scm (directory-union): ... here. New procedure. * doc/guix.texi (G-Expressions): Document it. Ludovic Courtès 2017-10-22gexp: Add 'file-union'....* gnu/services.scm (file-union): Move to... * guix/gexp.scm (file-union): ... here. New procedure. * doc/guix.texi (G-Expressions): Document it. Ludovic Courtès 2017-10-12services: cleanup: Remove Shadow lock files from /etc....Partly fixes <https://bugs.gnu.org/28772>. Reported by Oleg Pykhalov <go.wigust@gmail.com>. * gnu/services.scm (cleanup-gexp): Remove /etc/{passwd,group}.lock and /etc/.pwd.lock. Ludovic Courtès 2017-09-22services: network-manager: Add support for VPN plug-ins....* gnu/services.scm (directory-union): Export. * gnu/services/networking.scm (<network-manager-configuration>)[vpn-plugins]: New field. (vpn-plugin-directory, network-manager-environment): New procedure. (network-manager-shepherd-service): Pass #:environment-variables to 'make-forkexec-constructor'. (network-manager-service-type): Add SESSION-ENVIRONMENT-SERVICE-TYPE extension. * doc/guix.texi (Networking Services): Document it. Ludovic Courtès 2017-09-16services: Add 'fold-service-types'....* gnu/services.scm (%distro-root-directory, %service-type-path): New variables. (fold-service-types): New procedure. Ludovic Courtès 2017-09-16services: Add a description and location for each service type....* gnu/services.scm (<service-type>)[description, location]: New field. * doc/guix.texi (Service Types and Services): Document 'description'. Ludovic Courtès