93

When running a PowerShell script on a x64-bit OS platform, how can you determine in the script what version of PowerShell (32-bit or 64-bit) the script is running on?

Background
Both 32-bit and 64-bit versions of PowerShell are installed by default on a 64-bit platform such as Windows Server 2008. This can lead to difficulties when a PowerShell script is ran that must target a specific architecture (i.e. using 64-bit for a script for SharePoint 2010, in order to consume the 64-bit libraries).

Related question:

Community
  • 1
  • 1
Tangiest
  • 43,737
  • 24
  • 82
  • 113

5 Answers5

164

If you're shell is running on .NET 4.0 (PowerShell 3.0):

PS> [Environment]::Is64BitProcess
True
Shay Levy
  • 121,444
  • 32
  • 184
  • 206
  • Shay, thanks for sharing a very useful code snippet. +1 Unfortunately, I'm running on PowerShell v2, but I'm happy to accept this as the answer. – Tangiest Dec 21 '11 at 14:11
  • 3
    @ShayLevy No, definitely better to accept the one that's going to be applicable long into the future. In 2018, PowerShell 2 is a lot less relevant. – jpmc26 Apr 06 '18 at 20:22
87

To determine in your script what version of PowerShell you're using, you can use the following helper functions (courtesy of JaredPar's answer to an related question):

# Is this a Wow64 powershell host
function Test-Wow64() {
    return (Test-Win32) -and (test-path env:\PROCESSOR_ARCHITEW6432)
}

# Is this a 64 bit process
function Test-Win64() {
    return [IntPtr]::size -eq 8
}

# Is this a 32 bit process
function Test-Win32() {
    return [IntPtr]::size -eq 4
}

The above functions make use of the fact that the size of System.IntPtr is platform specific. It is 4 bytes on a 32-bit machine and 8 bytes on a 64-bit machine.

Note, it is worth noting that the locations of the 32-bit and 64-bit versions of Powershell are somewhat misleading. The 32-bit PowerShell is found at C:\Windows\SysWOW64\WindowsPowerShell\v1.0\powershell.exe, and the 64-bit PowerShell is at C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe, courtesy of this article.

Community
  • 1
  • 1
Tangiest
  • 43,737
  • 24
  • 82
  • 113
  • 2
    based on this answer I found that the most useful way in order to use the value in string is: `[IntPtr]::size * 8`. That will multiply 8 by the size giving you 32/64 depending on architecture, for example: `"$([IntPtr]::size * 8)bit"` – Sebastian Apr 12 '17 at 20:38
  • 2
    FYI, to launch a 64 bit process from a 32-bit command line, replace "System32" with "sysnative". C:\Windows\sysnative\WindowsPowerShell\v1.0\powershell.exe "[IntPtr]::size" – JohnP2 Mar 28 '18 at 14:06
15

You can use this as well. I tested it on PowerShell version 2.0 and 4.0.

$Arch = (Get-Process -Id $PID).StartInfo.EnvironmentVariables["PROCESSOR_ARCHITECTURE"];
if ($Arch -eq 'x86') {
    Write-Host -Object 'Running 32-bit PowerShell';
}
elseif ($Arch -eq 'amd64') {
    Write-Host -Object 'Running 64-bit PowerShell';
}

The value of $Arch will either be x86 or amd64.

EDIT:

The caveat is that Process.StartInfo.EnvironmentVariables always returns the environment of the current process, no matter which process you execute it on.

Ricky Han
  • 1,309
  • 1
  • 15
  • 25
  • 5
    `Process.StartInfo.EnvironmentVariables` always returns the environment of the current process, no matter which process you execute it on. Just use `$env:PROCESSOR_ARCHITECTURE` if you want to access the current environment - this is PowerShell 1.0 up AFAIK. Certainly 2.0. You can list the environment with `ls env:`. – JT. Mar 30 '15 at 04:34
  • $Is64bit = $env:PROCESSOR_ARCHITECTURE -eq 'AMD64' – Nathan Hartley Oct 24 '16 at 19:21
4

With Windows itself (and PowerShell) now supported on more architectures, like ARM64, it might not always be enough to check whether the application is 64-bit.

[Environment]::Is64BitProcess will also return True on Windows running on ARM64, so you cannot rely on it if what you really need to know is whether you're running on AMD64. To do this, on Windows you can use the following environment variable:

$Env:PROCESSOR_ARCHITECTURE, which returns values like AMD64, Arm64, or x86.

Knelis
  • 6,782
  • 2
  • 34
  • 54
2
Switch([IntPtr]::size * 8) {

32 { <#your 32 bit stuff#> ;break }

64 { <#your 64 bit stuff#> ;break }

}
Fluxnull
  • 31
  • 2