How to get disk capacity and free space of remote computer

PowershellScriptingPowershell 2.0

Powershell Problem Overview


I have this one-liner:

get-WmiObject win32_logicaldisk -Computername remotecomputer

and the output is this:

DeviceID     : A:
DriveType    : 2
ProviderName :
FreeSpace    :
Size         :
VolumeName   :

DeviceID     : C:
DriveType    : 3
ProviderName :
FreeSpace    : 20116508672
Size         : 42842714112
VolumeName   :

DeviceID     : D:
DriveType    : 5
ProviderName :
FreeSpace    :
Size         :
VolumeName   :

How do I get Freespace and Size of DeviceID C:? I need to extract just these two values with no other informations. I have tried it with Select cmdlet, but with no effect.

Edit: I need to extract the numerical values only and store them in variables.

Powershell Solutions


Solution 1 - Powershell

Much simpler solution:

Get-PSDrive C | Select-Object Used,Free

and for remote computers (needs Powershell Remoting)

Invoke-Command -ComputerName SRV2 {Get-PSDrive C} | Select-Object PSComputerName,Used,Free

Solution 2 - Powershell

$disk = Get-WmiObject Win32_LogicalDisk -ComputerName remotecomputer -Filter "DeviceID='C:'" |
Select-Object Size,FreeSpace

$disk.Size
$disk.FreeSpace

To extract the values only and assign them to a variable:

$disk = Get-WmiObject Win32_LogicalDisk -ComputerName remotecomputer -Filter "DeviceID='C:'" |
Foreach-Object {$_.Size,$_.FreeSpace}

Solution 3 - Powershell

Just one command simple sweet and clean but this only works for local disks

Get-PSDrive

enter image description here

You could still use this command on a remote server by doing a Enter-PSSession -Computername ServerName and then run the Get-PSDrive it will pull the data as if you ran it from the server.

Solution 4 - Powershell

I created a PowerShell advanced function (script cmdlet) a while back that allows you to query multiple computers.

The code for the function is a little over 100 lines long, so you can find it here: PowerShell version of the df command

Check out the Usage section for examples. The following usage example queries a set of remote computers (input from the PowerShell pipeline) and displays the output in a table format with numeric values in human-readable form:

PS> $cred = Get-Credential -Credential 'example\administrator'
PS> 'db01','dc01','sp01' | Get-DiskFree -Credential $cred -Format | Format-Table -GroupBy Name -AutoSize

   Name: DB01

Name Vol Size  Used  Avail Use% FS   Type
---- --- ----  ----  ----- ---- --   ----
DB01 C:  39.9G 15.6G 24.3G   39 NTFS Local Fixed Disk
DB01 D:  4.1G  4.1G  0B     100 CDFS CD-ROM Disc


   Name: DC01

Name Vol Size  Used  Avail Use% FS   Type
---- --- ----  ----  ----- ---- --   ----
DC01 C:  39.9G 16.9G 23G     42 NTFS Local Fixed Disk
DC01 D:  3.3G  3.3G  0B     100 CDFS CD-ROM Disc
DC01 Z:  59.7G 16.3G 43.4G   27 NTFS Network Connection


   Name: SP01

Name Vol Size   Used   Avail Use% FS   Type
---- --- ----   ----   ----- ---- --   ----
SP01 C:  39.9G  20G    19.9G   50 NTFS Local Fixed Disk
SP01 D:  722.8M 722.8M 0B     100 UDF  CD-ROM Disc

Solution 5 - Powershell

Another way is casting a string to a WMI object:

$size = ([wmi]"\\remotecomputer\root\cimv2:Win32_logicalDisk.DeviceID='c:'").Size
$free = ([wmi]"\\remotecomputer\root\cimv2:Win32_logicalDisk.DeviceID='c:'").FreeSpace

Also you can divide the results by 1GB or 1MB if you want different units:

$disk = ([wmi]"\\remotecomputer\root\cimv2:Win32_logicalDisk.DeviceID='c:'")
"Remotecomputer C: has {0:#.0} GB free of {1:#.0} GB Total" -f ($disk.FreeSpace/1GB),($disk.Size/1GB) | write-output

Output is: Remotecomputer C: has 252.7 GB free of 298.0 GB Total

Solution 6 - Powershell

There are two issues I encountered with the other suggestions

    1) Drive mappings are not supported if you run the powershell under task scheduler
    2) You may get Access is denied errors errors trying to used "get-WmiObject" on remote computers (depending on your infrastructure setup, of course)

The alternative that doesn't suffer from these issues is to use GetDiskFreeSpaceEx with a UNC path:

