Skip to content

Commit ca66d69

Browse files
dschoGit for Windows Build Agent
authored andcommitted
Add full mingw-w64-git (i.e. regular MSYS2 ecosystem) support (#5971)
Every once in a while, there are bug reports in Git for Windows' bug tracker that describe an issue running [inside MSYS2 proper](https://gitforwindows.org/install-inside-msys2-proper), totally ignoring the big, honking warning on top of [the page](https://gitforwindows.org/install-inside-msys2-proper) that spells out clearly that this is an unsupported use case. At the same time, we cannot easily deflect and say "just use MSYS2 directly" (and leave the "and stop pestering us" out). We cannot do that because there is only an _MSYS_ `git` package in MSYS2 (i.e. a Git that uses the quite slow POSIX emulation layer provided by the MSYS2 runtime), but no `mingw-w64-git` package (which would be equivalent in speed to Git for Windows). In msys2/MINGW-packages#26470, I am preparing to change that. As part of that PR, I noticed and fixed a couple of issues _in `git-for-windows/git` that prevented full support for `mingw-w64-git` in MSYS2, such as problems with CLANG64 and UCRT64. While at it, I simplified the entire setup to trust MSYS2's `MINGW_PREFIX` & related environment variables instead of hard-coding values like the installation prefix and what `MSYSTEM` to fall back on if it is unset.
2 parents bb6f1e1 + dfed74f commit ca66d69

File tree

6 files changed

+66
-114
lines changed

6 files changed

+66
-114
lines changed

compat/mingw.c

Lines changed: 7 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -3615,7 +3615,7 @@ int xwcstoutf(char *utf, const wchar_t *wcs, size_t utflen)
36153615
}
36163616

36173617
#ifdef ENSURE_MSYSTEM_IS_SET
3618-
#if !defined(RUNTIME_PREFIX) || !defined(HAVE_WPGMPTR)
3618+
#if !defined(RUNTIME_PREFIX) || !defined(HAVE_WPGMPTR) || !defined(MINGW_PREFIX)
36193619
static size_t append_system_bin_dirs(char *path UNUSED, size_t size UNUSED)
36203620
{
36213621
return 0;
@@ -3633,25 +3633,16 @@ static size_t append_system_bin_dirs(char *path, size_t size)
36333633
/* strip trailing `git.exe` */
36343634
len = slash - prefix;
36353635

3636-
/* strip trailing `cmd` or `mingw64\bin` or `mingw32\bin` or `bin` or `libexec\git-core` */
3637-
if (strip_suffix_mem(prefix, &len, "\\mingw64\\libexec\\git-core") ||
3638-
strip_suffix_mem(prefix, &len, "\\mingw64\\bin"))
3636+
/* strip trailing `cmd` or `<mingw-prefix>\bin` or `bin` or `libexec\git-core` */
3637+
if (strip_suffix_mem(prefix, &len, "\\" MINGW_PREFIX "\\libexec\\git-core") ||
3638+
strip_suffix_mem(prefix, &len, "\\" MINGW_PREFIX "\\bin"))
36393639
off += xsnprintf(path + off, size - off,
3640-
"%.*s\\mingw64\\bin;", (int)len, prefix);
3641-
else if (strip_suffix_mem(prefix, &len, "\\clangarm64\\libexec\\git-core") ||
3642-
strip_suffix_mem(prefix, &len, "\\clangarm64\\bin"))
3643-
off += xsnprintf(path + off, size - off,
3644-
"%.*s\\clangarm64\\bin;", (int)len, prefix);
3645-
else if (strip_suffix_mem(prefix, &len, "\\mingw32\\libexec\\git-core") ||
3646-
strip_suffix_mem(prefix, &len, "\\mingw32\\bin"))
3647-
off += xsnprintf(path + off, size - off,
3648-
"%.*s\\mingw32\\bin;", (int)len, prefix);
3640+
"%.*s\\" MINGW_PREFIX "\\bin;", (int)len, prefix);
36493641
else if (strip_suffix_mem(prefix, &len, "\\cmd") ||
36503642
strip_suffix_mem(prefix, &len, "\\bin") ||
36513643
strip_suffix_mem(prefix, &len, "\\libexec\\git-core"))
36523644
off += xsnprintf(path + off, size - off,
3653-
"%.*s\\mingw%d\\bin;", (int)len, prefix,
3654-
(int)(sizeof(void *) * 8));
3645+
"%.*s\\" MINGW_PREFIX "\\bin;", (int)len, prefix);
36553646
else
36563647
return 0;
36573648

