git.exe 拉取错误:无法生成 git:无效的参数

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/48608113/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-19 13:03:32  来源:igfitidea点击:

git.exe pull error: cannot spawn git: Invalid argument

gittortoisegit

提问by toouur

I have an error exactly as it's on the picture.

我有一个和图片上一样的错误。

enter image description here

在此处输入图片说明

Tried various settings, googled, reinstalled. Git pull doesn't work in TortoiseGit, I can commit and push, though.

尝试了各种设置,谷歌搜索,重新安装。Git pull 在 TortoiseGit 中不起作用,不过我可以提交和推送。

I have ssh client in network tab. What else can I try?

我在网络选项卡中有 ssh 客户端。我还能尝试什么?

采纳答案by MrTux

Update:

更新:

Git for Windows 2.16.1(4) is out and that should fix this issue: https://github.com/git-for-windows/git/releases

Git for Windows 2.16.1(4) 已经发布,应该可以解决这个问题:https: //github.com/git-for-windows/git/releases



Old answer:

旧答案:

This is a known issue in Git for Windows 2.16.1(2) and 2.16.1(3): https://github.com/git-for-windows/git/issues/1481

这是适用于 Windows 2.16.1(2) 和 2.16.1(3) 的 Git 中的一个已知问题:https: //github.com/git-for-windows/git/issues/1481

Only workaround is to use Git for Windows 2.16.1 (Download) (or older; 2.16.0 has other critical issues: TortoiseGit revert failed - unable to revert local changes).

唯一的解决方法是将 Git 用于 Windows 2.16.1(下载)(或更早版本;2.16.0 有其他严重问题:TortoiseGit 恢复失败 - 无法恢复本地更改)。

Just for the notes, bugreport in TortoiseGit: https://gitlab.com/tortoisegit/tortoisegit/issues/3156

只是为了笔记,TortoiseGit 中的错误报告:https: //gitlab.com/tortoisegit/tortoisegit/issues/3156

