GNU bug report logs - #76888
31.0.50; start-process: Spawning child process: Invalid argument

Previous Next

Package: emacs;

Reported by: Richard Copley <rcopley <at> gmail.com>

Date: Sun, 9 Mar 2025 12:39:01 UTC

Severity: normal

Found in version 31.0.50

Fixed in version 31.1

Done: Michael Albinus <michael.albinus <at> gmx.de>

Bug is archived. No further changes may be made.

To add a comment to this bug, you must first unarchive it, by sending
a message to control AT debbugs.gnu.org, with unarchive 76888 in the body.
You can then email your comments to 76888 AT debbugs.gnu.org in the normal way.

Toggle the display of automated, internal messages from the tracker.

View this report as an mbox folder, status mbox, maintainer mbox


Report forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 09 Mar 2025 12:39:01 GMT) Full text and rfc822 format available.

Acknowledgement sent to Richard Copley <rcopley <at> gmail.com>:
New bug report received and forwarded. Copy sent to bug-gnu-emacs <at> gnu.org. (Sun, 09 Mar 2025 12:39:02 GMT) Full text and rfc822 format available.

Message #5 received at submit <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: bug-gnu-emacs <at> gnu.org
Subject: 31.0.50; start-process: Spawning child process: Invalid argument
Date: Sun, 9 Mar 2025 12:37:56 +0000
When the "*Async Shell Command*" buffer is re-used, its
connection-local variable 'shell-file-name' is set permanently instead
of temporarily, and if the value is inappropriate, an error ensues.

Recipe from 'emacs -Q', on Windows:

Visit a remote file on a Linux system using tramp. (You will need to
substitute an appropriate remote file name here.)

[C-x C-f] /plink:xxx:/ [RET]

Execute an asynchronous shell command.

[M-&] echo [RET]

NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
returns the path to "cmdproxy.exe" as expected.

Execute an asynchronous shell command again.

[M-&] echo [RET]

NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
now returns "/bin/sh".

Visit a local file.

[C-x C-f C-a C-k] C:/ [RET]

Execute an async shell command.

[M-&] echo [RET]

An error is signalled, with the message "start-process: Spawning child
process: Invalid argument". (Note, the invalid argument is the
executable name, "/bin/sh").

In GNU Emacs 31.0.50 (build 1, x86_64-w64-mingw32) of 2025-03-01 built
 on MACHINE
Repository revision: 2095d0fcc686107c2ee25f75983710ca5f4abacf
Repository branch: master
Windowing system distributor 'Microsoft Corp.', version 10.0.19045
System Description: Microsoft Windows 10 Pro (v10.0.2009.19045.5555)

Configured using:
 'configure --config-cache --with-modules --without-pop
 --without-compress-install --with-tree-sitter=ifavailable
 --without-libsystemd --without-dbus --without-gconf --without-gsettings
 --without-mailutils --with-small-ja-dic --with-native-compilation=aot
 --prefix=/mingw64 --build=x86_64-w64-mingw32 'CFLAGS=-O2'

Configured features:
ACL GIF GMP GNUTLS HARFBUZZ JPEG LCMS2 LIBXML2 MODULES NATIVE_COMP
NOTIFY W32NOTIFY PDUMPER PNG RSVG SOUND SQLITE3 THREADS TIFF
TOOLKIT_SCROLL_BARS TREE_SITTER WEBP XPM ZLIB

Important settings:
  value of $LANG: ENG
  locale-coding-system: cp1252

Major mode: Messages

Minor modes in effect:
  tooltip-mode: t
  global-eldoc-mode: t
  show-paren-mode: t
  electric-indent-mode: t
  mouse-wheel-mode: t
  tool-bar-mode: t
  menu-bar-mode: t
  file-name-shadow-mode: t
  global-font-lock-mode: t
  font-lock-mode: t
  blink-cursor-mode: t
  minibuffer-regexp-mode: t
  buffer-read-only: t
  line-number-mode: t
  indent-tabs-mode: t
  transient-mark-mode: t
  auto-composition-mode: t
  auto-encryption-mode: t
  auto-compression-mode: t

Load-path shadows:
None found.