function getDiskSpaceInfoUNC($p_UNCpath, $p_unit = 1tb, $p_format = '{0:N1}')
{
    # unit, one of --> 1kb, 1mb, 1gb, 1tb, 1pb
    $l_typeDefinition = @' 
        [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] 
        [return: MarshalAs(UnmanagedType.Bool)] 
        public static extern bool GetDiskFreeSpaceEx(string lpDirectoryName, 
            out ulong lpFreeBytesAvailable, 
            out ulong lpTotalNumberOfBytes, 
            out ulong lpTotalNumberOfFreeBytes); 
'@
    $l_type = Add-Type -MemberDefinition $l_typeDefinition -Name Win32Utils -Namespace GetDiskFreeSpaceEx -PassThru

    $freeBytesAvailable     = New-Object System.UInt64 # differs from totalNumberOfFreeBytes when per-user disk quotas are in place
    $totalNumberOfBytes     = New-Object System.UInt64
    $totalNumberOfFreeBytes = New-Object System.UInt64
         
    $l_result = $l_type::GetDiskFreeSpaceEx($p_UNCpath,([ref]$freeBytesAvailable),([ref]$totalNumberOfBytes),([ref]$totalNumberOfFreeBytes)) 

    $totalBytes     = if($l_result) { $totalNumberOfBytes    /$p_unit } else { '' }
    $totalFreeBytes = if($l_result) { $totalNumberOfFreeBytes/$p_unit } else { '' }
         
    New-Object PSObject -Property @{
        Success   = $l_result
        Path      = $p_UNCpath
        Total     = $p_format -f $totalBytes
        Free      = $p_format -f $totalFreeBytes
    } 
}

Solution 7 - Powershell

Get-PSDrive C | Select-Object @{ E={$_.Used/1GB}; L='Used' }, @{ E={$_.Free/1GB}; L='Free' }

Solution 8 - Powershell

Command-line:

powershell gwmi Win32_LogicalDisk -ComputerName remotecomputer -Filter "DriveType=3" ^|
select Name, FileSystem,FreeSpace,BlockSize,Size ^| % {$_.BlockSize=
(($_.FreeSpace)/($_.Size))*100;$_.FreeSpace=($_.FreeSpace/1GB);$_.Size=($_.Size/1GB);$_}
^| Format-Table Name, @{n='FS';e={$_.FileSystem}},@{n='Free, Gb';e={'{0:N2}'-f
$_.FreeSpace}}, @{n='Free,%';e={'{0:N2}'-f $_.BlockSize}},@{n='Capacity ,Gb';e={'{0:N3}'
-f $_.Size}} -AutoSize

Output:

Name FS   Free, Gb Free,% Capacity ,Gb

---- --   -------- ------ ------------

C:   NTFS 16,64    3,57   465,752

D:   NTFS 43,63    9,37   465,759

I:   NTFS 437,59   94,02  465,418

N:   NTFS 5,59     0,40   1 397,263

O:   NTFS 8,55     0,96   886,453

P:   NTFS 5,72     0,59   976,562

command-line:

wmic logicaldisk where DriveType="3" get caption, VolumeName, VolumeSerialNumber, Size, FileSystem, FreeSpace

out:

Caption  FileSystem  FreeSpace     Size           VolumeName  VolumeSerialNumber

C:       NTFS        17864343552   500096991232   S01         EC641C36

D:       NTFS        46842589184   500104687616   VM1         CAF2C258

I:       NTFS        469853536256  499738734592   V8          6267CDCC

N:       NTFS        5998840832    1500299264512  Vm-1500     003169D1

O:       NTFS        9182349312    951821143552   DT01        A8FC194C

P:       NTFS        6147043840    1048575144448  DT02        B80A0F40

command-line:

wmic logicaldisk where Caption="C:" get caption, VolumeName, VolumeSerialNumber, Size, FileSystem, FreeSpace

out:

Caption  FileSystem  FreeSpace    Size          VolumeName  VolumeSerialNumber

C:       NTFS        17864327168  500096991232  S01         EC641C36

command-line:

dir C:\ /A:DS | find "free"

out:
               4 Dir(s)  17 864 318 976 bytes free

dir C:\ /A:DS /-C | find "free"

out:
               4 Dir(s)     17864318976 bytes free

Solution 9 - Powershell

Just found Get-Volume command, which returns SizeRemaining, so something like (Get-Volume -DriveLetter C).SizeRemaining / (1e+9) can be used to see remained Gb for disk C. Seems works faster than Get-WmiObject Win32_LogicalDisk.

Solution 10 - Powershell

PS> Get-CimInstance -ComputerName bobPC win32_logicaldisk | where caption -eq "C:" | foreach-object {write " $($_.caption) $('{0:N2}' -f ($_.Size/1gb)) GB total, $('{0:N2}' -f ($_.FreeSpace/1gb)) GB free "}  
C: 117.99 GB total, 16.72 GB free 

