Hi Ludo,
Ludovic Courtès <ludo@gnu.org> writes:
Toggle quote (16 lines)
> How about this:
>
> diff --git a/guix/scripts/environment.scm b/guix/scripts/environment.scm
> index ec071402f4..ac2c79ab65 100644
> --- a/guix/scripts/environment.scm
> +++ b/guix/scripts/environment.scm
> @@ -420,7 +420,7 @@ (define script
> ;; Script to obtain the list of environment variable values. On a POSIX
> ;; shell we can rely on 'set', but on fish we have to use 'env' (fish's
> ;; 'set' truncates values and prints them in a different format.)
> - "env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
> + "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
>
> (define lines
> (match (primitive-fork)
Unfortunately, this doesn't quite work. I tried this patch:
Toggle snippet (36 lines)
diff --git a/guix/scripts/environment.scm b/guix/scripts/environment.scm
index 510cee727f..4399a5dd04 100644
--- a/guix/scripts/environment.scm
+++ b/guix/scripts/environment.scm
@@ -420,7 +420,7 @@ (define script
;; Script to obtain the list of environment variable values. On a POSIX
;; shell we can rely on 'set', but on fish we have to use 'env' (fish's
;; 'set' truncates values and prints them in a different format.)
- "env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
+ "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
(define lines
(match (primitive-fork)
@@ -440,7 +440,7 @@ (define lines
(result (begin
(display script port)
(let loop ((lines '()))
- (match (read-line port)
+ (match (pk 'read-line (read-line port))
((? eof-object?) (reverse lines))
("GUIX-CHECK-DONE\r"
(display "done\n" port)
@@ -458,10 +458,10 @@ (define lines
;; but it also truncates values anyway, so don't try to support it.
(let ((index (string-index line #\=)))
(if index
- (vhash-cons (string-take line index)
+ (vhash-cons (pk 'variable line (string-take line index))
(string-drop line (+ 1 index))
table)
- table)))
+ (pk 'dropped line table))))
vlist-null
lines))
Toggle snippet (118 lines)
[0] [env] marusich@suzaku:~/guix-master
$ ./pre-inst-env guix shell --check --pure --development guix
guix shell: checking the environment variables visible from shell '/bin/bash'...
;;; (read-line "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\r")
;;; (read-line "\x1b[?2004h[0] [env] marusich@suzaku:~/guix-master\r\r")
;;; (read-line "$ PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\r")
;;; (read-line "\x1b[?2004l\rPKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig\r")
;;; (read-line "PWD=/home/marusich/guix-master\r")
;;; (read-line "LOGNAME=marusich\r")
;;; (read-line "GUILE_LOAD_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0\r")
;;; (read-line "HOME=/home/marusich\r")
;;; (read-line "LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:do=01;35:bd=40;33;01:cd=40;33;01:or=40;31;01:mi=00:su=37;41:sg=30;43:ca=30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arc=01;31:*.arj=01;31:*.taz=01;31:*.lha=01;31:*.lz4=01;31:*.lzh=01;31:*.lzma=01;31:*.tlz=01;31:*.txz=01;31:*.tzo=01;31:*.t7z=01;31:*.zip=01;31:*.z=01;31:*.dz=01;31:*.gz=01;31:*.lrz=01;31:*.lz=01;31:*.lzo=01;31:*.xz=01;31:*.zst=01;31:*.tzst=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01;31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.alz=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.cab=01;31:*.wim=01;31:*.swm=01;31:*.dwm=01;31:*.esd=01;31:*.jpg=01;35:*.jpeg=01;35:*.mjpg=01;35:*.mjpeg=01;35:*.gif=01;35:*.bmp=01;35:*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.png=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35:*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.webp=01;35:*.ogm=01;35:*.mp4=01;35:*.m4v=01;35:*.mp4v=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35:*.gl=01;35:*.dl=01;35:*.xcf=01;35:*.xwd=01;35:*.yuv=01;35:*.cgm=01;35:*.emf=01;35:*.ogv=01;35:*.ogx=01;35:*.aac=00;36:*.au=00;36:*.flac=00;36:*.m4a=00;36:*.mid=00;36:*.midi=00;36:*.mka=00;36:*.mp3=00;36:*.mpc=00;36:*.ogg=00;36:*.ra=00;36:*.wav=00;36:*.oga=00;36:*.opus=00;36:*.spx=00;36:*.xspf=00;36:\r")
;;; (read-line "GUILE_LOAD_COMPILED_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/guile/3.0/site-ccache:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0\r")
;;; (read-line "INFOPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/info\r")
;;; (read-line "TERM=screen.xterm-256color\r")
;;; (read-line "CPLUS_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include/c++:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include\r")
;;; (read-line "ACLOCAL_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/aclocal\r")
;;; (read-line "USER=marusich\r")
;;; (read-line "LIBRARY_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib\r")
;;; (read-line "SHLVL=1\r")
;;; (read-line "GUIX_LOCPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/locale\r")
;;; (read-line "GUIX_ENVIRONMENT=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile\r")
;;; (read-line "PS1=\r")
;;; (read-line "PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/sbin\r")
;;; (read-line "C_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include\r")
;;; (read-line "_=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin/env\r")
;;; (read-line "GUIX-CHECK-DONE\r")
;;; (variable "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit" "PS1")
;;; (dropped "\x1b[?2004h[0] [env] marusich@suzaku:~/guix-master\r" #<vhash 2b482ca0 1 pairs>)
;;; (variable "$ PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit" "$ PS1")
;;; (variable "\x1b[?2004l\rPKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig" "\x1b[?2004l\rPKG_CONFIG_PATH")
;;; (variable "PWD=/home/marusich/guix-master" "PWD")
;;; (variable "LOGNAME=marusich" "LOGNAME")
;;; (variable "GUILE_LOAD_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0" "GUILE_LOAD_PATH")
;;; (variable "HOME=/home/marusich" "HOME")
;;; (variable "LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:do=01;35:bd=40;33;01:cd=40;33;01:or=40;31;01:mi=00:su=37;41:sg=30;43:ca=30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arc=01;31:*.arj=01;31:*.taz=01;31:*.lha=01;31:*.lz4=01;31:*.lzh=01;31:*.lzma=01;31:*.tlz=01;31:*.txz=01;31:*.tzo=01;31:*.t7z=01;31:*.zip=01;31:*.z=01;31:*.dz=01;31:*.gz=01;31:*.lrz=01;31:*.lz=01;31:*.lzo=01;31:*.xz=01;31:*.zst=01;31:*.tzst=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01;31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.alz=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.cab=01;31:*.wim=01;31:*.swm=01;31:*.dwm=01;31:*.esd=01;31:*.jpg=01;35:*.jpeg=01;35:*.mjpg=01;35:*.mjpeg=01;35:*.gif=01;35:*.bmp=01;35:*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.png=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35:*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.webp=01;35:*.ogm=01;35:*.mp4=01;35:*.m4v=01;35:*.mp4v=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35:*.gl=01;35:*.dl=01;35:*.xcf=01;35:*.xwd=01;35:*.yuv=01;35:*.cgm=01;35:*.emf=01;35:*.ogv=01;35:*.ogx=01;35:*.aac=00;36:*.au=00;36:*.flac=00;36:*.m4a=00;36:*.mid=00;36:*.midi=00;36:*.mka=00;36:*.mp3=00;36:*.mpc=00;36:*.ogg=00;36:*.ra=00;36:*.wav=00;36:*.oga=00;36:*.opus=00;36:*.spx=00;36:*.xspf=00;36:" "LS_COLORS")
;;; (variable "GUILE_LOAD_COMPILED_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/guile/3.0/site-ccache:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0" "GUILE_LOAD_COMPILED_PATH")
;;; (variable "INFOPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/info" "INFOPATH")
;;; (variable "TERM=screen.xterm-256color" "TERM")
;;; (variable "CPLUS_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include/c++:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include" "CPLUS_INCLUDE_PATH")
;;; (variable "ACLOCAL_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/aclocal" "ACLOCAL_PATH")
;;; (variable "USER=marusich" "USER")
;;; (variable "LIBRARY_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib" "LIBRARY_PATH")
;;; (variable "SHLVL=1" "SHLVL")
;;; (variable "GUIX_LOCPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/locale" "GUIX_LOCPATH")
;;; (variable "GUIX_ENVIRONMENT=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile" "GUIX_ENVIRONMENT")
;;; (variable "PS1=" "PS1")
;;; (variable "PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/sbin" "PATH")
;;; (variable "C_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include" "C_INCLUDE_PATH")
;;; (variable "_=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin/env" "_")
guix shell: warning: variable 'PKG_CONFIG_PATH' is missing from shell environment
hint: One or more environment variables have a different value in the shell than
the one we set. This means that you may find yourself running code in an
environment different from the one you asked Guix to prepare.
This usually indicates that your shell startup files are unexpectedly
modifying those environment variables. For example, if you are using Bash,
make sure that environment variables are set or modified in
`~/.bash_profile' and _not_ in `~/.bashrc'. For more information on Bash
startup files, run:
info "(bash) Bash Startup Files"
Alternatively, you can avoid the problem by passing the `--container' or
`-C' option. That will give you a fully isolated environment running in a
"container", immune to the issue described above.
[1] [env] marusich@suzaku:~/guix-master
$
Most of the interesting stuff happened in the first few lines:
Toggle snippet (9 lines)
;;; (read-line "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\r")
;;; (read-line "\x1b[?2004h[0] [env] marusich@suzaku:~/guix-master\r\r")
;;; (read-line "$ PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\r")
;;; (read-line "\x1b[?2004l\rPKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig\r")
As you can see, nothing good is happening when the code parses this
later on:
Toggle snippet (9 lines)
;;; (variable "PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit" "PS1")
;;; (dropped "\x1b[?2004h[0] [env] marusich@suzaku:~/guix-master\r" #<vhash 2b482ca0 1 pairs>)
;;; (variable "$ PS1=; env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit" "$ PS1")
;;; (variable "\x1b[?2004l\rPKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig" "\x1b[?2004l\rPKG_CONFIG_PATH")
Although I'm sure you see it, for clarity I will explain why the above
is bad: The first variable was actually just the entire script being
echoed back; it is not actually an environment variable. The second
variable "$ PS1" is also not really an environment variable. And the
variable "\x1b[?2004l\rPKG_CONFIG_PATH", again, appears to contain
garbage at the start, probably from my PS1 value.
Basically, I think we can work around these issues if we just read and
discard all that junk at the start. I wasn't able to figure out a
graceful way to force that to happen, but I did find that simply
printing a few lines at the start of the script was good enough to work
around the issue on my computer. Here's my proposed patch, with
debugging statements included:
Toggle snippet (41 lines)
diff --git a/guix/scripts/environment.scm b/guix/scripts/environment.scm
index 510cee727f..35669b39cd 100644
--- a/guix/scripts/environment.scm
+++ b/guix/scripts/environment.scm
@@ -420,7 +420,8 @@ (define script
;; Script to obtain the list of environment variable values. On a POSIX
;; shell we can rely on 'set', but on fish we have to use 'env' (fish's
;; 'set' truncates values and prints them in a different format.)
- "env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
+ "PS1=; for i in 1 2 3; do echo GUIX_FLUSH_$i; done; \
+env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
(define lines
(match (primitive-fork)
@@ -439,8 +440,10 @@ (define lines
(let* ((port (fdopen controller "r+l"))
(result (begin
(display script port)
+ (while (not (string=? "GUIX_FLUSH_3\r"
+ (read-line port))))
(let loop ((lines '()))
- (match (read-line port)
+ (match (pk 'read-line (read-line port))
((? eof-object?) (reverse lines))
("GUIX-CHECK-DONE\r"
(display "done\n" port)
@@ -458,10 +461,10 @@ (define lines
;; but it also truncates values anyway, so don't try to support it.
(let ((index (string-index line #\=)))
(if index
- (vhash-cons (string-take line index)
+ (vhash-cons (pk 'variable line (string-take line index))
(string-drop line (+ 1 index))
table)
- table)))
+ (pk 'dropped line table))))
vlist-null
lines))
Toggle snippet (58 lines)
[0] [env] marusich@suzaku:~/guix-master
$ ./pre-inst-env guix shell --check --pure --development guix
guix shell: checking the environment variables visible from shell '/bin/bash'...
;;; (read-line "PKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig\r")
;;; (read-line "PWD=/home/marusich/guix-master\r")
;;; (read-line "LOGNAME=marusich\r")
;;; (read-line "GUILE_LOAD_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0\r")
;;; (read-line "HOME=/home/marusich\r")
;;; (read-line "LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:do=01;35:bd=40;33;01:cd=40;33;01:or=40;31;01:mi=00:su=37;41:sg=30;43:ca=30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arc=01;31:*.arj=01;31:*.taz=01;31:*.lha=01;31:*.lz4=01;31:*.lzh=01;31:*.lzma=01;31:*.tlz=01;31:*.txz=01;31:*.tzo=01;31:*.t7z=01;31:*.zip=01;31:*.z=01;31:*.dz=01;31:*.gz=01;31:*.lrz=01;31:*.lz=01;31:*.lzo=01;31:*.xz=01;31:*.zst=01;31:*.tzst=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01;31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.alz=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.cab=01;31:*.wim=01;31:*.swm=01;31:*.dwm=01;31:*.esd=01;31:*.jpg=01;35:*.jpeg=01;35:*.mjpg=01;35:*.mjpeg=01;35:*.gif=01;35:*.bmp=01;35:*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.png=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35:*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.webp=01;35:*.ogm=01;35:*.mp4=01;35:*.m4v=01;35:*.mp4v=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35:*.gl=01;35:*.dl=01;35:*.xcf=01;35:*.xwd=01;35:*.yuv=01;35:*.cgm=01;35:*.emf=01;35:*.ogv=01;35:*.ogx=01;35:*.aac=00;36:*.au=00;36:*.flac=00;36:*.m4a=00;36:*.mid=00;36:*.midi=00;36:*.mka=00;36:*.mp3=00;36:*.mpc=00;36:*.ogg=00;36:*.ra=00;36:*.wav=00;36:*.oga=00;36:*.opus=00;36:*.spx=00;36:*.xspf=00;36:\r")
;;; (read-line "GUILE_LOAD_COMPILED_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/guile/3.0/site-ccache:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0\r")
;;; (read-line "INFOPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/info\r")
;;; (read-line "TERM=screen.xterm-256color\r")
;;; (read-line "CPLUS_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include/c++:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include\r")
;;; (read-line "ACLOCAL_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/aclocal\r")
;;; (read-line "USER=marusich\r")
;;; (read-line "LIBRARY_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib\r")
;;; (read-line "SHLVL=1\r")
;;; (read-line "GUIX_LOCPATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/locale\r")
;;; (read-line "GUIX_ENVIRONMENT=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile\r")
;;; (read-line "PS1=\r")
;;; (read-line "PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin:/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/sbin\r")
;;; (read-line "C_INCLUDE_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/include\r")
;;; (read-line "_=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/bin/env\r")
;;; (read-line "GUIX-CHECK-DONE\r")
;;; (variable "PKG_CONFIG_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/lib/pkgconfig" "PKG_CONFIG_PATH")
;;; (variable "PWD=/home/marusich/guix-master" "PWD")
;;; (variable "LOGNAME=marusich" "LOGNAME")
;;; (variable "GUILE_LOAD_PATH=/gnu/store/hvcq6yjfjjc7060pq09zm1rj02mivg4h-profile/share/guile/site/3.0" "GUILE_LOAD_PATH")
;;; (variable "HOME=/home/marusich" "HOME")
;;; (variable "LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:do=01;35:bd=40;33;01:cd=40;33;01:or=40;31;01:mi=00:su=37;41:sg=30;43:ca=30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arc=01;31:*.arj=01;31:*.taz=01;31:*.lha=01;31:*.lz4=01;31:*.lzh=01;31:*.lzma=01;31:*.tlz=01;31:*.txz=01;31:*.tzo=01;31:*.t7z=01;31:*.zip=01;31:*.z=01;31:*.dz=01;31:*.gz=01;31:*.lrz=01;31:*.lz=01;31:*.lzo=01;31:*.xz=01;31:*.zst=01;31:*.tzst=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01;31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.alz=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.cab=01;31:*.wim=01;31:*.swm=01;31:*.dwm=01;31:*.esd=01;31:*.jpg=01;35:*.jpeg=01;35:*.mjpg=01;35:*.mjpeg=01;35:*.gif=01;35:*.bmp=01;35:*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.png=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35:*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.webp=01;35:*.ogm=01;35:*.mp4=01;35:*.m4v=01;35:*.mp4v=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35:*.gl=01;35:*.dl=01;35:*.xcf=01;35:*.xwd=01;
From c3eea81846ae71a246e6b592be74062f4bf26474 Mon Sep 17 00:00:00 2001
* guix/scripts/environment.scm (child-shell-environment): In the script
executed the child shell, set PS1 to an empty value and then echo three
sentinel lines to try to "flush" the original PS1 value before printing the
environment variables. In the parent process, read and discard all lines up
to and including the last sentinel line. After that, read the remaining lines
as usual.
---
guix/scripts/environment.scm | 18 +++++++++++++++++-
1 file changed, 17 insertions(+), 1 deletion(-)
Toggle diff (47 lines)
diff --git a/guix/scripts/environment.scm b/guix/scripts/environment.scm
index ec071402f4..0b137467f9 100644
--- a/guix/scripts/environment.scm
+++ b/guix/scripts/environment.scm
@@ -2,6 +2,7 @@
;;; Copyright © 2014, 2015, 2018 David Thompson <davet@gnu.org>
;;; Copyright © 2015-2022 Ludovic Courtès <ludo@gnu.org>
;;; Copyright © 2018 Mike Gerwitz <mtg@gnu.org>
+;;; Copyright © 2022 Chris Marusich <cmmarusich@gmail.com>
;;;
;;; This file is part of GNU Guix.
;;;
@@ -420,7 +421,16 @@ by running 'set' in the shell."
;; Script to obtain the list of environment variable values. On a POSIX
;; shell we can rely on 'set', but on fish we have to use 'env' (fish's
;; 'set' truncates values and prints them in a different format.)
- "env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
+ ;;
+ ;; Why print "GUIX_FLUSH" a few times? We are trying to "flush" the
+ ;; original PS1 value to the port so we can read it (and discard it)
+ ;; before we start reading the environment variables from the port. If we
+ ;; don't do this, the original PS1 value can sometimes get interleaved
+ ;; into the output, which interferes with our parsing logic. It's a hack,
+ ;; but in practice it seems to do the job. If you know of a more graceful
+ ;; solution, please implement it! See: https://issues.guix.gnu.org/51466
+ "PS1=; for i in 1 2 3; do echo GUIX_FLUSH_$i; done; \
+env || /usr/bin/env || set; echo GUIX-CHECK-DONE; read x; exit\n")
(define lines
(match (primitive-fork)
@@ -439,6 +449,12 @@ by running 'set' in the shell."
(let* ((port (fdopen controller "r+l"))
(result (begin
(display script port)
+ ;; Ignore all lines up to and including the final
+ ;; "GUIX_FLUSH" line.
+ (while (not (string=? "GUIX_FLUSH_3\r"
+ (read-line port))))
+ ;; Now (hopefully) the original PS1 value will not be
+ ;; interleaved in the remaining lines.
(let loop ((lines '()))
(match (read-line port)
((? eof-object?) (reverse lines))
base-commit: d65979c46c99dc36324ca94aa9650b9de37f22de
--
2.26.3