Features:
(shadow sort mail-extr emacsbug lisp-mnt message mailcap yank-media puny
rfc822 mml mml-sec epa derived epg rfc6068 epg-config gnus-util
text-property-search mm-decode mm-bodies mm-encode mail-parse rfc2231
mailabbrev gmm-utils mailheader sendmail rfc2047 rfc2045 ietf-drums
mm-util mail-prsvr mail-utils dired-aux dired dired-loaddefs tramp-cmds
tramp-cache time-stamp tramp-sh comp-run comp-common tramp rx trampver
tramp-integration files-x tramp-message help-mode tramp-compat xdg shell
pcomplete comint ansi-osc ring parse-time iso8601 time-date format-spec
auth-source cl-seq eieio eieio-core cl-macs icons password-cache json
subr-x map byte-opt gv bytecomp byte-compile ansi-color tramp-loaddefs
cl-loaddefs cl-lib rmc iso-transl tooltip cconv eldoc paren electric
uniquify ediff-hook vc-hooks lisp-float-type elisp-mode mwheel
touch-screen dos-w32 ls-lisp disp-table term/w32-win w32-win w32-vars
term/common-win tool-bar dnd fontset image regexp-opt fringe
tabulated-list replace newcomment text-mode lisp-mode prog-mode register
page tab-bar menu-bar rfn-eshadow isearch easymenu timer select
scroll-bar mouse jit-lock font-lock syntax font-core term/tty-colors
frame minibuffer nadvice seq simple cl-generic indonesian philippine
cham georgian utf-8-lang misc-lang vietnamese tibetan thai tai-viet lao
korean japanese eucjp-ms cp51932 hebrew greek romanian slovak czech
european ethiopic indian cyrillic chinese composite emoji-zwj charscript
charprop case-table epa-hook jka-cmpr-hook help abbrev obarray oclosure
cl-preloaded button loaddefs theme-loaddefs faces cus-face macroexp
files window text-properties overlay sha1 md5 base64 format env
code-pages mule custom widget keymap hashtable-print-readable backquote
threads w32notify w32 lcms2 multi-tty move-toolbar make-network-process
tty-child-frames native-compile emacs)

Memory information:
((conses 16 108744 17611) (symbols 48 9243 0) (strings 32 30108 2194)
 (string-bytes 1 1031459) (vectors 16 16442)
 (vector-slots 8 220843 10978) (floats 8 36 12) (intervals 56 782 25)
 (buffers 992 15))




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sat, 15 Mar 2025 11:49:02 GMT) Full text and rfc822 format available.

Message #8 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: Richard Copley <rcopley <at> gmail.com>,
 Michael Albinus <michael.albinus <at> gmx.de>
Cc: 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50;
 start-process: Spawning child process: Invalid argument
Date: Sat, 15 Mar 2025 13:48:10 +0200
> From: Richard Copley <rcopley <at> gmail.com>
> Date: Sun, 9 Mar 2025 12:37:56 +0000
> 
> When the "*Async Shell Command*" buffer is re-used, its
> connection-local variable 'shell-file-name' is set permanently instead
> of temporarily, and if the value is inappropriate, an error ensues.
> 
> Recipe from 'emacs -Q', on Windows:
> 
> Visit a remote file on a Linux system using tramp. (You will need to
> substitute an appropriate remote file name here.)
> 
> [C-x C-f] /plink:xxx:/ [RET]
> 
> Execute an asynchronous shell command.
> 
> [M-&] echo [RET]
> 
> NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> returns the path to "cmdproxy.exe" as expected.
> 
> Execute an asynchronous shell command again.
> 
> [M-&] echo [RET]
> 
> NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> now returns "/bin/sh".
> 
> Visit a local file.
> 
> [C-x C-f C-a C-k] C:/ [RET]
> 
> Execute an async shell command.
> 
> [M-&] echo [RET]
> 
> An error is signalled, with the message "start-process: Spawning child
> process: Invalid argument". (Note, the invalid argument is the
> executable name, "/bin/sh").

Michael, any comments or suggestions?




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 16 Mar 2025 08:22:04 GMT) Full text and rfc822 format available.

Message #11 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: rcopley <at> gmail.com, michael.albinus <at> gmx.de
Cc: 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50;
 start-process: Spawning child process: Invalid argument
Date: Sun, 16 Mar 2025 10:21:13 +0200
> Cc: 76888 <at> debbugs.gnu.org
> Date: Sat, 15 Mar 2025 13:48:10 +0200
> From: Eli Zaretskii <eliz <at> gnu.org>

Trying this recipe, I have some questions and observations.

> > From: Richard Copley <rcopley <at> gmail.com>
> > Date: Sun, 9 Mar 2025 12:37:56 +0000
> > 
> > When the "*Async Shell Command*" buffer is re-used, its
> > connection-local variable 'shell-file-name' is set permanently instead
> > of temporarily, and if the value is inappropriate, an error ensues.

I'm not sure this is relevant, see below.  Or if it _is_ relevant, I
don't think I understand why the value of shell-file-name in the
"*Async Shell Command*" buffer matters.

> > Recipe from 'emacs -Q', on Windows:
> > 
> > Visit a remote file on a Linux system using tramp. (You will need to
> > substitute an appropriate remote file name here.)
> > 
> > [C-x C-f] /plink:xxx:/ [RET]

This shows the remote file on display.

