#pragma once #include "types.hh" #include #include #include #include #include #include #include namespace nix { #define foreach(it_type, it, collection) \ for (it_type it = (collection).begin(); it != (collection).end(); ++it) #define foreach_reverse(it_type, it, collection) \ for (it_type it = (collection).rbegin(); it != (collection).rend(); ++it) /* Return an environment variable. */ string getEnv(const string & key, const string & def = ""); /* Return an absolutized path, resolving paths relative to the specified directory, or the current directory otherwise. The path is also canonicalised. */ Path absPath(Path path, Path dir = ""); /* Canonicalise a path by removing all `.' or `..' components and double or trailing slashes. Optionally resolves all symlink components such that each component of the resulting path is
aboutsummaryrefslogtreecommitdiff
;;; GNU Guix --- Functional package management for GNU
;;; Copyright © 2017 Sou Bunnbu <iyzsong@member.fsf.org>
;;;
;;; 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 (gnu services sysctl)
  #:use-module (gnu services)
  #:use-module (gnu services shepherd)
  #:use-module (gnu packages linux)
  #:use-module (guix gexp)
  #:use-module (guix records)
  #:use-module (srfi srfi-1)
  #:use-module (ice-9 match)
  #:export (sysctl-configuration
            sysctl-configuration-sysctl
            sysctl-configuration-settings
            sysctl-service-type
            %default-sysctl-settings))


;;;
;;; System Control Service.
;;;

(define %default-sysctl-settings
  ;; Default kernel parameters enabled with sysctl.
  '(("fs.protected_hardlinks" . "1")
    ("fs.protected_symlinks" . "1")))

(define-record-type* <sysctl-configuration>
  sysctl-configuration make-sysctl-configuration
  sysctl-configuration?
  (sysctl   sysctl-configuration-sysctl    ; path of the 'sysctl' command
            (default (file-append procps "/sbin/sysctl")))
  (settings sysctl-configuration-settings  ; alist of string pairs
            (default %default-sysctl-settings)))

(define (sysctl-configuration-settings->sysctl.conf settings)
  "Return a file for @command{sysctl} to set kernel parameters as specified by
@var{settings}."
  (apply mixed-text-file "sysctl.conf"
         (append-map (match-lambda
                       ((key . value)
                        (list key "=" value "\n")))
                     settings)))

(define sysctl-shepherd-service
  (match-lambda
    (($ <sysctl-configuration> sysctl settings)
     (let ((sysctl.conf
            (sysctl-configuration-settings->sysctl.conf settings)))
       (shepherd-service
        (documentation "Configure kernel parameters at boot.")
        (provision '(sysctl))
        (start #~(lambda _
                   (zero? (system* #$sysctl "--load" #$sysctl.conf))))
        (one-shot? #t))))))

(define sysctl-service-type
  (service-type
   (name 'sysctl)
   (extensions
    (list (service-extension shepherd-root-service-type
                             (compose list sysctl-shepherd-service))))
   (compose concatenate)
   (extend (lambda (config settings)
             (sysctl-configuration
              (inherit config)
              (settings (append (sysctl-configuration-settings config)
                                settings)))))
   (default-value (sysctl-configuration))
   (description "Set Linux kernel parameters under @file{/proc/sys} at system
startup time.")))
ic: AutoCloseFD readSide, writeSide; void create(); }; class AutoCloseDir { DIR * dir; public: AutoCloseDir(); AutoCloseDir(DIR * dir); ~AutoCloseDir(); void operator =(DIR * dir); operator DIR *(); void close(); }; class Pid { pid_t pid; bool separatePG; int killSignal; public: Pid(); Pid(pid_t pid); ~Pid(); void operator =(pid_t pid); operator pid_t(); void kill(bool quiet = false); int wait(bool block); void setSeparatePG(bool separatePG); void setKillSignal(int signal); }; /* An "agent" is a helper program that runs in the background and that we talk to over pipes, such as the "guix offload" program. */ struct Agent { /* Pipes for talking to the agent. */ Pipe toAgent; /* Pipe for the agent's standard output/error. */ Pipe fromAgent; /* Pipe for build standard output/error--e.g., for build processes started by "guix offload". */ Pipe builderOut; /* The process ID of the agent. */ Pid pid; /* The command and arguments passed to the agent. */ Agent(const string &command, const Strings &args); ~Agent(); }; /* Kill all processes running under the specified uid by sending them a SIGKILL. */ void killUser(uid_t uid); /* Fork a process that runs the given function, and return the child pid to the caller. */ pid_t startProcess(std::function fun, bool dieWithParent = true, const string & errorPrefix = "error: ", bool runExitHandlers = false); /* Run a program and return its stdout in a string (i.e., like the shell backtick operator). */ string runProgram(Path program, bool searchPath = false, const Strings & args = Strings()); MakeError(ExecError, Error) /* Convert a list of strings to a null-terminated vector of char *'s. The result must not be accessed beyond the lifetime of the list of strings. */ std::vector stringsToCharPtrs(const Strings & ss); /* Close all file descriptors except stdin, stdout, stderr, and those listed in the given set. Good practice in child processes. */ void closeMostFDs(const set & exceptions); /* Set the close-on-exec flag for the given file descriptor. */ void closeOnExec(int fd); /* Common initialisation performed in child processes. */ void commonChildInit(Pipe & logPipe); /* User interruption. */ extern volatile sig_atomic_t _isInterrupted; void _interrupted(); void inline checkInterrupt() { if (_isInterrupted) _interrupted(); } MakeError(Interrupted, BaseError) /* String tokenizer. */ template C tokenizeString(const string & s, const string & separators = " \t\n\r"); /* Concatenate the given strings with a separator between the elements. */ string concatStringsSep(const string & sep, const Strings & ss); string concatStringsSep(const string & sep, const StringSet & ss); /* Remove trailing whitespace from a string. */ string chomp(const string & s); /* Convert the exit status of a child as returned by wait() into an error string. */ string statusToString(int status); bool statusOk(int status); /* Parse a string into an integer. */ template bool string2Int(const string & s, N & n) { std::istringstream str(s); str >> n; return str && str.get() == EOF; } /* Return true iff `s' ends in `suffix'. */ bool hasSuffix(const string & s, const string & suffix); /* Read string `s' from stream `str'. */ void expect(std::istream & str, const string & s); MakeError(FormatError, Error) /* Read a C-style string from stream `str'. */ string parseString(std::istream & str); /* Utility function used to parse legacy ATerms. */ bool endOfList(std::istream & str); /* Exception handling in destructors: print an error message, then ignore the exception. */ void ignoreException(); }