mirror of
https://git.in.rschanz.org/ryan77627/guix.git
synced 2024-12-24 05:18:07 -05:00
mapped-devices: Ensure 'cryptsetup open' gets a tty.
Fixes <https://issues.guix.gnu.org/54770>.
Regression introduced in 400c9ed3d7
.
Previously, for an encrypted /home (say), "cryptsetup open" would be
invoked by shepherd, with /dev/null as its standard input. It would
thus run in non-interactive mode and, instead of asking for a
passphrase, fail with:
Nothing to read on input.
This change ensures it runs in interactive mode.
* gnu/build/file-systems.scm (system*/console, system*/tty): New
procedures.
* gnu/system/mapped-devices.scm (open-luks-device): Use 'system*/tty'
instead of 'system*'.
This commit is contained in:
parent
df473496ed
commit
931f13840b
2 changed files with 56 additions and 23 deletions
|
@ -1,5 +1,5 @@
|
||||||
;;; GNU Guix --- Functional package management for GNU
|
;;; GNU Guix --- Functional package management for GNU
|
||||||
;;; Copyright © 2014, 2015, 2016, 2017, 2018, 2020, 2021 Ludovic Courtès <ludo@gnu.org>
|
;;; Copyright © 2014-2018, 2020-2022 Ludovic Courtès <ludo@gnu.org>
|
||||||
;;; Copyright © 2016, 2017 David Craven <david@craven.ch>
|
;;; Copyright © 2016, 2017 David Craven <david@craven.ch>
|
||||||
;;; Copyright © 2017 Mathieu Othacehe <m.othacehe@gmail.com>
|
;;; Copyright © 2017 Mathieu Othacehe <m.othacehe@gmail.com>
|
||||||
;;; Copyright © 2019 Guillaume Le Vaillant <glv@posteo.net>
|
;;; Copyright © 2019 Guillaume Le Vaillant <glv@posteo.net>
|
||||||
|
@ -54,6 +54,7 @@ (define-module (gnu build file-systems)
|
||||||
|
|
||||||
bind-mount
|
bind-mount
|
||||||
|
|
||||||
|
system*/tty
|
||||||
mount-flags->bit-mask
|
mount-flags->bit-mask
|
||||||
check-file-system
|
check-file-system
|
||||||
mount-file-system
|
mount-file-system
|
||||||
|
@ -67,6 +68,33 @@ (define-module (gnu build file-systems)
|
||||||
;;;
|
;;;
|
||||||
;;; Code:
|
;;; Code:
|
||||||
|
|
||||||
|
(define (system*/console program . args)
|
||||||
|
"Run PROGRAM with ARGS in a tty on top of /dev/console. The return value is
|
||||||
|
as for 'system*'."
|
||||||
|
(match (primitive-fork)
|
||||||
|
(0
|
||||||
|
(dynamic-wind
|
||||||
|
(const #t)
|
||||||
|
(lambda ()
|
||||||
|
(login-tty (open-fdes "/dev/console" O_RDWR))
|
||||||
|
(apply execlp program program args))
|
||||||
|
(lambda ()
|
||||||
|
(primitive-_exit 127))))
|
||||||
|
(pid
|
||||||
|
(cdr (waitpid pid)))))
|
||||||
|
|
||||||
|
(define (system*/tty program . args)
|
||||||
|
"Run PROGRAM with ARGS, creating a tty if its standard input isn't one.
|
||||||
|
The return value is as for 'system*'.
|
||||||
|
|
||||||
|
This is necessary for commands such as 'cryptsetup open' or 'fsck' that may
|
||||||
|
need to interact with the user but might be invoked from shepherd, where
|
||||||
|
standard input is /dev/null."
|
||||||
|
(apply (if (isatty? (current-input-port))
|
||||||
|
system*
|
||||||
|
system*/console)
|
||||||
|
program args))
|
||||||
|
|
||||||
(define (bind-mount source target)
|
(define (bind-mount source target)
|
||||||
"Bind-mount SOURCE at TARGET."
|
"Bind-mount SOURCE at TARGET."
|
||||||
(mount source target "" MS_BIND))
|
(mount source target "" MS_BIND))
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
;;; GNU Guix --- Functional package management for GNU
|
;;; GNU Guix --- Functional package management for GNU
|
||||||
;;; Copyright © 2014, 2015, 2016, 2017, 2018, 2019, 2020, 2021 Ludovic Courtès <ludo@gnu.org>
|
;;; Copyright © 2014-2022 Ludovic Courtès <ludo@gnu.org>
|
||||||
;;; Copyright © 2016 Andreas Enge <andreas@enge.fr>
|
;;; Copyright © 2016 Andreas Enge <andreas@enge.fr>
|
||||||
;;; Copyright © 2017, 2018 Mark H Weaver <mhw@netris.org>
|
;;; Copyright © 2017, 2018 Mark H Weaver <mhw@netris.org>
|
||||||
;;;
|
;;;
|
||||||
|
@ -202,7 +202,8 @@ (define (open-luks-device source targets)
|
||||||
;; XXX: 'use-modules' should be at the top level.
|
;; XXX: 'use-modules' should be at the top level.
|
||||||
(use-modules (rnrs bytevectors) ;bytevector?
|
(use-modules (rnrs bytevectors) ;bytevector?
|
||||||
((gnu build file-systems)
|
((gnu build file-systems)
|
||||||
#:select (find-partition-by-luks-uuid))
|
#:select (find-partition-by-luks-uuid
|
||||||
|
system*/tty))
|
||||||
((guix build utils) #:select (mkdir-p)))
|
((guix build utils) #:select (mkdir-p)))
|
||||||
|
|
||||||
;; Create '/run/cryptsetup/' if it does not exist, as device locking
|
;; Create '/run/cryptsetup/' if it does not exist, as device locking
|
||||||
|
@ -211,28 +212,32 @@ (define (open-luks-device source targets)
|
||||||
|
|
||||||
;; Use 'cryptsetup-static', not 'cryptsetup', to avoid pulling the
|
;; Use 'cryptsetup-static', not 'cryptsetup', to avoid pulling the
|
||||||
;; whole world inside the initrd (for when we're in an initrd).
|
;; whole world inside the initrd (for when we're in an initrd).
|
||||||
(zero? (system* #$(file-append cryptsetup-static "/sbin/cryptsetup")
|
;; 'cryptsetup open' requires standard input to be a tty to allow
|
||||||
"open" "--type" "luks"
|
;; for interaction but shepherd sets standard input to /dev/null;
|
||||||
|
;; thus, explicitly request a tty.
|
||||||
|
(zero? (system*/tty
|
||||||
|
#$(file-append cryptsetup-static "/sbin/cryptsetup")
|
||||||
|
"open" "--type" "luks"
|
||||||
|
|
||||||
;; Note: We cannot use the "UUID=source" syntax here
|
;; Note: We cannot use the "UUID=source" syntax here
|
||||||
;; because 'cryptsetup' implements it by searching the
|
;; because 'cryptsetup' implements it by searching the
|
||||||
;; udev-populated /dev/disk/by-id directory but udev may
|
;; udev-populated /dev/disk/by-id directory but udev may
|
||||||
;; be unavailable at the time we run this.
|
;; be unavailable at the time we run this.
|
||||||
(if (bytevector? source)
|
(if (bytevector? source)
|
||||||
(or (let loop ((tries-left 10))
|
(or (let loop ((tries-left 10))
|
||||||
(and (positive? tries-left)
|
(and (positive? tries-left)
|
||||||
(or (find-partition-by-luks-uuid source)
|
(or (find-partition-by-luks-uuid source)
|
||||||
;; If the underlying partition is
|
;; If the underlying partition is
|
||||||
;; not found, try again after
|
;; not found, try again after
|
||||||
;; waiting a second, up to ten
|
;; waiting a second, up to ten
|
||||||
;; times. FIXME: This should be
|
;; times. FIXME: This should be
|
||||||
;; dealt with in a more robust way.
|
;; dealt with in a more robust way.
|
||||||
(begin (sleep 1)
|
(begin (sleep 1)
|
||||||
(loop (- tries-left 1))))))
|
(loop (- tries-left 1))))))
|
||||||
(error "LUKS partition not found" source))
|
(error "LUKS partition not found" source))
|
||||||
source)
|
source)
|
||||||
|
|
||||||
#$target)))))))
|
#$target)))))))
|
||||||
|
|
||||||
(define (close-luks-device source targets)
|
(define (close-luks-device source targets)
|
||||||
"Return a gexp that closes TARGET, a LUKS device."
|
"Return a gexp that closes TARGET, a LUKS device."
|
||||||
|
|
Loading…
Reference in a new issue