> > Execute an asynchronous shell command.
> > 
> > [M-&] echo [RET]

This command should run on the remote host, because the
default-directory is remote, due to the current-buffer visiting a
remote file, per the above "C-x C-f" command.

Is that what you see?  Does the "echo" command run on the remote host?

> > NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> > returns the path to "cmdproxy.exe" as expected.
> > 
> > Execute an asynchronous shell command again.
> > 
> > [M-&] echo [RET]
> > 
> > NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> > now returns "/bin/sh".
> > 
> > Visit a local file.
> > 
> > [C-x C-f C-a C-k] C:/ [RET]

Now the local file is shown in the selected window, and the current
buffer visits that file, so its default-directory is local.

> > Execute an async shell command.
> > 
> > [M-&] echo [RET]

This command should run locally, because default-directory is local.
Is that what you see?

> > An error is signalled, with the message "start-process: Spawning child
> > process: Invalid argument". (Note, the invalid argument is the
> > executable name, "/bin/sh").

In my case, the error message dosn't pop up each time, but I do see it
from time to time.

Michael, does Tramp reuse the value of shell-file-name between shell
commands, and if so, how does it know whether to reuse or not?




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 16 Mar 2025 08:49:04 GMT) Full text and rfc822 format available.

Message #14 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: Eli Zaretskii <eliz <at> gnu.org>
Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Sun, 16 Mar 2025 08:47:35 +0000
On Sun, 16 Mar 2025 at 08:21, Eli Zaretskii <eliz <at> gnu.org> wrote:
>
> > Cc: 76888 <at> debbugs.gnu.org
> > Date: Sat, 15 Mar 2025 13:48:10 +0200
> > From: Eli Zaretskii <eliz <at> gnu.org>
>
> Trying this recipe, I have some questions and observations.
>
> > > From: Richard Copley <rcopley <at> gmail.com>
> > > Date: Sun, 9 Mar 2025 12:37:56 +0000
> > >
> > > When the "*Async Shell Command*" buffer is re-used, its
> > > connection-local variable 'shell-file-name' is set permanently instead
> > > of temporarily, and if the value is inappropriate, an error ensues.
>
> I'm not sure this is relevant, see below.  Or if it _is_ relevant, I
> don't think I understand why the value of shell-file-name in the
> "*Async Shell Command*" buffer matters.

There are two factors, the combination of which leads to the problem.

The first factor is that the value of shell-file-name sometimes gets
set buffer-locally in the "*Async Shell Command*" buffer. (This is
true for the Tramp code, when the buffer is reused. I don't know if it
is meaningful to ask whether it is true for the non-Tramp code.)

The second factor is that 'async-shell-command' sometimes uses the
value of shell-file-name from the "*Async Shell Command*" buffer.
(This is true for the non-Tramp code. I don't know if it is true for
the Tramp code.)

If we were to arrange for at least one of those factors to be no
longer true, the problem would go away.

Which one should we target? I make no recommendation. But, for
example, if we target the second factor, we could kill all buffer
local variables in the "*Async Shell Command*" buffer somewhere near
the beginning of the code path that is followed when
'async-shell-command' is invoked. This would need to be done in the
non-Tramp code. I don't know if it would need to be done in the Tramp
code.

All of this may also apply to 'shell-command'. I did not investigate.

> > > Recipe from 'emacs -Q', on Windows:
> > >
> > > Visit a remote file on a Linux system using tramp. (You will need to
> > > substitute an appropriate remote file name here.)
> > >
> > > [C-x C-f] /plink:xxx:/ [RET]
>
> This shows the remote file on display.
>
> > > Execute an asynchronous shell command.
> > >
> > > [M-&] echo [RET]
>
> This command should run on the remote host, because the
> default-directory is remote, due to the current-buffer visiting a
> remote file, per the above "C-x C-f" command.
>
> Is that what you see?  Does the "echo" command run on the remote host?

Yes.

> > > NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> > > returns the path to "cmdproxy.exe" as expected.
> > >
> > > Execute an asynchronous shell command again.
> > >
> > > [M-&] echo [RET]
> > >
> > > NOTE: (with-current-buffer "*Async Shell Command*" shell-file-name)
> > > now returns "/bin/sh".
> > >
> > > Visit a local file.
> > >
> > > [C-x C-f C-a C-k] C:/ [RET]
>
> Now the local file is shown in the selected window, and the current
> buffer visits that file, so its default-directory is local.
>
> > > Execute an async shell command.
> > >
> > > [M-&] echo [RET]
>
> This command should run locally, because default-directory is local.
> Is that what you see?

Yes.