@@ -3747,13 +3738,7 @@ static void setup_windows_environment(void)
37473738
char buf[32768];
37483739
size_t off = 0;
37493740

3750-
#if defined(__aarch64__) || defined(_M_ARM64) || defined(_M_ARM64EC)
3751-
setenv("MSYSTEM", "CLANGARM64", 1);
3752-
#elif defined(__MINGW64__) || defined(_M_AMD64)
3753-
setenv("MSYSTEM", "MINGW64", 1);
3754-
#else
3755-
setenv("MSYSTEM", "MINGW32", 1);
3756-
#endif
3741+
setenv("MSYSTEM", ENSURE_MSYSTEM_IS_SET, 1);
37573742

37583743
if (home)
37593744
off += xsnprintf(buf + off, sizeof(buf) - off,

config.mak.uname

Lines changed: 24 additions & 85 deletions
Original file line numberDiff line numberDiff line change
@@ -438,14 +438,8 @@ ifeq ($(uname_S),Windows)
438438
GIT_VERSION := $(GIT_VERSION).MSVC
439439
pathsep = ;
440440
# Assume that this is built in Git for Windows' SDK
441-
ifeq (MINGW32,$(MSYSTEM))
442-
prefix = /mingw32
443-
else
444-
ifeq (CLANGARM64,$(MSYSTEM))
445-
prefix = /clangarm64
446-
else
447-
prefix = /mingw64
448-
endif
441+
ifneq (,$(MSYSTEM))
442+
prefix = $(MINGW_PREFIX)
449443
endif
450444
# Prepend MSVC 64-bit tool-chain to PATH.
451445
#
@@ -499,7 +493,7 @@ ifeq ($(uname_S),Windows)
499493
NATIVE_CRLF = YesPlease
500494
DEFAULT_HELP_FORMAT = html
501495
SKIP_DASHED_BUILT_INS = YabbaDabbaDoo
502-
ifeq (/mingw64,$(subst 32,64,$(subst clangarm,mingw,$(prefix))))
496+
ifneq (,$(MINGW_PREFIX))
503497
# Move system config into top-level /etc/
504498
ETC_GITCONFIG = ../etc/gitconfig
505499
ETC_GITATTRIBUTES = ../etc/gitattributes
@@ -515,7 +509,9 @@ endif
515509
compat/win32/pthread.o compat/win32/syslog.o \
516510
compat/win32/trace2_win32_process_info.o \
517511
compat/win32/dirent.o compat/win32/fscache.o compat/win32/wsl.o
518-
COMPAT_CFLAGS = -D__USE_MINGW_ACCESS -DDETECT_MSYS_TTY -DENSURE_MSYSTEM_IS_SET -DNOGDI -DHAVE_STRING_H -Icompat -Icompat/regex -Icompat/win32 -DSTRIP_EXTENSION=\".exe\"
512+
COMPAT_CFLAGS = -D__USE_MINGW_ACCESS -DDETECT_MSYS_TTY \
513+
-DENSURE_MSYSTEM_IS_SET="\"$(MSYSTEM)\"" -DMINGW_PREFIX="\"$(patsubst /%,%,$(MINGW_PREFIX))\"" \
514+
-DNOGDI -DHAVE_STRING_H -Icompat -Icompat/regex -Icompat/win32 -DSTRIP_EXTENSION=\".exe\"
519515
BASIC_LDFLAGS = -IGNORE:4217 -IGNORE:4049 -NOLOGO
520516
# invalidcontinue.obj allows Git's source code to close the same file
521517
# handle twice, or to access the osfhandle of an already-closed stdout
@@ -733,26 +729,25 @@ ifeq ($(uname_S),MINGW)
733729
ifneq (,$(findstring -O,$(filter-out -O0 -Og,$(CFLAGS))))
734730
BASIC_LDFLAGS += -Wl,--dynamicbase
735731
endif
736-
ifeq (MINGW32,$(MSYSTEM))
737-
prefix = /mingw32
738-
HOST_CPU = i686
739-
BASIC_LDFLAGS += -Wl,--pic-executable,-e,_mainCRTStartup
740-
endif
741-
ifeq (MINGW64,$(MSYSTEM))
742-
prefix = /mingw64
743-
HOST_CPU = x86_64
744-
BASIC_LDFLAGS += -Wl,--pic-executable,-e,mainCRTStartup
745-
else ifeq (CLANGARM64,$(MSYSTEM))
746-
prefix = /clangarm64
747-
HOST_CPU = aarch64
748-
BASIC_LDFLAGS += -Wl,--pic-executable,-e,mainCRTStartup
749-
else
750-
COMPAT_CFLAGS += -D_USE_32BIT_TIME_T
751-
BASIC_LDFLAGS += -Wl,--large-address-aware
732+
ifneq (,$(MSYSTEM))
733+
ifeq ($(MINGW_PREFIX),$(filter-out /%,$(MINGW_PREFIX)))
734+
# Override if empty or does not start with a slash
735+
MINGW_PREFIX := /$(shell echo '$(MSYSTEM)' | tr A-Z a-z)
736+
endif
737+
prefix = $(MINGW_PREFIX)
738+
HOST_CPU = $(patsubst %-w64-mingw32,%,$(MINGW_CHOST))
739+
BASIC_LDFLAGS += -Wl,--pic-executable
740+
COMPAT_CFLAGS += -DDETECT_MSYS_TTY \
741+
-DENSURE_MSYSTEM_IS_SET="\"$(MSYSTEM)\"" \
742+
-DMINGW_PREFIX="\"$(patsubst /%,%,$(MINGW_PREFIX))\""
743+
ifeq (MINGW32,$(MSYSTEM))
744+
BASIC_LDFLAGS += -Wl,--large-address-aware
745+
endif
746+
# Move system config into top-level /etc/
747+
ETC_GITCONFIG = ../etc/gitconfig
748+
ETC_GITATTRIBUTES = ../etc/gitattributes
752749
endif
753-
CC = gcc
754-
COMPAT_CFLAGS += -D__USE_MINGW_ANSI_STDIO=0 -DDETECT_MSYS_TTY \
755-
-DENSURE_MSYSTEM_IS_SET -fstack-protector-strong
750+
COMPAT_CFLAGS += -D__USE_MINGW_ANSI_STDIO=0 -fstack-protector-strong
756751
EXTLIBS += -lntdll
757752
EXTRA_PROGRAMS += headless-git$X
758753
INSTALL = /bin/install
@@ -762,62 +757,6 @@ ifeq ($(uname_S),MINGW)
762757
USE_LIBPCRE = YesPlease
763758
USE_MIMALLOC = YesPlease
764759
NO_PYTHON =
765-
ifeq (/mingw64,$(subst 32,64,$(subst clangarm,mingw,$(prefix))))
766-
# Move system config into top-level /etc/
767-
ETC_GITCONFIG = ../etc/gitconfig
768-
ETC_GITATTRIBUTES = ../etc/gitattributes
769-
endif
770-
MINGW_PREFIX := $(subst /,,$(prefix))
771-
772-
DESTDIR_WINDOWS = $(shell cygpath -aw '$(DESTDIR_SQ)')
773-
DESTDIR_MIXED = $(shell cygpath -am '$(DESTDIR_SQ)')
774-
install-mingit-test-artifacts:
775-
install -m755 -d '$(DESTDIR_SQ)/usr/bin'
776-
printf '%s\n%s\n' >'$(DESTDIR_SQ)/usr/bin/perl' \
777-
"#!/mingw64/bin/busybox sh" \
778-
"exec \"$(shell cygpath -am /usr/bin/perl.exe)\" \"\$$@\""
779-
780-
install -m755 -d '$(DESTDIR_SQ)'
781-
printf '%s%s\n%s\n%s\n%s\n%s\n' >'$(DESTDIR_SQ)/init.bat' \
782-
"PATH=$(DESTDIR_WINDOWS)\\$(MINGW_PREFIX)\\bin;" \
783-
"C:\\WINDOWS;C:\\WINDOWS\\system32" \
784-
"@set GIT_TEST_INSTALLED=$(DESTDIR_MIXED)/$(MINGW_PREFIX)/bin" \
785-
"@`echo "$(DESTDIR_WINDOWS)" | sed 's/:.*/:/'`" \
786-
"@cd `echo "$(DESTDIR_WINDOWS)" | sed 's/^.://'`\\test-git\\t" \
787-
"@echo Now, run 'helper\\test-run-command testsuite'"
788-
789-
install -m755 -d '$(DESTDIR_SQ)/test-git'
790-
sed 's/^\(NO_PERL\|NO_PYTHON\)=.*/\1=YesPlease/' \
791-
<GIT-BUILD-OPTIONS >'$(DESTDIR_SQ)/test-git/GIT-BUILD-OPTIONS'
792-
793-
install -m755 -d '$(DESTDIR_SQ)/test-git/t/helper'
794-
install -m755 $(TEST_PROGRAMS) '$(DESTDIR_SQ)/test-git/t/helper'
795-
(cd t && $(TAR) cf - t[0-9][0-9][0-9][0-9] lib-diff) | \
796-
(cd '$(DESTDIR_SQ)/test-git/t' && $(TAR) xf -)
797-
install -m755 t/t556x_common t/*.sh '$(DESTDIR_SQ)/test-git/t'
798-
799-
install -m755 -d '$(DESTDIR_SQ)/test-git/templates'
800-
(cd templates && $(TAR) cf - blt) | \
801-
(cd '$(DESTDIR_SQ)/test-git/templates' && $(TAR) xf -)
802-
803-
# po/build/locale for t0200
804-
install -m755 -d '$(DESTDIR_SQ)/test-git/po/build/locale'
805-
(cd po/build/locale && $(TAR) cf - .) | \
806-
(cd '$(DESTDIR_SQ)/test-git/po/build/locale' && $(TAR) xf -)
807-
808-
# git-daemon.exe for t5802, git-http-backend.exe for t5560
809-
install -m755 -d '$(DESTDIR_SQ)/$(MINGW_PREFIX)/bin'
810-
install -m755 git-daemon.exe git-http-backend.exe \
811-
'$(DESTDIR_SQ)/$(MINGW_PREFIX)/bin'
812-
813-
# git-upload-archive (dashed) for t5000
814-
install -m755 -d '$(DESTDIR_SQ)/$(MINGW_PREFIX)/bin'
815-
install -m755 git-upload-archive.exe '$(DESTDIR_SQ)/$(MINGW_PREFIX)/bin'
816-
817-
# git-difftool--helper for t7800
818-
install -m755 -d '$(DESTDIR_SQ)/$(MINGW_PREFIX)/libexec/git-core'
819-
install -m755 git-difftool--helper \
820-
'$(DESTDIR_SQ)/$(MINGW_PREFIX)/libexec/git-core'
821760
endif
822761
ifeq ($(uname_S),QNX)
823762
COMPAT_CFLAGS += -DSA_RESTART=0

contrib/buildsystems/CMakeLists.txt

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -282,7 +282,14 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Windows")
282282
_CONSOLE DETECT_MSYS_TTY STRIP_EXTENSION=".exe" NO_SYMLINK_HEAD UNRELIABLE_FSTAT
283283
NOGDI OBJECT_CREATION_MODE=1 __USE_MINGW_ANSI_STDIO=0
284284
USE_NED_ALLOCATOR OVERRIDE_STRDUP MMAP_PREVENTS_DELETE USE_WIN32_MMAP
285-
HAVE_WPGMPTR ENSURE_MSYSTEM_IS_SET HAVE_RTLGENRANDOM)
285+
HAVE_WPGMPTR HAVE_RTLGENRANDOM)
286+
if(CMAKE_GENERATOR_PLATFORM STREQUAL "x64")
287+
add_compile_definitions(ENSURE_MSYSTEM_IS_SET="MINGW64" MINGW_PREFIX="mingw64")
288+
elseif(CMAKE_GENERATOR_PLATFORM STREQUAL "arm64")
289+
add_compile_definitions(ENSURE_MSYSTEM_IS_SET="CLANGARM64" MINGW_PREFIX="clangarm64")
290+
elseif(CMAKE_GENERATOR_PLATFORM STREQUAL "x86")
291+
add_compile_definitions(ENSURE_MSYSTEM_IS_SET="MINGW32" MINGW_PREFIX="mingw32")
292+
endif()
286293
list(APPEND compat_SOURCES
287294
compat/mingw.c
288295
compat/winansi.c

environment.c

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -91,16 +91,22 @@ int max_allowed_tree_depth =
9191
* the stack overflow can occur.
9292
*/
9393
512;
94-
#elif defined(GIT_WINDOWS_NATIVE) && defined(__clang__) && defined(__aarch64__)
94+
#elif defined(GIT_WINDOWS_NATIVE) && defined(__clang__)
9595
/*
96-
* Similar to Visual C, it seems that on Windows/ARM64 the clang-based
97-
* builds have a smaller stack space available. When running out of
98-
* that stack space, a `STATUS_STACK_OVERFLOW` is produced. When the
96+
* Similar to Visual C, it seems that clang-based builds on Windows
97+
* have a smaller stack space available. When running out of that
98+
* stack space, a `STATUS_STACK_OVERFLOW` is produced. When the
9999
* Git command was run from an MSYS2 Bash, this unfortunately results
100100
* in an exit code 127. Let's prevent that by lowering the maximal
101-
* tree depth; This value seems to be low enough.
101+
* tree depth; Unfortunately, it seems that the exact limit differs
102+
* for aarch64 vs x86_64, and the difference is too large to simply
103+
* use a single limit.
102104
*/
105+
#if defined(__aarch64__)
103106
1280;
107+
#else
108+
1152;
109+
#endif
104110
#else
105111
2048;
106112
#endif

meson.build

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1271,7 +1271,6 @@ elif host_machine.system() == 'windows'
12711271

12721272
libgit_c_args += [
12731273
'-DDETECT_MSYS_TTY',
1274-
'-DENSURE_MSYSTEM_IS_SET',
12751274
'-DNATIVE_CRLF',
12761275
'-DNOGDI',
12771276
'-DNO_POSIX_GOODIES',
@@ -1281,6 +1280,18 @@ elif host_machine.system() == 'windows'
12811280
'-D__USE_MINGW_ANSI_STDIO=0',
12821281
]
12831282

1283+
msystem = get_option('msystem')
1284+
if msystem != ''
1285+
mingw_prefix = get_option('mingw_prefix')
1286+
if mingw_prefix == ''
1287+
mingw_prefix = '/' + msystem.to_lower()
1288+
endif
1289+
libgit_c_args += [
1290+
'-DENSURE_MSYSTEM_IS_SET="' + msystem + '"',
1291+
'-DMINGW_PREFIX="' + mingw_prefix + '"'
1292+
]
1293+
endif
1294+
12841295
libgit_dependencies += compiler.find_library('ntdll')
12851296
libgit_include_directories += 'compat/win32'
12861297
if compiler.get_id() == 'msvc'

meson_options.txt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,10 @@ option('runtime_prefix', type: 'boolean', value: false,
2121
description: 'Resolve ancillary tooling and support files relative to the location of the runtime binary instead of hard-coding them into the binary.')
2222
option('sane_tool_path', type: 'array', value: [],
2323
description: 'An array of paths to pick up tools from in case the normal tools are broken or lacking.')
24+
option('msystem', type: 'string', value: '',
25+
description: 'Fall-back on Windows when MSYSTEM is not set.')
26+
option('mingw_prefix', type: 'string', value: '',
27+
description: 'Fall-back on Windows when MINGW_PREFIX is not set.')
2428

2529
# Build information compiled into Git and other parts like documentation.
2630
option('build_date', type: 'string', value: '',

0 commit comments

Comments
 (0)