From 7cf0b1798bddad33876258d6715b363896252e40 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Mon, 11 May 2015 13:59:51 -0700 Subject: [PATCH] configure: Start adding MSVC support This commit starts to add MSVC support to the ./configure script to enable the build system to detect and build an MSVC target with the cl.exe compiler and toolchain. The primary change here is a large sanity check when an MSVC target is requested (and currently only `x86_64-pc-windows-msvc` is recognized). When building an MSVC target, the configure script either requires the `--msvc-root` argument or for `cl.exe` to be in `PATH`. It also requires that if in the path `cl.exe` is the 64-bit version of the compiler. Once detected the configure script will run the `vcvarsall.bat` script provided by Visual Studio to learn about the `INCLUDE` and `LIB` variables needed by the `cl.exe` compiler to run (the default include/lib paths for the compiler/linker). These variables are then reexported when running `make` to ensure that our own compiles are running the same toolchain. The purpose of this detection and environment variable scraping is to avoid requiring the build itself to be run inside of a `cmd.exe` shell but rather allow it to run in the currently expected MinGW/MSYS shell. --- configure | 65 +++++++++++++++++++++++++++++--- mk/cfg/x86_64-pc-windows-msvc.mk | 29 +++++++++++--- 2 files changed, 83 insertions(+), 11 deletions(-) diff --git a/configure b/configure index 4e150488224b..b57a2f0fbefe 100755 --- a/configure +++ b/configure @@ -1084,6 +1084,65 @@ do err "musl libc $CFG_MUSL_ROOT/lib/libc.a not found" fi ;; + + x86_64-*-msvc) + # Currently the build system is not configured to build jemalloc + # with MSVC, so we omit this optional dependency. + step_msg "targeting MSVC, disabling jemalloc" + CFG_DISABLE_JEMALLOC=1 + putvar CFG_DISABLE_JEMALLOC + + # There are some MSYS python builds which will auto-translate + # windows-style paths to MSYS-style paths in Python itself. + # Unfortunately this breaks LLVM's build system as somewhere along + # the line LLVM prints a path into a file from Python and then CMake + # later tries to interpret that path. If Python prints a MSYS path + # and CMake tries to use it as a Windows path, you're gonna have a + # Bad Time. + # + # Consequently here we try to detect when that happens and print an + # error if it does. + if $CFG_PYTHON -c 'import sys; print sys.argv[1]' `pwd` | grep '^/' + then + err "python is silently translating windows paths to MSYS paths \ + and the build will fail if this python is used.\n\n \ + Either an official python install must be used or an \ + alternative python package in MinGW must be used." + fi + + # MSVC requires cmake because that's how we're going to build LLVM + probe_need CFG_CMAKE cmake + + # Use the REG program to figure out where VS is installed + # We need to figure out where cl.exe and link.exe are, so we do some + # munging and some probing here. We also look for the default + # INCLUDE and LIB variables for MSVC so we can set those in the + # build system as well. + install=$(reg QUERY \ + 'HKLM\SOFTWARE\Wow6432Node\Microsoft\VisualStudio\12.0' \ + -v InstallDir) + need_ok "couldn't find visual studio install root" + CFG_MSVC_ROOT=$(echo "$install" | grep InstallDir | sed 's/.*REG_SZ[ ]*//') + CFG_MSVC_ROOT=$(dirname "$CFG_MSVC_ROOT") + CFG_MSVC_ROOT=$(dirname "$CFG_MSVC_ROOT") + CFG_MSVC_CL="${CFG_MSVC_ROOT}/VC/bin/amd64/cl.exe" + CFG_MSVC_LIB="${CFG_MSVC_ROOT}/VC/bin/amd64/lib.exe" + CFG_MSVC_LINK="${CFG_MSVC_ROOT}/VC/bin/amd64/link.exe" + + vcvarsall="${CFG_MSVC_ROOT}/VC/vcvarsall.bat" + CFG_MSVC_INCLUDE_PATH=$(cmd /c "\"$vcvarsall\" amd64 && cmd /c echo %INCLUDE%") + need_ok "failed to learn about MSVC's INCLUDE" + CFG_MSVC_LIB_PATH=$(cmd /c "\"$vcvarsall\" amd64 && cmd /c echo %LIB%") + need_ok "failed to learn about MSVC's LIB" + + putvar CFG_MSVC_ROOT + putvar CFG_MSVC_CL + putvar CFG_MSVC_LIB + putvar CFG_MSVC_LINK + putvar CFG_MSVC_INCLUDE_PATH + putvar CFG_MSVC_LIB_PATH + ;; + *) ;; esac @@ -1125,6 +1184,7 @@ do do make_dir $t/rt/stage$s make_dir $t/rt/jemalloc + make_dir $t/rt/compiler-rt for i in \ isaac sync test \ arch/i386 arch/x86_64 arch/arm arch/aarch64 arch/mips arch/powerpc @@ -1496,11 +1556,6 @@ do putvar $CFG_LLVM_INST_DIR done -# Munge any paths that appear in config.mk back to posix-y -cp config.tmp config.tmp.bak -sed -e 's@ \([a-zA-Z]\):[/\\]@ /\1/@g;' config.tmp -rm -f config.tmp.bak - msg copy_if_changed ${CFG_SRC_DIR}Makefile.in ./Makefile move_if_changed config.tmp config.mk diff --git a/mk/cfg/x86_64-pc-windows-msvc.mk b/mk/cfg/x86_64-pc-windows-msvc.mk index 4a77b658d46f..4e97ae3abe11 100644 --- a/mk/cfg/x86_64-pc-windows-msvc.mk +++ b/mk/cfg/x86_64-pc-windows-msvc.mk @@ -1,9 +1,9 @@ # x86_64-pc-windows-msvc configuration -CC_x86_64-pc-windows-msvc=cl -LINK_x86_64-pc-windows-msvc=link -CXX_x86_64-pc-windows-msvc=cl -CPP_x86_64-pc-windows-msvc=cl -AR_x86_64-pc-windows-msvc=llvm-ar +CC_x86_64-pc-windows-msvc="$(CFG_MSVC_CL)" -nologo +LINK_x86_64-pc-windows-msvc="$(CFG_MSVC_LINK)" -nologo +CXX_x86_64-pc-windows-msvc="$(CFG_MSVC_CL)" -nologo +CPP_x86_64-pc-windows-msvc="$(CFG_MSVC_CL)" -nologo +AR_x86_64-pc-windows-msvc="$(CFG_MSVC_LIB)" -nologo CFG_LIB_NAME_x86_64-pc-windows-msvc=$(1).dll CFG_STATIC_LIB_NAME_x86_64-pc-windows-msvc=$(1).lib CFG_LIB_GLOB_x86_64-pc-windows-msvc=$(1)-*.dll @@ -21,4 +21,21 @@ CFG_UNIXY_x86_64-pc-windows-msvc := CFG_LDPATH_x86_64-pc-windows-msvc := CFG_RUN_x86_64-pc-windows-msvc=$(2) CFG_RUN_TARG_x86_64-pc-windows-msvc=$(call CFG_RUN_x86_64-pc-windows-msvc,,$(2)) -CFG_GNU_TRIPLE_x86_64-pc-windows-msvc := x86_64-pc-windows-msvc +CFG_GNU_TRIPLE_x86_64-pc-windows-msvc := x86_64-pc-win32 + +# These two environment variables are scraped by the `./configure` script and +# are necessary for `cl.exe` to find standard headers (the INCLUDE variable) and +# for `link.exe` to find standard libraries (the LIB variable). +ifdef CFG_MSVC_INCLUDE_PATH +export INCLUDE := $(CFG_MSVC_INCLUDE_PATH) +endif +ifdef CFG_MSVC_LIB_PATH +export LIB := $(CFG_MSVC_LIB_PATH) +endif + +# Unfortunately `link.exe` is also a program in `/usr/bin` on MinGW installs, +# but it's not the one that we want. As a result we make sure that our detected +# `link.exe` shows up in PATH first. +ifdef CFG_MSVC_LINK +export PATH := $(CFG_MSVC_ROOT)/VC/bin/amd64:$(PATH) +endif