> > > An error is signalled, with the message "start-process: Spawning child
> > > process: Invalid argument". (Note, the invalid argument is the
> > > executable name, "/bin/sh").
>
> In my case, the error message dosn't pop up each time, but I do see it
> from time to time.
>
> Michael, does Tramp reuse the value of shell-file-name between shell
> commands, and if so, how does it know whether to reuse or not?




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 16 Mar 2025 09:08:04 GMT) Full text and rfc822 format available.

Message #17 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: Richard Copley <rcopley <at> gmail.com>
Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Sun, 16 Mar 2025 11:07:12 +0200
> From: Richard Copley <rcopley <at> gmail.com>
> Date: Sun, 16 Mar 2025 08:47:35 +0000
> Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
> 
> > I'm not sure this is relevant, see below.  Or if it _is_ relevant, I
> > don't think I understand why the value of shell-file-name in the
> > "*Async Shell Command*" buffer matters.
> 
> There are two factors, the combination of which leads to the problem.
> 
> The first factor is that the value of shell-file-name sometimes gets
> set buffer-locally in the "*Async Shell Command*" buffer. (This is
> true for the Tramp code, when the buffer is reused. I don't know if it
> is meaningful to ask whether it is true for the non-Tramp code.)

If Tramp sets the buffer-local value in the "*Async Shell Command*"
buffer, it should also set default-directory in that buffer.

> The second factor is that 'async-shell-command' sometimes uses the
> value of shell-file-name from the "*Async Shell Command*" buffer.
> (This is true for the non-Tramp code. I don't know if it is true for
> the Tramp code.)

Please point out the code which uses the value of shell-file-name
local to the "*Async Shell Command*" buffer.

In any case, since no step in your recipe makes that buffer the
current buffer, the buffer-local value there should not matter.

> Which one should we target? I make no recommendation. But, for
> example, if we target the second factor, we could kill all buffer
> local variables in the "*Async Shell Command*" buffer somewhere near
> the beginning of the code path that is followed when
> 'async-shell-command' is invoked. This would need to be done in the
> non-Tramp code. I don't know if it would need to be done in the Tramp
> code.

Buffer-local values should matter only when commands are invoked with
that buffer the current buffer.  Which part(s) of your recipe do that?




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 16 Mar 2025 09:41:03 GMT) Full text and rfc822 format available.

Message #20 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: Eli Zaretskii <eliz <at> gnu.org>
Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Sun, 16 Mar 2025 09:39:32 +0000
On Sun, 16 Mar 2025 at 09:07, Eli Zaretskii <eliz <at> gnu.org> wrote:
>
> > From: Richard Copley <rcopley <at> gmail.com>
> > Date: Sun, 16 Mar 2025 08:47:35 +0000
> > Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
> >
> > > I'm not sure this is relevant, see below.  Or if it _is_ relevant, I
> > > don't think I understand why the value of shell-file-name in the
> > > "*Async Shell Command*" buffer matters.
> >
> > There are two factors, the combination of which leads to the problem.
> >
> > The first factor is that the value of shell-file-name sometimes gets
> > set buffer-locally in the "*Async Shell Command*" buffer. (This is
> > true for the Tramp code, when the buffer is reused. I don't know if it
> > is meaningful to ask whether it is true for the non-Tramp code.)
>
> If Tramp sets the buffer-local value in the "*Async Shell Command*"
> buffer, it should also set default-directory in that buffer.
>
> > The second factor is that 'async-shell-command' sometimes uses the
> > value of shell-file-name from the "*Async Shell Command*" buffer.
> > (This is true for the non-Tramp code. I don't know if it is true for
> > the Tramp code.)
>
> Please point out the code which uses the value of shell-file-name
> local to the "*Async Shell Command*" buffer.

In 'shell-command' in "simple.el", 'start-process-shell-command'
is called after changing to the "*Async Shell Command*" buffer.

        (let* ((buffer (get-buffer-create
                (or output-buffer shell-command-buffer-name-async)))
                [...])
          [...]
          (with-current-buffer buffer
        [...]
          (setq proc
            (start-process-shell-command "Shell" buffer command)))

Then in the body of 'start-process-shell-command',

  (start-process name buffer shell-file-name shell-command-switch command)

> In any case, since no step in your recipe makes that buffer the
> current buffer, the buffer-local value there should not matter.

No disagreement from me.

> > Which one should we target? I make no recommendation. But, for
> > example, if we target the second factor, we could kill all buffer
> > local variables in the "*Async Shell Command*" buffer somewhere near
> > the beginning of the code path that is followed when
> > 'async-shell-command' is invoked. This would need to be done in the
> > non-Tramp code. I don't know if it would need to be done in the Tramp
> > code.
>
> Buffer-local values should matter only when commands are invoked with
> that buffer the current buffer.  Which part(s) of your recipe do that?

The recipe does not do that. The command 'async-shell-command' is
invoked three times from dired buffers and never from the "*Async
Shell Command*" buffer.




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Sun, 16 Mar 2025 10:26:05 GMT) Full text and rfc822 format available.

