Programmatically finding the VS2017 installation directory
Asked Answered
U

10

10

With previous versions of VS you could query the registry to determine the installation directory for VS:

HKLM\SOFTWARE\Wow6432Node\Microsoft\VisualStudio\14.0

However, this doesn't seem to work with the VS2017 RC. We have scripts that detect the latest installed VS and then do "the right thing", and so far I'm having issues plugging VS2017 into those systems.

Does anyone know how to programmatically determine the installation location for VS2017?

Uppish answered 12/12, 2016 at 17:37 Comment(1)
Applications are not supposed to use the Wow nodes. They only exist in x64 systems to allow x86 applications to work. Have you checked the HKLM\SOFTWARE\Microsoft\VisualStudio\15.0\Setup node? Anyway, the disk layout has changed a lot. Almost everything can be found in the `%PROGRAM FILES%\Microsoft Visual Studio 15.0` nowRuth
C
15

You can use vswhere tool to get VS2017 location.

Example:

@echo off

rem VS2017U2 contains vswhere.exe
if "%VSWHERE%"=="" set "VSWHERE=%ProgramFiles(x86)%\Microsoft Visual Studio\Installer\vswhere.exe"

for /f "usebackq tokens=*" %%i in (`"%VSWHERE%" -latest -products * -requires Microsoft.Component.MSBuild -property installationPath`) do (
  set InstallDir=%%i
)

if exist "%InstallDir%\MSBuild\15.0\Bin\MSBuild.exe" (
  "%InstallDir%\MSBuild\15.0\Bin\MSBuild.exe" %*
)

You can read more about it here: https://blogs.msdn.microsoft.com/heaths/2017/02/25/vswhere-available/

Compassionate answered 26/2, 2017 at 6:14 Comment(5)
I'm swapping to this one as the accepted answer as it provides me with an example of how I can script to get the path.Uppish
This didn't quite work for me - see the changes I needed to do in my answer.Andromache
This works if vswhere is on the path by default which it isn't. See @Srekel's answer below...Pericline
vswhere is a self contained exe so you can always copy it to where ever you wantUnhallow
"%VSWHERE%" -latest might not be the best idea if you have both VS2017 and VS2019 installed; you can try "%VSWHERE%" -version [15.0,16.0) though to pinpoint to VS2017Quadrangle
A
5

Visual Studio 2017 supports no-registry, side-by-side installations of all SKUs (Enterprise, Professional and Community).

MSI installlers can query via APIs described here: https://blogs.msdn.microsoft.com/heaths/2016/09/15/changes-to-visual-studio-15-setup/

Examples are here:

Astrodynamics answered 12/12, 2016 at 18:0 Comment(1)
I figured it was some kind of side-by-side thing - thanks for the links!Uppish
A
1

KindDragon's solution didn't quite work for me due to batch's "delayed expansion" "feature". (WAT)

Here is my code, compatible with VS 2017 15.2 (for the vswhere.exe installation)

SETLOCAL EnableDelayedExpansion

if not exist "%ProgramFiles(x86)%\Microsoft Visual Studio\Installer\vswhere.exe" (
  echo "WARNING: You need VS 2017 version 15.2 or later (for vswhere.exe)"
)

for /f "usebackq tokens=*" %%i in (`"%ProgramFiles(x86)%\Microsoft Visual Studio\Installer\vswhere.exe" -latest -products * -requires Microsoft.Component.MSBuild -property installationPath`) do (
  set InstallDir=%%i
)

if exist "!InstallDir!\VC\Auxiliary\Build\vcvars64.bat" (
  call "!InstallDir!\VC\Auxiliary\Build\vcvars64.bat"
) else (
  echo "Could not find !InstallDir!\VC\Auxiliary\Build\vcvars64.bat"
)

Especially note usage of SETLOCAL EnableDelayedExpansion and !InstallDir!

Andromache answered 2/6, 2017 at 7:35 Comment(4)
I don't see how delayed expansion factors in to KindDragon's solution - it would only be relevant if the "set" and "get" of the environment variable were nested within a single statement... as it stands his solution works for meUppish
I dunno man. I pasted it into my batch file and it didn't work, seemingly because it didn't expand the InstallDir variable at runtime. Then I used EnabledDelayedExpansion and it worked for me. I abhor batch files and wasn't too keen on understanding what went wrong and am happy to just have found a solution :D Posted it in hopes that it might help someone else.Andromache
This snippet actually works because it doesn't presume vswhere is on the path. For those wondering about the delayed expansion, all it does is enable expansion of variables using the !somevar! syntax within looping and conditional blocks. The currently accepted answer by @Compassionate doesn't use delayed expansion so I presume @Andromache is referring to his own construct not working without it.Pericline
IIRC, the problem arose when trying to actually use the InstallDir variable. Without delayed expansions, using it with the traditional % lookup doesn't work because then it has the value it has at the beginning of the batch file - i.e. nothing.Andromache
H
1

Well, vswhere.exe doesn't really supply more than the Visual Studio edition installation path. Here's my .profile file Interix snippet from 2008 doing the same with a minor update (shell script):

if [[ -n $PROCESSOR_ARCHITEW6432 || $PROCESSOR_ARCHITECTURE != "x86" ]]; then
  hkeybase='HKLM\SOFTWARE\Wow6432Node\Microsoft\'
else
  hkeybase='HKLM\SOFTWARE\Microsoft\'
fi
for vsver in "15.0" "14.0" "12.0" "11.0" "10.0" "9.0" "8.0"; do
  _vsinstalldir=$(reg.exe query ${hkeybase}'VisualStudio\SxS\VS7' -v $vsver 2>/dev/null \
   | sed -n 's|.*REG_SZ *\([ [:print:]]*\).*|\1|p' | sed 's|\\|/|g')
