I am unable to figure this out. I am trying to build the Microchip XC32 PIC32 microcontroller GCC cross-compiler.
To try it yourself (this is how I got to my error I'm stuck on):
On Windows 10 or Windows 11: enable "developer mode" to allow symlinks. Windows key --> search for "Use developer features", click the button (now blue in the image below) to turn it on:

Clone my repo here: https://github.com/ElectricRCAircraftGuy/Microchip_XC32_Compiler
Install MSYS2, and open the MSYS2 UCRT64 shell. Optionally, follow my full MSYS2 setup instructions here.
Install dependencies via pacman, like this: copy and paste this whole blob all at once, into the terminal:
# ============= DO THIS TO INSTALL ALL DEPENDENCIES AT ONCE! ============= # UCRT64 if [ "$MSYSTEM" != "UCRT64" ]; then echo "ERROR: You must run this script in an MSYS2 ucrt64 terminal!" exit 1 fi package_list=( "mingw-w64-ucrt-x86_64-gcc" # specific version for MSYS2 ucrt64 "make" "binutils" "autoconf" "autogen" "bison" "dejagnu" "flex" "gawk" "gperf" "gzip" # "nsis" # generic; must be specific; hence the line below "mingw-w64-ucrt-x86_64-nsis" # specific version for MSYS2 ucrt64 "perl" "scons" "tcl" "texinfo" "wget" "zip" # "texlive" # generic; must be specific; hence the line below "mingw-w64-ucrt-x86_64-texlive-core" # specific version for MSYS2 ucrt64 # "texlive-extra-utils" # generic; must be specific; hence the line below "mingw-w64-ucrt-x86_64-texlive-extra-utils" # specific version for MSYS2 ucrt64 ) # Only install packages if tHey are NOT already installed. for package in "${package_list[@]}"; do if ! pacman -Qs $package > /dev/null; then echo -e "\n=== $package is not installed. Installing... ===" pacman -S --noconfirm $package else echo -e "\n=== $package is already installed. ===" fi done echo -e "\n=== Done installing packages! ===\n"Run the build script:
build-xc32-v4.35m.sh:time ./build-xc32-v4.35m.shAbout 20 minutes into it, it fails when compiling gcc, while configuring GMP. Note that to get clean errors you must modify the build script to use
-j1instead of-j$(nproc), here in the first line, or else you'll get multi-threaded output garbled on top of each other in the terminal:time make -j$(nproc) all-gcc \ STAGE1_LIBS="-lexpat -lmchp -Wl,-Bstatic -lstdc++ -Wl,-Bdynamic" \ CPPFLAGS="-I${hostinstalldir}/include -imacros host-defs.h" \ LDFLAGS=-L${hostinstalldir}/lib make install-gcc
Here's my failure. Configuring GMP seems to fail when it's looking for mp_limb_t. I've marked some notes/lines with <==== below:
checking for sysctl... no
checking for sysctlbyname... no
checking for times... no
checking for library containing clock_gettime... none required
checking for vsnprintf... yes
checking whether vsnprintf works... probably
configure: WARNING: cannot check for properly working vsnprintf when cross compiling, will assume it's ok
checking whether sscanf needs writable input... no
checking for struct pst_processor.psp_iticksperclktick... no
checking size of void *... 8
checking size of unsigned short... 2
checking size of unsigned... 4
checking size of unsigned long... 4
checking size of mp_limb_t... 0 <===== SIZE SHOULD BE 8
configure: error: Oops, mp_limb_t doesn't seem to work <===== ERROR
make: *** [Makefile:4701: configure-gmp] Error 1
real 3m27.324s
user 0m1.373s
sys 0m30.921s
Error: [gcc] failed to build!
real 3m27.510s
user 0m1.373s
Note that the build script runs perfectly to completion on Ubuntu 22.04, once I install the dependencies. It's Windows in MSYS2 that I am unable to get it to work in. Any help is greatly appreciated. This will help the PIC32 community build with GCC without having to buy a license from Microchip. The cross-compiler is GPL-licensed.
I've left a comment here too with a little more detail: https://github.com/JuliaLang/julia/issues/13206#issuecomment-1791823912. I no longer think symlinks are the issue, as I've tried copying the data directly over them with no change.
I have provided the autogenerated Makefile and gcc/gmp/config.log files here: https://github.com/ElectricRCAircraftGuy/Microchip_XC32_Compiler/tree/main/temp_debug_files. I've described them in the README.md file in that directory.
Been stuck on this for days. Could use some community support.
If anyone wants to try it in the MSYS2 MINGW64 environment instead, here is how to install those dependencies in that terminal:
# ============= DO THIS TO INSTALL ALL DEPENDENCIES AT ONCE! =============
# mingw64
if [ "$MSYSTEM" != "MINGW64" ]; then
echo "ERROR: You must run this script in an MSYS2 mingw64 terminal!"
exit 1
fi
package_list=(
"mingw-w64-x86_64-gcc" # specific version for MSYS2 mingw64
"make"
"binutils"
"autoconf"
"autogen"
"bison"
"dejagnu"
"flex"
"gawk"
"gperf"
"gzip"
# "nsis" # generic; must be specific; hence the line below
"mingw-w64-x86_64-nsis" # specific version for MSYS2 mingw64
"perl"
"scons"
"tcl"
"texinfo"
"wget"
"zip"
# "texlive" # generic; must be specific; hence the line below
"mingw-w64-x86_64-texlive-core" # specific version for MSYS2 mingw64
# "texlive-extra-utils" # generic; must be specific; hence the line below
"mingw-w64-x86_64-texlive-extra-utils" # specific version for MSYS2 mingw64
)
# Only install packages if tHey are NOT already installed.
for package in "${package_list[@]}"; do
if ! pacman -Qs $package > /dev/null; then
echo -e "\n=== $package is not installed. Installing... ==="
pacman -S --noconfirm $package
else
echo -e "\n=== $package is already installed. ==="
fi
done
echo -e "\n=== Done installing packages! ===\n"
Here's the autogenerated Makefile chunk of interest: C:\Users\gabriel\GS\dev\Microchip_XC32_Compiler\xc32-v4.35-src\pic32m-build\gcc\Makefile:
.PHONY: configure-gmp maybe-configure-gmp
maybe-configure-gmp:
maybe-configure-gmp: configure-gmp
configure-gmp:
@r=`${PWD_COMMAND}`; export r; \
s=`cd $(srcdir); ${PWD_COMMAND}`; export s; \
test ! -f $(HOST_SUBDIR)/gmp/Makefile || exit 0; \
$(SHELL) $(srcdir)/mkinstalldirs $(HOST_SUBDIR)/gmp; \
$(HOST_EXPORTS) \
echo Configuring in $(HOST_SUBDIR)/gmp; \
cd "$(HOST_SUBDIR)/gmp" || exit 1; \
case $(srcdir) in \
/* | [A-Za-z]:[\\/]*) topdir=$(srcdir) ;; \
*) topdir=`echo $(HOST_SUBDIR)/gmp/ | \
sed -e 's,\./,,g' -e 's,[^/]*/,../,g' `$(srcdir) ;; \
esac; \
module_srcdir=gmp; \
$(SHELL) \
$$s/$$module_srcdir/configure \
--srcdir=$${topdir}/$$module_srcdir \
$(HOST_CONFIGARGS) --build=${build_alias} --host=none-${host_vendor}-${host_os} \
--target=none-${host_vendor}-${host_os} --disable-shared LEX="touch lex.yy.c" \
|| exit 1
More leads to follow up on:
- https://www.google.com/search?q=bug%3A+msys2+doesnt+accept+absolute+paths+in+gcc&oq=bug%3A+msys2+doesnt+accept+absolute+paths+in+gcc&gs_lcrp=EgZjaHJvbWUyBggAEEUYOTIGCAEQRRg60gEJMTQ5NDNqMGo0qAIAsAIA&client=ms-android-google&sourceid=chrome-mobile&ie=UTF-8
- https://stackoverflow.com/a/39256699/4561887
- https://github.com/msys2/MINGW-packages/issues/6711#issuecomment-662982274
Note to self: I think a leading / in an include may be interpreted by MSYS GCC as C:\, which means that /c/my/path is seen as C:\c\my\path instead of as C:\my\path. This is contrary to how the MSYS terminal handles it, however. What a PITA. Study the sources above.
Convert to relative paths in the build script, using realpath --relative-to. Update my Stack Overflow answer on this too: https://stackoverflow.com/a/60157372/4561887
Solved. Big thanks to @HolyBlackCat for the comments and help, including this one, which got me started on finding the solution.
The fix: when compiling in an MSYS2 terminal in Windows, absolute
#includepaths are not allowed in C and C++!It turns out it's an MSYS2 gcc absolute path issue/bug. You cannot call the
configurescript with an absolute path since it uses the call path to generate a C include in the build process. And, absolute paths are broken in C or C++ includes in MSYS2 on Windows.So, change this part in
build-xc32-v4.35m.sh:To this. The only change is the creation and usage of
gcc_srcdir_RELATIVEto call theconfigurescript with a relative path instead of an absolute path!:What does not work
If you obtain these relative paths:
...and use them inside the build script like this:
...that just breaks the build. It doesn't work. The build system complains that all (or almost all) of those paths need to be absolute paths. The only fix you need is therefore the relative call to the
configurescript, like this:${gcc_srcdir_RELATIVE}/configure.Explanation of the
${gcc_srcdir_RELATIVE}/configurerelative path fix that worksQuick summary:
Calling the gcc
configurescript with a relative path causes that relative path to get inserted into the main gccMakefile, and then passed to the gmpconfigurescript, where it is injected into an autogeneratedconftest.cC file as an include statement. So, using an absolute path to call the gccconfigurescript puts an absolute path in the#includeinsideconftest.c, and using a relative path to call the gccconfigurescript puts a relative path into that#includestatement. In the MSYS2 UCRT64 gcc compiler, however, only relative paths are allowed, due to path conversion issues of theC:\(in a Windows-style path) or/c/(in a Unix-style path on Windows) part which pertains to the beginning of absolute paths.Details:
By doing this, the
srcdirvariable in the top of theMicrochip_XC32_Compiler/xc32-v4.35-src/pic32m-build/gcc/Makefilefile changes from this absolute path here:To this relative path here:
The following is in the same Makefile here. Notice that
topdir=$(srcdir), and--srcdir=$${topdir}/$$module_srcdiris passed to the call toconfigurefor thegmplibrary.Well, the gmp
configurescript uses that--srcdirparameter to set this include, as shown inMicrochip_XC32_Compiler/xc32-v4.35-src/pic32m-build/gcc/gmp/config.loghere:And, due to this not-a-bug bug, absolute Linux-style includes in MSYS2 gcc on Windows are not allowed:
So, by calling
${gcc_srcdir_RELATIVE}/configure, that include now looks like this in the autogeneratedconftest.cfile, and it works just fine!:Note that in the process of figuring this out, I tried testing Windows-style include paths like this:
...and I'm pretty sure those failed in gcc running in MSYS2 UCRT64 too.
I consider this absolute path problem in gcc in MSYS2 a definite bug. Update: it's not a bug. It was my user error and misunderstanding.
And now I'm on to my next bug in this very difficult build process. :/
References
From the bottom of my question:
See also
--build=,--host=, and--target=arguments toconfigurescripts.~directory in a Windows install of Git Bash - see in particular the section titled, "More details on paths in Git Bash and MSYS2"