Message #23 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: Richard Copley <rcopley <at> gmail.com>
Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Sun, 16 Mar 2025 12:24:54 +0200
> From: Richard Copley <rcopley <at> gmail.com>
> Date: Sun, 16 Mar 2025 09:39:32 +0000
> Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
> 
> On Sun, 16 Mar 2025 at 09:07, Eli Zaretskii <eliz <at> gnu.org> wrote:
> >
> > > The first factor is that the value of shell-file-name sometimes gets
> > > set buffer-locally in the "*Async Shell Command*" buffer. (This is
> > > true for the Tramp code, when the buffer is reused. I don't know if it
> > > is meaningful to ask whether it is true for the non-Tramp code.)
> >
> > If Tramp sets the buffer-local value in the "*Async Shell Command*"
> > buffer, it should also set default-directory in that buffer.
> >
> > > The second factor is that 'async-shell-command' sometimes uses the
> > > value of shell-file-name from the "*Async Shell Command*" buffer.
> > > (This is true for the non-Tramp code. I don't know if it is true for
> > > the Tramp code.)
> >
> > Please point out the code which uses the value of shell-file-name
> > local to the "*Async Shell Command*" buffer.
> 
> In 'shell-command' in "simple.el", 'start-process-shell-command'
> is called after changing to the "*Async Shell Command*" buffer.
> 
>         (let* ((buffer (get-buffer-create
>                 (or output-buffer shell-command-buffer-name-async)))
>                 [...])
>           [...]
>           (with-current-buffer buffer
>         [...]
>           (setq proc
>             (start-process-shell-command "Shell" buffer command)))
> 
> Then in the body of 'start-process-shell-command',
> 
>   (start-process name buffer shell-file-name shell-command-switch command)

That's a mistake: at least for local commands, the values of
shell-file-name and shell-command-switch should come from the buffer
that is current when the command is invoked.

Let's wait for Michael to chime in and explain how these variables
should be populated for remote shell commands; I guess
connection-local variables should be consulted, but the relevant
connection should be taken again from the buffer that is current when
the command is invoked.

> > Buffer-local values should matter only when commands are invoked with
> > that buffer the current buffer.  Which part(s) of your recipe do that?
> 
> The recipe does not do that. The command 'async-shell-command' is
> invoked three times from dired buffers and never from the "*Async
> Shell Command*" buffer.

Then it's a clear bug.  I'm guessing the code in question never
expected shell-command to have a buffer-local value (which is indeed
an unusual and strange situation).  So maybe a simpler solution is to
never make shell-command's value be buffer-local.




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Mon, 17 Mar 2025 09:02:01 GMT) Full text and rfc822 format available.

Message #26 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Michael Albinus <michael.albinus <at> gmx.de>
To: Eli Zaretskii <eliz <at> gnu.org>
Cc: Richard Copley <rcopley <at> gmail.com>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Mon, 17 Mar 2025 10:01:03 +0100
Eli Zaretskii <eliz <at> gnu.org> writes:

Hi,

>> > > The first factor is that the value of shell-file-name sometimes gets
>> > > set buffer-locally in the "*Async Shell Command*" buffer. (This is
>> > > true for the Tramp code, when the buffer is reused. I don't know if it
>> > > is meaningful to ask whether it is true for the non-Tramp code.)
>> >
>> > If Tramp sets the buffer-local value in the "*Async Shell Command*"
>> > buffer, it should also set default-directory in that buffer.

It is vice-versa. Tramp sets a buffer-local value of shell-file-name in
"*Async Shell Command*" depending on the default-directory of that
buffer. In fact, it is a connection-local value (which is implemented
via buffer-local value).

The setting of the connection-local value is done in
tramp-integration.el:

--8<---------------cut here---------------start------------->8---
(defconst tramp-connection-local-default-shell-variables
  '((shell-file-name . "/bin/sh")
    (shell-command-switch . "-c"))
  "Default connection-local shell variables for remote connections.")
--8<---------------cut here---------------end--------------->8---