if [[ -n $_vsinstalldir ]]; then break; fi
done; unset vsver

That's enumerating Visual Studio installations favouring the latest in registry key

HKLM\SOFTWARE\Microsoft\VisualStudio\SxS\VS7

Still working for Visual Studio 2017. Would be easy to translate to cmd syntax. To query the registry is simpler and doesn't require vswhere.exe in your path, thus favourable IMO.

Now finding the current Visual C++ instance and the SDKs is another task entirely. :D

Common output in case you wonder:

C:/Program Files (x86)/Microsoft Visual Studio/2017/Enterprise/
Huntington answered 15/9, 2017 at 14:14 Comment(0)
R
1

I had a devil of time trying to modify Srekel's answer to search for only VS2017. Note: If you put the "for" statement below inside an "if" block it will wreck the escape characters and won't work.

SETLOCAL EnableDelayedExpansion

if not exist "%ProgramFiles(x86)%\Microsoft Visual Studio\Installer\vswhere.exe" (
  echo "WARNING: You need VS 2017 version 15.2 or later (for vswhere.exe)"
)

set vswherestr=^"!ProgramFiles(x86)!\Microsoft Visual Studio\Installer\vswhere.exe^" -version [15.0,16.0^^) -products * -requires Microsoft.Component.MSBuild -property installationPath
for /f "usebackq tokens=*" %%i in (`!vswherestr!`) do (  
  set BUILDVCTOOLS=%%i\Common7\Tools
  echo BUILDVCTOOLS: !BUILDVCTOOLS!
  if not exist !BUILDVCTOOLS!\VsDevCmd.bat (
    echo Error: Cannot find VS2017 Build Tools
    goto :buildfailed
  )
  call "!BUILDVCTOOLS!\VsDevCmd.bat"
)    
Rainband answered 26/10, 2018 at 12:51 Comment(0)
A
0

May I recommend my package get-vs2017-path it uses only built-in Windows tools (and although it's built as an NPM package, it has no dependencies, and the tools folder works standalone)

Archidiaconal answered 17/2, 2017 at 17:27 Comment(0)
P
0

See following answer in here:

https://mcmap.net/q/190274/-reliable-way-to-find-the-location-devenv-exe-of-visual-studio-2017

You can use either command line tool for querying Visual studio location, but I also provide programmatic way to query Visual Studio location. Code is based upon vswhere source code, but simplified.

Pontias answered 14/5, 2019 at 19:35 Comment(0)
U
0

We have only 3 Visual Studio editions.

  • \Community
  • \Professional
  • \Enterprise

As such we can simplify everything a bit.
Here some tested CMD script.

@SET env_all_vs2017_root=%ProgramFiles(x86)%\Microsoft Visual Studio\2017
@SET env_vs2017_path="%env_all_vs2017_root%\Professional"
@IF NOT EXIST %env_vs2017_path%  SET env_vs2017_path="%env_all_vs2017_root%\Community"
@IF NOT EXIST %env_vs2017_path%  SET env_vs2017_path="%env_all_vs2017_root%\Enterprise"
@REM Let's fail laudly
@IF NOT EXIST %env_vs2017_path%  SET "env_vs2017_path=Visual Studio 2017 install path was not found by %~nx0"

@REM  You may want to remove quotes
@SET unquoted=%env_vs2017_path:"=%


@REM  And now let's see the result and PAUSE

@ECHO VS 2017 install path is
@ECHO %unquoted%

@PAUSE
Unmentionable answered 6/9, 2019 at 8:48 Comment(0)
C
-2

You can use this PowerShell snippet for finding the VS2017 installation directory:

$vssetup_path = "$([Environment]::GetFolderPath("MyDocuments"))\WindowsPowerShell\Modules\VSSetup"
if (-not (Test-Path $vssetup_path -pathType container))
{
    iwr https://github.com/Microsoft/vssetup.powershell/releases/download/1.0.36-rc/VSSetup.zip -OutFile "$env:TEMP\VSSetup.zip"
    Expand-Archive "$env:TEMP\VSSetup.zip" $vssetup_path
}
$vs2017 = Get-VSSetupInstance -All | Select-VSSetupInstance -Require 'Microsoft.VisualStudio.Workload.NativeDesktop' -Version '[15.0,16.0)' -Latest
"Installation Path: " + $vs2017.InstallationPath
#`vsdevcmd.bat -arch=x86` or `vsdevcmd.bat -arch=amd64` can be used to setup path's to VC++ compiler
"VsDevCmd.bat Path: " + $vs2017.InstallationPath + "\Common7\Tools\VsDevCmd.bat"
Compassionate answered 31/1, 2017 at 22:34 Comment(1)
Hey, you tried to sneak the module into my system 😜. Anyway it failed on my system... (-not (Test-Path $vssetup_path -pathType container)) -eq 0 so the module did not installArchidiaconal
K
-3

I use powershell like KindDragon suggested

$Is64bitOs = $env:PROCESSOR_ARCHITEW6432 -eq 'AMD64';
if ($Is64bitOs){
    $registryPath = "Registry::HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\VisualStudio\14.0";
}
else {
    $registryPath = "Registry::HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\14.0";
}

$VSInstallDir = (Get-ItemProperty -Path Registry::HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\VisualStudio\14.0 -Name ShellFolder).ShellFolder;
Known answered 17/2, 2017 at 18:19 Comment(3)
It's path to VS2015, not 2017Compassionate
I'm not sure about the new VS2017 version, but possibly change 14.0 to 15.0?Known
No, VS2017 don't use registryCompassionate

© 2022 - 2024 — McMap. All rights reserved.