PS: For Git for Windows >= 2.16 you need at least TortoiseGit 2.5.7 (cf. https://stackoverflow.com/a/48457419/3906760).

PS:对于 Windows >= 2.16 的 Git,您至少需要 TortoiseGit 2.5.7(参见https://stackoverflow.com/a/48457419/3906760)。

回答by u8942599

I rolled back to the version 2.16.0, the problem has disappeared. Git for Windows 2.16.0(2)

我回滚到2.16.0版本,问题消失了。 Windows 版 Git 2.16.0(2)

回答by VonC

git-for-windows/gitissue 1481mentioned in 2018 for Git 2.16 is formally fixed with Git 2.25 (Q1 2020).

git-for-windows/git2018 年针对 Git 2.16 提到的问题 1481已通过 Git 2.25(2020 年第一季度)正式修复。

A Work around has been introduced for an issue where a FD is left open when spawning a child process and is kept open in the child can interfere with the operation in the parent process on Windows.

已针对以下问题引入了变通办法:FD 在生成子进程时保持打开状态并在子进程中保持打开状态可能会干扰 Windows 上父进程中的操作。

See commit 3ba3720(02 Dec 2019), commit 4d0375c(30 Nov 2019), and commit ac33519, commit 9a780a3, commit c5a03b1, commit eea4a7f(22 Nov 2019) by Johannes Schindelin (dscho).
(Merged by Junio C Hamano -- gitster--in commit 55d607d, 10 Dec 2019)

提交3ba3720(2019年12月2日),提交4d0375c(二○一九年十一月三十○日),以及提交ac33519提交9a780a3提交c5a03b1提交eea4a7f(2019年11月22日)由约翰Schindelin( )dscho
(由Junio C gitsterHamano合并-- --commit 55d607d,2019 年 12 月 10 日)

mingw: work around incorrect standard handles

Signed-off-by: Johannes Schindelin

For some reason, when being called via TortoiseGit the standard handles, or at least what is returned by _get_osfhandle(0) for standard input, can take on the value (HANDLE)-2 (which is not a legal value, according to the documentation).

Even if this value is not documented anywhere, CreateProcess()seems to work fine without complaints if hStdInputset to this value.

In contrast, the upcoming code to restrict which file handles get inherited by spawned processes would result in ERROR_INVALID_PARAMETERwhen including such handle values in the list.

mingw:解决不正确的标准句柄

签字人:约翰内斯·辛德林

出于某种原因,当通过 TortoiseGit 调用时,标准句柄,或者至少是_get_osfhandle(0返回的标准输入,可以采用值 (HANDLE)-2(根据文档,这不是合法值)。

即使此值未在任何地方记录,CreateProcess()如果hStdInput设置为此值,似乎也可以正常工作而不会抱怨。

相比之下,即将发布的用于限制生成的进程继承哪些文件句柄的代码将导致在ERROR_INVALID_PARAMETER列表中包含此类句柄值时。

Note:

笔记:

mingw: restrict file handle inheritance only on Windows 7 and later

Signed-off-by: Johannes Schindelin

Turns out that it don't work so well on Vista, see git-for-windows/gitissue 1742 for details.

According to Old New Thing, it shouldwork on Windows Vista and later.

But apparently there are issues on Windows Vista when pipes are involved. Given that Windows Vista is past its end of life (official support ended on April 11th, 2017), let's not spend toomuch time on this issue and just disable the file handle inheritance restriction on any Windows version earlier than Windows 7. To help this, special-case the value (HANDLE)-2 returned by _get_osfhandle()and replace it with INVALID_HANDLE_VALUE,which will hopefully let the handle inheritance restriction work even when called from TortoiseGit.

mingw: 仅在 Windows 7 及更高版本上限制文件句柄继承

签字人:约翰内斯·辛德林

事实证明它在 Vista 上运行得不太好,有关详细信息,请参阅git-for-windows/git问题 1742

根据Old New Thing,它应该适用于 Windows Vista 及更高版本。

但是当涉及管道时,Windows Vista 上显然存在问题。鉴于 Windows Vista 已经过时(官方支持于 2017 年 4 月 11 日结束),让我们不要在这个问题上花太多时间,只需在 Windows 7 之前的任何 Windows 版本上禁用文件句柄继承限制即可。 , 特殊情况下返回的值 (HANDLE)-2_get_osfhandle()并将其替换为,INVALID_HANDLE_VALUE,即使从 TortoiseGit 调用,也有望让句柄继承限制起作用。

That is why there is a new configuration setting:

这就是为什么有一个新的配置设置

core.restrictinheritedhandles:

Windows-only: override whether spawned processes inherit only standard file handles (stdin, stdoutand stderr) or all handles.
Can be auto, trueor false. Defaults to auto, which means trueon Windows 7 and later, and falseon older Windows versions.

core.restrictinheritedhandles:

仅限 Windows:覆盖生成的进程是仅继承标准文件句柄(stdin,stdoutstderr)还是所有句柄。
可以auto,truefalse。默认为auto,这意味着true在 Windows 7 及更高false版本以及旧版 Windows 上。



mingw: spawned processes need to inherit only standard handles

Signed-off-by: Johannes Schindelin

By default, CreateProcess()does not inherit any open file handles, unless the bInheritHandlesparameter is set to TRUE. Which we do need to set because we need to pass in stdin/stdout/stderr to talk to the child processes.
Sadly, this means that all file handles (unless marked via O_NOINHERIT) are inherited.

This lead to problems in VFS for Git(the Virtual File System for Git), where a long-running read-object hook is used to hydrate missing objects, and depending on the circumstances, might only be called afterGit opened a file handle.

Ideally, we would not open files without O_NOINHERITunless reallynecessary (i.e. when we want to pass the opened file handle as standard handle into a child process), but apparently it is all-too-easy to introduce incorrect open()calls: this happened, and prevented updating a file after the read-object hook was started because the hook still held a handle on said file.

Happily, there is a solution: as described in the "Old New Thing" there is a way, starting with Windows Vista, that lets us define precisely which handles should be inherited by the child process.

And since we bumped the minimum Windows version for use with Git for Windows to Vista with v2.10.1 (i.e. a longtime ago), we can use this method. So let's do exactly that.

We need to make sure that the list of handles to inherit does not contain duplicates; Otherwise CreateProcessW()would fail with ERROR_INVALID_ARGUMENT.

While at it, stop setting errnoto ENOENTunless it really is the correct value.

Also, fall back to not limiting handle inheritance under certain error conditions (e.g. on Windows 7, which is a lot stricter in what handles you can specify to limit to).

mingw: 产生的进程只需要继承标准句柄

签字人:约翰内斯·辛德林

默认情况下,CreateProcess()不继承任何打开的文件句柄,除非bInheritHandles参数设置为TRUE。我们确实需要设置它,因为我们需要传入 stdin/stdout/stderr 来与子进程对话。
可悲的是,这意味着所有文件句柄(除非标记为 via O_NOINHERIT)都是继承的。

这会导致VFS for GitGit的虚拟文件系统)出现问题,其中使用长时间运行的读取对象挂钩来补充丢失的对象,并且根据情况,可能仅Git 打开文件句柄调用。

理想情况下,O_NOINHERIT除非真的有必要,否则我们不会打开文件(即,当我们想将打开的文件句柄作为标准句柄传递给子进程时),但显然引入不正确的open()调用太容易了:这发生了,并且阻止了在读取对象钩子启动后更新文件,因为钩子仍然持有所述文件的句柄。

令人高兴的是,有一个解决方案:如“旧的新事物”中所述,有一种方法可以从 Windows Vista 开始,让我们精确定义子进程应该继承哪些句柄。

并且由于我们将用于 Windows 的 Git 的最低 Windows 版本提升到带有 v2.10.1 的 Vista(即很久以前),我们可以使用这种方法。所以让我们这样做。

我们需要确保要继承的句柄列表不包含重复项;否则CreateProcessW()会失败ERROR_INVALID_ARGUMENT

在此期间,停止设置errno为,ENOENT除非它确实是正确的值。

此外,在某些错误条件下(例如,在 Windows 7 上,您可以指定要限制的句柄要严格得多)回退到不限制句柄继承。

And:

和:

mingw: do set errnocorrectly when trying to restrict handle inheritance

Reported-by: Johannes Sixt
Signed-off-by: Johannes Schindelin
Acked-by: Johannes Sixt

In 9a780a384de("mingw: spawned processes need to inherit only standard handles", 2019-11-22, Git v2.25.0 -- mergelisted in batch #5), we taught the Windows-specific part to restrict which file handles are passed on to the spawned processes.

Since this logic seemed to be a bit fragile across Windows versions (we stillsupport Windows Vista in Git for Windows, for example), a fall-back was added to try spawning the process again, this time without restricting which file handles are to be inherited by the spawned process.

In the common case (i.e. when the process could not be spawned for reasons otherthan the file handle inheritance), the fall-back attempt would still fail, of course.

Crucially, one thing we missed in that code path was to set errnoappropriately.

Let's fix that by making sure that errnois set correctly. It even appears that errnowas set in the wrongcase previously: CreateProcessW()returns non-zero upon success, but errnowas set only in the non-zero case.

However, when mingw_spawnvpe()wants to see whether the file in question is a script, it calls parse_interpreter(), which in turn tries to open()the file. Obviously, this call fails, and sets errnoto ENOENT, deep inside the call chain started from that test helper.

Instead, we force re-set errnoat the beginning of the function mingw_spawnve_fd(), which shouldbe safe given that callers of that function will want to look at errnoif -1 was returned. And if that errnois 0 ("No error"), regression tests like t0061.2 will kick in.

mingw:errno尝试限制句柄继承时正确设置

报告人:Johannes Sixt
签字人:Johannes Schindelin
认可:Johannes Sixt

9a780a384de(“ mingw:生成的进程只需要继承标准句柄”,2019 年 11 月 22 日,Git v2.25.0 --合并第 5 批中列出)中,我们教了 Windows 特定的部分来限制传递哪些文件句柄到生成的进程。

由于此逻辑在 Windows 版本中似乎有点脆弱(例如,我们仍然支持 Windows Vista 中的 Git for Windows),因此添加了一个后备以尝试再次生成该进程,这次不限制要使用哪些文件句柄由衍生进程继承。

在通常情况下(即当进程无法催生的原因其他不是文件句柄继承),掉回的尝试仍然失败,当然。

至关重要的是,我们在该代码路径中遗漏的一件事是errno适当设置。

让我们通过确保errno正确设置来解决这个问题。甚至似乎之前errno错误的情况下设置了:CreateProcessW()成功时返回非零,但errno仅在非零情况下设置。

但是,当mingw_spawnvpe()想要查看有问题的文件是否是脚本时,它会调用parse_interpreter(),而后者又会尝试访问open()该文件。显然,此调用失败,并设置errnoENOENT,在从该测试助手开始的调用链深处。

相反,我们errno在函数的开头强制重新设置,考虑到该函数的调用者想要查看是否返回 -1 mingw_spawnve_fd(),这应该是安全的errno。如果它errno是 0(“没有错误”),像 t0061.2 这样的回归测试就会开始。