>> In 'shell-command' in "simple.el", 'start-process-shell-command'
>> is called after changing to the "*Async Shell Command*" buffer.
>>
>>         (let* ((buffer (get-buffer-create
>>                 (or output-buffer shell-command-buffer-name-async)))
>>                 [...])
>>           [...]
>>           (with-current-buffer buffer
>>         [...]
>>           (setq proc
>>             (start-process-shell-command "Shell" buffer command)))
>>
>> Then in the body of 'start-process-shell-command',
>>
>>   (start-process name buffer shell-file-name shell-command-switch command)
>
> That's a mistake: at least for local commands, the values of
> shell-file-name and shell-command-switch should come from the buffer
> that is current when the command is invoked.
>
> Let's wait for Michael to chime in and explain how these variables
> should be populated for remote shell commands; I guess
> connection-local variables should be consulted, but the relevant
> connection should be taken again from the buffer that is current when
> the command is invoked.

Tramp sets connection-local values for asynchronous processes in the
buffer which is given at start. Always.

>> > Buffer-local values should matter only when commands are invoked with
>> > that buffer the current buffer.  Which part(s) of your recipe do that?

We're speaking about connection-local values. And they are set in
Tramp's implementation of make-process.

>> The recipe does not do that. The command 'async-shell-command' is
>> invoked three times from dired buffers and never from the "*Async
>> Shell Command*" buffer.
>
> Then it's a clear bug.  I'm guessing the code in question never
> expected shell-command to have a buffer-local value (which is indeed
> an unusual and strange situation).  So maybe a simpler solution is to
> never make shell-command's value be buffer-local.

That's not possible if Tramp is in play with its connection-local
variables.

It seems to me that the problem is rather the re-use of the "*Async
Shell Command*" buffer even in case the default-directory changes. It
isn't a problem if this change is inside the same "remote" file system
Tramp offers virtually. But if the change means, that another remote
connection is established, or there is a change between remote and local
directory, I propose to use another (new) "*Async Shell Command*" buffer.

Best regards, Michael.




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Mon, 17 Mar 2025 14:36:03 GMT) Full text and rfc822 format available.

Message #29 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: Michael Albinus <michael.albinus <at> gmx.de>
Cc: rcopley <at> gmail.com, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Mon, 17 Mar 2025 16:35:14 +0200
> From: Michael Albinus <michael.albinus <at> gmx.de>
> Cc: Richard Copley <rcopley <at> gmail.com>,  76888 <at> debbugs.gnu.org
> Date: Mon, 17 Mar 2025 10:01:03 +0100
> 
> It seems to me that the problem is rather the re-use of the "*Async
> Shell Command*" buffer even in case the default-directory changes. It
> isn't a problem if this change is inside the same "remote" file system
> Tramp offers virtually. But if the change means, that another remote
> connection is established, or there is a change between remote and local
> directory, I propose to use another (new) "*Async Shell Command*" buffer.

We could reuse the buffer, but kill all its local variables, no?

But I feel that I still don't understand how this problem happens.
Can you take me through the steps of processing M-&, and explain how
come the buffer-local value of "*Async Shell Command*" gets to be used
for M-& in this scenario?  In particular, even if the buffer is
reused, why don't we re-calculate the local value of shell-file-name
every invocation of a shell command? why cache it?




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Mon, 24 Mar 2025 11:55:01 GMT) Full text and rfc822 format available.

Message #32 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: Eli Zaretskii <eliz <at> gnu.org>
Cc: Michael Albinus <michael.albinus <at> gmx.de>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Mon, 24 Mar 2025 11:54:07 +0000
On Sun, 16 Mar 2025 at 10:24, Eli Zaretskii <eliz <at> gnu.org> wrote:
>
> > From: Richard Copley <rcopley <at> gmail.com>
> > Date: Sun, 16 Mar 2025 09:39:32 +0000
> > Cc: michael.albinus <at> gmx.de, 76888 <at> debbugs.gnu.org
> >
> > On Sun, 16 Mar 2025 at 09:07, Eli Zaretskii <eliz <at> gnu.org> wrote:
> > >
> > > > The first factor is that the value of shell-file-name sometimes gets
> > > > set buffer-locally in the "*Async Shell Command*" buffer. (This is
> > > > true for the Tramp code, when the buffer is reused. I don't know if it
> > > > is meaningful to ask whether it is true for the non-Tramp code.)
> > >
> > > If Tramp sets the buffer-local value in the "*Async Shell Command*"
> > > buffer, it should also set default-directory in that buffer.
> > >
> > > > The second factor is that 'async-shell-command' sometimes uses the
> > > > value of shell-file-name from the "*Async Shell Command*" buffer.
> > > > (This is true for the non-Tramp code. I don't know if it is true for
> > > > the Tramp code.)
> > >
> > > Please point out the code which uses the value of shell-file-name
> > > local to the "*Async Shell Command*" buffer.
> >
> > In 'shell-command' in "simple.el", 'start-process-shell-command'
> > is called after changing to the "*Async Shell Command*" buffer.
> >
> >         (let* ((buffer (get-buffer-create
> >                 (or output-buffer shell-command-buffer-name-async)))
> >                 [...])
> >           [...]
> >           (with-current-buffer buffer
> >         [...]
> >           (setq proc
> >             (start-process-shell-command "Shell" buffer command)))
> >
> > Then in the body of 'start-process-shell-command',
> >
> >   (start-process name buffer shell-file-name shell-command-switch command)
>
> That's a mistake: at least for local commands, the values of
> shell-file-name and shell-command-switch should come from the buffer
> that is current when the command is invoked.

It's easy to move the call to 'start-process-shell-command' outside
the 'with-current-buffer' form. I have patched my local emacs repo to
do that. It works just fine for me. Whether that is the right thing to
do I leave to your judgement. I refrain from attaching the patch since
I do not intend to complete a copyright assignment.




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Tue, 25 Mar 2025 12:57:02 GMT) Full text and rfc822 format available.