PS> 

Solution 11 - Powershell

I know of psExec tools which you can download from here

There comes a psinfo.exe from the tools package. The basic usage is in the following manner in powershell/cmd.

enter image description here

However you could have a lot of options with it

Usage: psinfo [[\computer[,computer[,..] | @file [-u user [-p psswd]]] [-h] [-s] [-d] [-c [-t delimiter]] [filter]

\computer Perform the command on the remote computer or computers specified. If you omit the computer name the command runs on the local system, and if you specify a wildcard (\*), the command runs on all computers in the current domain.

@file	Run the command on each computer listed in the text file specified.
-u	Specifies optional user name for login to remote computer.
-p	Specifies optional password for user name. If you omit this you will be prompted to enter a hidden password.
-h	Show list of installed hotfixes.
-s	Show list of installed applications.
-d	Show disk volume information.
-c	Print in CSV format.
-t	The default delimiter for the -c option is a comma, but can be overriden with the specified character.

filter Psinfo will only show data for the field matching the filter. e.g. "psinfo service" lists only the service pack field.

Solution 12 - Powershell

On PowerShell:

"FreeSpace C:  " + [math]::Round((Get-Volume -DriveLetter C).SizeRemaining / 1Gb) + " GB"

Solution 13 - Powershell

I remote into the computer using Enter-PSsession pcName then I type Get-PSDrive

That will list all drives and space used and remaining. If you need to see all the info formated, pipe it to FL like this: **Get-PSdrive | FL ***

Solution 14 - Powershell

I created this simple function to help me. This makes my calls a lot easier to read that having inline an Get-WmiObject, Where-Object statements, etc.

function GetDiskSizeInfo($drive) {
    $diskReport = Get-WmiObject Win32_logicaldisk
    $drive = $diskReport | Where-Object { $_.DeviceID -eq $drive}

    $result = @{
        Size = $drive.Size
        FreeSpace = $drive.Freespace
    }
    return $result
}

$diskspace = GetDiskSizeInfo "C:"
write-host $diskspace.FreeSpace " " $diskspace.Size

Solution 15 - Powershell

In case you want to check multiple drive letters and/or filter between local and network drives, you can use PowerShell to take advantage of the Win32_LogicalDisk WMI class. Here's a quick example:

$localVolumes = Get-WMIObject win32_volume;

foreach ($vol in $localVolumes) {
  if ($vol.DriveLetter -ne $null ) {
    $d = $vol.DriveLetter[0];
    if ($vol.DriveType -eq 3) {
      Write-Host ("Drive " + $d + " is a Local Drive");
    }
    elseif ($vol.DriveType -eq 4) {
      Write-Host ("Drive" + $d + " is a Network Drive");
    }
    else {
      // ... and so on
    }

    $drive = Get-PSDrive $d;
    Write-Host ("Used space on drive " + $d + ": " + $drive.Used + " bytes. `r`n");
    Write-Host ("Free space on drive " + $d + ": " + $drive.Free + " bytes. `r`n");
  }
}

I used the above technique to create a Powershell script that checks all drives and send an e-mail alert whenever they go below a user-defined quota. You can get it from this post on my blog.

Solution 16 - Powershell

PowerShell Fun

Get-WmiObject win32_logicaldisk -Computername <ServerName> -Credential $(get-credential) | Select DeviceID,VolumeName,FreeSpace,Size | where {$_.DeviceID -eq "C:"}

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionculterView Question on Stackoverflow
Solution 1 - PowershellNull Pointers etc.View Answer on Stackoverflow
Solution 2 - PowershellShay LevyView Answer on Stackoverflow
Solution 3 - PowershellgrepitView Answer on Stackoverflow
Solution 4 - PowershellmweiselView Answer on Stackoverflow
Solution 5 - PowershellGreg BrayView Answer on Stackoverflow
Solution 6 - PowershellWarren StevensView Answer on Stackoverflow
Solution 7 - PowershellleorzzView Answer on Stackoverflow
Solution 8 - PowershellSTTRView Answer on Stackoverflow
Solution 9 - PowershellIlya FinkelsheynView Answer on Stackoverflow
Solution 10 - PowershellquuxView Answer on Stackoverflow
Solution 11 - PowershellHimanshu ChauhanView Answer on Stackoverflow
Solution 12 - Powershelllynx_74View Answer on Stackoverflow
Solution 13 - PowershellMichael DarkView Answer on Stackoverflow
Solution 14 - PowershellKaj BonfilsView Answer on Stackoverflow
Solution 15 - PowershellDarksealView Answer on Stackoverflow
Solution 16 - PowershellGhostWolfView Answer on Stackoverflow