VsDevShell.psm1
function Get-VsWherePath { [CmdletBinding()] param( ) $VsWhereCommand = Get-Command -Name vswhere -CommandType Application -ErrorAction SilentlyContinue if ($VsWhereCommand) { $VsWherePath = $VswhereCommand.Source } else { $VsWherePath = Join-Path ${Env:ProgramFiles(x86)} "Microsoft Visual Studio\Installer\vswhere.exe" } $VsWherePath } function Get-VsInstallPath { [CmdletBinding()] param( ) $VsWherePath = Get-VsWherePath if (-Not (Test-Path -Path $VsWherePath -PathType Leaf)) { throw [System.IO.FileNotFoundException] "vswhere.exe not found." } $VsInstallPath = & $VsWherePath "-latest" "-property" "installationPath" $VsInstallPath } function Get-VsDevCmdPath { [CmdletBinding()] param( [string] $VsInstallPath ) if ([string]::IsNullOrEmpty($VsInstallPath)) { $VsInstallPath = Get-VsInstallPath } $VsToolsPath = Join-Path $VsInstallPath "Common7/Tools" $VsDevCmdPath = Join-Path $VsToolsPath "VsDevCmd.bat" $VsDevCmdPath } function Get-VsDevEnv { [CmdletBinding()] param( [Parameter(Position=0)] [ValidateSet('x86','x64','arm','arm64')] [string] $Arch = "x64", [ValidateSet('x86','x64')] [string] $HostArch = "x64", [ValidateSet('Desktop','UWP')] [string] $AppPlatform = "Desktop", [string] $WinSdk, [switch] $NoExt, [switch] $NoLogo, [string] $VsInstallPath ) if ([string]::IsNullOrEmpty($VsInstallPath)) { $VsInstallPath = Get-VsInstallPath } if (-Not (Test-Path -Path $VsInstallPath -PathType Container)) { throw [System.IO.FileNotFoundException] "$VsInstallPath not found." } $VsDevCmdPath = Get-VsDevCmdPath -VsInstallPath $VsInstallPath if (-Not (Test-Path -Path $VsDevCmdPath -PathType Leaf)) { throw [System.IO.FileNotFoundException] "$VsDevCmdPath not found." } $Arch = $Arch.ToLower() $HostArch = $HostArch.ToLower() $VsCmdArgs = "-arch=$Arch" $VsCmdArgs += " -host_arch=$HostArch" if (-Not [string]::IsNullOrEmpty($WinSdk)) { $VsCmdArgs += " -winsdk=$WinSdk" } if ($NoExt) { $VsCmdArgs += " -no_ext" } if ($NoLogo) { $VsCmdArgs += " -no_logo" } $Env:VSCMD_SKIP_SENDTELEMETRY = "1" $Env:VSCMD_BANNER_SHELL_NAME_ALT = "$Arch Developer Shell" $processStartInfo = New-Object System.Diagnostics.ProcessStartInfo $processStartInfo.FileName = "${Env:COMSPEC}" $processStartInfo.Arguments = "/c `"`"$VsDevCmdPath`" $VsCmdArgs && set`"" $processStartInfo.WorkingDirectory = Split-Path $VsDevCmdPath $processStartInfo.RedirectStandardOutput = $true $processStartInfo.UseShellExecute = $false $processStartInfo.CreateNoWindow = $true $process = New-Object System.Diagnostics.Process $process.StartInfo = $processStartInfo $process.Start() | Out-Null $VsCmdOutput = $process.StandardOutput.ReadToEnd() $process.WaitForExit() $VsCmdOutput = $VsCmdOutput -split "`r`n" if ($process.ExitCode -ne 0) { throw "Failed to execute VsDevCmd.bat" } $PreEnv = [ordered]@{} (Get-ChildItem env:) | ForEach-Object { $PreEnv.Add($_.Name, $_.Value) } $VsDevEnv = [ordered]@{} foreach ($VsCmdLine in $VsCmdOutput) { if ($VsCmdLine.Contains('=')) { $Name, $Value = $VsCmdLine -split '=', 2 if ($PreEnv[$Name] -ne $Value) { $VsDevEnv.Add($Name, $Value) } } } $VsDevEnv } function Enter-VsDevShell { [CmdletBinding()] param( [Parameter(Position=0)] [ValidateSet('x86','x64','arm','arm64')] [string] $Arch = "x64", [ValidateSet('x86','x64')] [string] $HostArch = "x64", [ValidateSet('Desktop','UWP')] [string] $AppPlatform = "Desktop", [string] $WinSdk, [switch] $NoExt, [switch] $NoLogo, [string] $VsInstallPath ) $VsDevEnv = Get-VsDevEnv -Arch:$Arch -HostArch:$HostArch ` -AppPlatform:$AppPlatform -WinSdk:$WinSdk ` -NoExt:$NoExt -NoLogo:$NoLogo ` -VsInstallPath:$VsInstallPath $VsDevEnv.GetEnumerator() | ForEach-Object { [System.Environment]::SetEnvironmentVariable($_.Key, $_.Value) } } |