Skip to content

Instantly share code, notes, and snippets.

@rkitover
Last active May 9, 2024 20:08
Show Gist options
  • Save rkitover/f02f354543b3234fadc036a1529ea091 to your computer and use it in GitHub Desktop.
Save rkitover/f02f354543b3234fadc036a1529ea091 to your computer and use it in GitHub Desktop.
Load Visual Studio environment in MSYS2.
# Visual Studio Environemnt Loader
#
# For MSYS2/Cygwin/etc..
#
# Set the following in your ~/.bashrc:
#
# ENVIRONMENT CONFIGURATION:
#
# To enable static linking where possible:
#
# export VS_ENV_PREFER_STATIC=1
#
# MSVC CONFIGURATION:
#
# See vcvarsall.bat for possible values:
#
# export MSVC_ARCH=x64
#
# VCPKG CONFIGURATION:
#
# VCPKG_ROOT='C:\Users\bob\source\repos\vcpkg'
# VCPKG_TARGET_TRIPLET=x64-windows-static
#
vs_env_main() {
[ -z "$MSVC_ARCH" ] && set_msvc_arch
[ -z "$VSCMD_VER" ] && load_vs_environment
[ -n "$VCPKG_ROOT" ] && setup_vcpkg_environment
find_cccl || install_cccl && find_cccl
setup_cccl_environment
}
set_msvc_arch() {
# Arch defaults to x64.
export MSVC_ARCH=x64
if [ "$(uname -o)" = "Msys" ]; then
case "$MSYSTEM" in
MINGW32|CLANG32)
export MSVC_ARCH=x86
;;
esac
fi
}
load_vs_environment() {
OLDPWD=$PWD
cd 'c:/program files/microsoft visual studio/2022/community/vc/auxiliary/build'
msvc_env_raw=$(mktemp vs_env_rawXXXXX)
current_vars=$(mktemp vs_env_current_varsXXXXX)
msvc_env_vars=$(mktemp vs_env_varsXXXXX)
# Find the set of new vars from the MSVC environment that are
# not in the present environment.
env | sed 's/=.*//' | sort > "$current_vars"
cmd /c 'vcvarsall.bat '"$MSVC_ARCH"' & set' | \
grep -E '^[^=()]+=' > "$msvc_env_raw"
sed 's/=.*//' < "$msvc_env_raw" | sort > "$msvc_env_vars"
# Get only new vars from MSVC env but include PATH.
trie="PATH|$(comm -23 "$msvc_env_vars" "$current_vars" | \
paste -sd '|')"
# Make a map of Windows drives to converted paths.
drive_map=
if command -v cygpath >/dev/null; then
drive_map=$(mount | \
sed -n '/^\w: /{s/ .*//p}' | \
while read -r drive; do \
printf '%s\n' "s,$drive,$(cygpath "$drive")/,g"; \
done \
)
fi
# Load the MSVC environment with some edits.
eval "$(grep -E '^('"$trie"')=' "$msvc_env_raw" | sed -E '
# Quote var values in single quotes, because they use the
# Windows \ path-part separator.
s/=(.+)/='\''\1'\''/
# Setting PATH is special.
/^PATH=/{
# Map Windows drives to converted paths.
'"$drive_map"'
# Prepend existing PATH.
s/=/="\$PATH:"/
# Convert Windows ; path entry separator to the :
# UNIX path entry separator.
s/;/:/g
}
# Export the var.
s/^/export /
')"
# Remove duplicates from PATH.
# From: https://unix.stackexchange.com/a/40755/340856
export PATH="$(printf %s "$PATH" | awk -v RS=: '{
if (!arr[$0]++) {
printf("%s%s", !ln++ ? "" : ":", $0)
}
}')"
# Remove temp files.
rm -f "$msvc_env_raw" "$current_vars" "$msvc_env_vars"
cd "$OLDPWD"
unset OLDPWD msvc_env_raw current_vars msvc_env_vars \
trie drive_map
}
find_cccl() {
if command -v cccl >/dev/null; then
return 0
elif [ -x ~/.local/bin/cccl ]; then
export PATH="$PATH:~/.local/bin"
return 0
fi
return 1
}
install_cccl() {
OLDPWD=$PWD
mkdir -p /tmp/cccl-build
cd /tmp/cccl-build
curl -sLO "https://github.com/$(\
curl -sLo - 'https://github.com/swig/cccl/tags' | \
sed -nE 's/.*"([^"]+\.tar\.gz)".*/\1/p' | \
head -1 \
)"
tar zxf cccl*.tar.gz
rm cccl*.tar.gz
cd cccl*
mkdir -p ~/.local/bin
cp -f cccl ~/.local/bin
chmod +x ~/.local/bin/cccl
cd "$OLDPWD"
rm -rf /tmp/cccl-build
unset OLDPWD
}
setup_cccl_environment() {
for var in CC CXX LD; do
eval val="\$var"
case "$val" in
cccl|"cccl "*)
;;
*)
eval "$var"=cccl
;;
esac
unset val
done
case "$CCCL_OPTIONS" in
"/FS"|"* /FS"|"/FS *"|"* /FS *")
;;
*)
if [ -n "$CCCL_OPTIONS" ]; then
export CCCL_OPTIONS="$CCCL_OPTIONS /FS"
else
export CCCL_OPTIONS="/FS"
fi
;;
esac
}
setup_vcpkg_environment() {
if [ -z "$VCPKG_TARGET_TRIPLET" ]; then
export VCPKG_TARGET_TRIPLET="${MSVC_ARCH}-windows${VS_ENV_PREFER_STATIC+-static}"
fi
case "$INCLUDE" in
*[Vv][Cc][Pp][Kk][Gg]*)
;;
*)
export INCLUDE="$INCLUDE;$VCPKG_ROOT"'\installed\'"$VCPKG_TARGET_TRIPLET"'\include'
;;
esac
case "$LIB" in
*[Vv][Cc][Pp][Kk][Gg]*)
;;
*)
export LIB="$LIB;$VCPKG_ROOT"'\installed\'"$VCPKG_TARGET_TRIPLET"'\lib'
;;
esac
}
vs_env_main "$@"
# vim:sw=4 et ft=sh:
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment