Reputation: 782
I'm trying to get a program using the <filesystem>
library running on Windows. I'm using MSYS2's (64 Bit) g++
.
#include <iostream>
#include <filesystem>
int main()
{
std::cout << "Hello World\n";
std::cout << "Current path is " << std::filesystem::current_path() << '\n';
}
I'm building it with
g++ -std=c++17 -Wall -Werror -Wextra main.cpp -lstdc++fs
I get no console output from the compiler. It silently generates an a.exe
. Executing the a.exe
just does nothing. There is no output and no errors. $?
(which is said to contain a program's return code) is 127
after running the program.
g++ -v
prints:
Using built-in specs.
COLLECT_GCC=C:\msys64\mingw64\bin\g++.exe
COLLECT_LTO_WRAPPER=C:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.1.0/lto-wrapper.exe
Target: x86_64-w64-mingw32
Configured with: ../gcc-9.1.0/configure --prefix=/mingw64 --with-local-prefix=/mingw64/local --build=x86_64-w64-mingw32 --host=x86_64-w64-mingw32 --target=x86_64-w64-mingw32 --with-native-system-header-dir=/mingw64/x86_64-w64-mingw32/include --libexecdir=/mingw64/lib --enable-bootstrap --with-arch=x86-64 --with-tune=generic --enable-languages=c,lto,c++,fortran,ada,objc,obj-c++ --enable-shared --enable-static --enable-libatomic --enable-threads=posix --enable-graphite --enable-fully-dynamic-string --enable-libstdcxx-filesystem-ts=yes --enable-libstdcxx-time=yes --disable-libstdcxx-pch --disable-libstdcxx-debug --disable-isl-version-check --enable-lto --enable-libgomp --disable-multilib --enable-checking=release --disable-rpath --disable-win32-registry --disable-nls --disable-werror --disable-symvers --enable-plugin --with-libiconv --with-system-zlib --with-gmp=/mingw64 --with-mpfr=/mingw64 --with-mpc=/mingw64 --with-isl=/mingw64 --with-pkgversion='Rev3, Built by MSYS2 project' --with-bugurl=https://sourceforge.net/projects/msys2 --with-gnu-as --with-gnu-ld
Thread model: posix
gcc version 9.1.0 (Rev3, Built by MSYS2 project)
What could be wrong?
(I get a Hello World
output and $?
is 0
, if I comment out the line with the std::filesystem::current_path()
call, so the compiler is working.)
Upvotes: 5
Views: 1657
Reputation: 782
Thanks to the commenters for dropping some ideas that finally led me to finding a solution.
If you have various MinGW-based tool sets installed (e.g. Cygwin, MinGW, MSYS, Git Bash), use the shell shipped with the set. Only carefully add the mingw*/bin
paths to PATH
; rather stick to the default PATH
setup of the respective shell. Click here, if you want to have convenient context menu shortcuts for the MSYS shell.
The problem was due to my weird local setup. Over the time I accumulated various versions of MinGW spread all over my computer. If I needed a utility, say diff
, I would google it and download something from somewhere (often sourceforge), install it to somewhere and add the bin
folder to my PATH
. This strategy worked for most things.
Toolsets I've installed over the time, including but not restricted to:
For some long time now I have mostly been using the Git Bash for everything. Lately I wanted to get the newest g++
compiler and stuff and found that MSYS2 has a package manager (pacman
) and pretty up to date packages so I installed it. And added it to the PATH
, then used the Git Bash.
However, each toolset coming with its own shell does its own PATH
magic and has its own MinGW copy. So I made my Git Bash use the MSYS2 g++
, but applications executed from the Git Bash still used DLLs from Git Bash's MinGW copy. I don't know for sure, but I think it's very probably that this was the problem.
For finding out, I used the following in the Git Bash:
# because of my PATH adjustment, I got the right g++
$ which g++
/c/msys64/mingw64/bin/g++
# my program uses DLLs from /mingw64, though
$ ldd a.exe
ntdll.dll => /c/Windows/SYSTEM32/ntdll.dll (0x77060000)
kernel32.dll => /c/Windows/system32/kernel32.dll (0x76e40000)
KERNELBASE.dll => /c/Windows/system32/KERNELBASE.dll (0x7fefcc00000)
msvcrt.dll => /c/Windows/system32/msvcrt.dll (0x7fefcf70000)
libgcc_s_seh-1.dll => /mingw64/bin/libgcc_s_seh-1.dll (0x61440000)
libwinpthread-1.dll => /mingw64/bin/libwinpthread-1.dll (0x64940000)
libstdc++-6.dll => /mingw64/bin/libstdc++-6.dll (0x6fc40000)
USER32.dll => /c/Windows/system32/USER32.dll (0x76f60000)
GDI32.dll => /c/Windows/system32/GDI32.dll (0x7fefddb0000)
LPK.dll => /c/Windows/system32/LPK.dll (0x7fefd540000)
USP10.dll => /c/Windows/system32/USP10.dll (0x7fefdbe0000)
# with cygpath I can find out that this is actually the Git Bash's installation
$ cygpath -w /mingw64
C:\Program Files\Git\mingw64
MSYS2 comes with its own shell, which sets up its PATH
correctly so the application works. In the MSYS2 shell:
$ ./a.exe
Hello World
Current path is "E:\\temporary\\2019_07_25-gpp_filesystem_test"
For the unlikely event someone got into a similar trouble and would like to use the MSYS2 shell more easily in various folders, check out this repo with a reg
script setting up convenient context menu shortcuts for the MSYS2 shell: https://github.com/njzhangyifei/msys2-mingw-shortcut-menus
Upvotes: 9