Message #35 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Michael Albinus <michael.albinus <at> gmx.de>
To: Richard Copley <rcopley <at> gmail.com>
Cc: Eli Zaretskii <eliz <at> gnu.org>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Tue, 25 Mar 2025 13:56:31 +0100
[Message part 1 (text/plain, inline)]
Richard Copley <rcopley <at> gmail.com> writes:

Hi Richard,

> It's easy to move the call to 'start-process-shell-command' outside
> the 'with-current-buffer' form. I have patched my local emacs repo to
> do that. It works just fine for me. Whether that is the right thing to
> do I leave to your judgement. I refrain from attaching the patch since
> I do not intend to complete a copyright assignment.

Thank you for the analysis. However, I don't believe that your change is
correct. `buffer' is the working (output) buffer of
start-process-shell-command, so we shall call it here.

Instead, I've tried the appended patch. Could you, please, check? It
fixes the problem for me.

Best regards, Michael.

[Message part 2 (text/x-patch, attachment)]

Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Wed, 26 Mar 2025 10:11:02 GMT) Full text and rfc822 format available.

Message #38 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: Michael Albinus <michael.albinus <at> gmx.de>
Cc: Eli Zaretskii <eliz <at> gnu.org>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Wed, 26 Mar 2025 10:09:45 +0000
Thanks Michael.

On Tue, 25 Mar 2025 at 12:56, Michael Albinus <michael.albinus <at> gmx.de> wrote:
>
> Richard Copley <rcopley <at> gmail.com> writes:
>
> > It's easy to move the call to 'start-process-shell-command' outside
> > the 'with-current-buffer' form. I have patched my local emacs repo to
> > do that. It works just fine for me. Whether that is the right thing to
> > do I leave to your judgement. I refrain from attaching the patch since
> > I do not intend to complete a copyright assignment.
>
> Thank you for the analysis. However, I don't believe that your change is
> correct. `buffer' is the working (output) buffer of
> start-process-shell-command, so we shall call it here.

Yes, but 'start-process-shell-command' takes care of switching to 'buffer'.

> Instead, I've tried the appended patch. Could you, please, check? It
> fixes the problem for me.

It doesn't work for me. With your patch, on my system, the original
recipe still exhibits the problem on the third invocation of
'async-shell-command'.

At the time when '(connection-local-value shell-file-name)' is invoked
in your patch, the current buffer is the output buffer (not the buffer
from which the user invoked 'async-shell-command'), and the default
directory is "/plink:xxx/" (not "c:/"), and the value returned is
"/bin/sh" (not the file name of "cmdproxy.exe").




Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Thu, 27 Mar 2025 11:14:03 GMT) Full text and rfc822 format available.

Message #41 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Michael Albinus <michael.albinus <at> gmx.de>
To: Richard Copley <rcopley <at> gmail.com>
Cc: Eli Zaretskii <eliz <at> gnu.org>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Thu, 27 Mar 2025 12:13:11 +0100
[Message part 1 (text/plain, inline)]
Richard Copley <rcopley <at> gmail.com> writes:

Hi Richard,

> Thanks Michael.
>
>> Thank you for the analysis. However, I don't believe that your change is
>> correct. `buffer' is the working (output) buffer of
>> start-process-shell-command, so we shall call it here.
>
> Yes, but 'start-process-shell-command' takes care of switching to 'buffer'.

Yes. But we're already here, due to the '(with-current-buffer buffer ...'.

>> Instead, I've tried the appended patch. Could you, please, check? It
>> fixes the problem for me.
>
> It doesn't work for me. With your patch, on my system, the original
> recipe still exhibits the problem on the third invocation of
> 'async-shell-command'.
>
> At the time when '(connection-local-value shell-file-name)' is invoked
> in your patch, the current buffer is the output buffer (not the buffer
> from which the user invoked 'async-shell-command'), and the default
> directory is "/plink:xxx/" (not "c:/"), and the value returned is
> "/bin/sh" (not the file name of "cmdproxy.exe").

I hoped that the connection-local-value trick works. The
default-directory of buffer is already changed; there is '(setq
default-directory directory)' in time.

However, connection-local-value does not work as I've hoped. It simply
uses the recent (buffer-local) value, if default-directory isn't remote.

So we must kill the local value(s) explicitly. The revised patch
(appended) seems to work. Tested on my Windows 11 VM with your recipe.

Best regards, Michael.

[Message part 2 (text/x-patch, attachment)]

Information forwarded to bug-gnu-emacs <at> gnu.org:
bug#76888; Package emacs. (Thu, 27 Mar 2025 16:39:02 GMT) Full text and rfc822 format available.

Message #44 received at 76888 <at> debbugs.gnu.org (full text, mbox):

From: Richard Copley <rcopley <at> gmail.com>
To: Michael Albinus <michael.albinus <at> gmx.de>
Cc: Eli Zaretskii <eliz <at> gnu.org>, 76888 <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Thu, 27 Mar 2025 16:38:04 +0000
On Thu, 27 Mar 2025 at 11:13, Michael Albinus <michael.albinus <at> gmx.de> wrote:
>
> Richard Copley <rcopley <at> gmail.com> writes:
>
> Hi Richard,
>
> > Thanks Michael.
> >
> >> Thank you for the analysis. However, I don't believe that your change is
> >> correct. `buffer' is the working (output) buffer of
> >> start-process-shell-command, so we shall call it here.
> >
> > Yes, but 'start-process-shell-command' takes care of switching to 'buffer'.
>
> Yes. But we're already here, due to the '(with-current-buffer buffer ...'.

OK, never mind.

> >> Instead, I've tried the appended patch. Could you, please, check? It
> >> fixes the problem for me.
> >
> > It doesn't work for me. With your patch, on my system, the original
> > recipe still exhibits the problem on the third invocation of
> > 'async-shell-command'.
> >
> > At the time when '(connection-local-value shell-file-name)' is invoked
> > in your patch, the current buffer is the output buffer (not the buffer
> > from which the user invoked 'async-shell-command'), and the default
> > directory is "/plink:xxx/" (not "c:/"), and the value returned is
> > "/bin/sh" (not the file name of "cmdproxy.exe").
>
> I hoped that the connection-local-value trick works. The
> default-directory of buffer is already changed; there is '(setq
> default-directory directory)' in time.
>
> However, connection-local-value does not work as I've hoped. It simply
> uses the recent (buffer-local) value, if default-directory isn't remote.
>
> So we must kill the local value(s) explicitly. The revised patch
> (appended) seems to work. Tested on my Windows 11 VM with your recipe.

Yes, that works.
Thanks!




Reply sent to Michael Albinus <michael.albinus <at> gmx.de>:
You have taken responsibility. (Thu, 27 Mar 2025 16:52:02 GMT) Full text and rfc822 format available.

Notification sent to Richard Copley <rcopley <at> gmail.com>:
bug acknowledged by developer. (Thu, 27 Mar 2025 16:52:02 GMT) Full text and rfc822 format available.

Message #49 received at 76888-done <at> debbugs.gnu.org (full text, mbox):

From: Michael Albinus <michael.albinus <at> gmx.de>
To: Richard Copley <rcopley <at> gmail.com>
Cc: Eli Zaretskii <eliz <at> gnu.org>, 76888-done <at> debbugs.gnu.org
Subject: Re: bug#76888: 31.0.50; start-process: Spawning child process:
 Invalid argument
Date: Thu, 27 Mar 2025 17:50:41 +0100
Version: 30.1

Richard Copley <rcopley <at> gmail.com> writes:

Hi Richard,

>> However, connection-local-value does not work as I've hoped. It simply
>> uses the recent (buffer-local) value, if default-directory isn't remote.
>>
>> So we must kill the local value(s) explicitly. The revised patch
>> (appended) seems to work. Tested on my Windows 11 VM with your recipe.
>
> Yes, that works.

Thanks for the feedback. I've pushed the patch to master.

> Thanks!

Best regards, Michael.




bug No longer marked as fixed in versions 30.1. Request was from Michael Albinus <michael.albinus <at> gmx.de> to control <at> debbugs.gnu.org. (Fri, 28 Mar 2025 12:33:01 GMT) Full text and rfc822 format available.

bug Marked as fixed in versions 31.1. Request was from Michael Albinus <michael.albinus <at> gmx.de> to control <at> debbugs.gnu.org. (Fri, 28 Mar 2025 12:33:01 GMT) Full text and rfc822 format available.

bug archived. Request was from Debbugs Internal Request <help-debbugs <at> gnu.org> to internal_control <at> debbugs.gnu.org. (Sat, 26 Apr 2025 11:24:14 GMT) Full text and rfc822 format available.

This bug report was last modified 55 days ago.

Previous Next


GNU bug tracking system
Copyright (C) 1999 Darren O. Benham, 1997,2003 nCipher Corporation Ltd, 1994-97 Ian Jackson.