8

I am trying to determine if a target pc has atleast 2 GB of free space. Here is what I have so far:

@echo off
for /f "usebackq delims== tokens=2" %%x in (`wmic logicaldisk where "DeviceID='C:'" get FreeSpace /format:value`) do set "FreeSpace=%%x"
IF /i %FreeSpace% GTR "2147483648" (ECHO C Drive Has Enough Available Disk For Install %FreeSpace%) else (ECHO C Drive Is FULL %FreeSpace%)

It does not matter if I set 2 GB or change it to 200 GB it always says I have enough space even though this drive only has 90 GB...Please help if you can.

this question was what I based my above code on: Check free disk space using Batch commands

seems like it should work but it does not.

Sean Beegle
  • 81
  • 1
  • 2

4 Answers4

13

You have 2 problems with your code:

1) IF only does a numeric comparison if the string on both sides evaluates to a number. Your left side is numeric, but your right side has quotes, which forces the entire comparison to be done using string semantics. Numeric digits always sort higher than a quote character, so it always reports TRUE.

As austinian suggests in his answer, removing the quotes apparantly gives the correct answer in your case. But that is not the entire story! In reality it is checking if the free space is greater than or equal to 2147483647.

2) Windows batch (cmd.exe) numbers are limited to signed 32 bit precision, which equates to a max value of 2 GB -1 byte (2147483647). The IF statement has an odd (perhaps unfortunate) behavior that any number greater than 2147483647 is treated as equal to 2147483647. So you cannot use your technique to test free space for values greater than 2147483647.

See https://stackoverflow.com/q/9116365/1012053 for more information.

Described in the link's answer is a tecnique you can use to test large numbers. You must left pad both sides of the condition to the same width, and force a string comparison.

For example, The following will test if free space is >= 4294967296 (4 GB)

@echo off
setlocal
set "pad=000000000000000"
set "NeededSpace=%pad%4294967296"
for /f "delims== tokens=2" %%x in (
  'wmic logicaldisk where "DeviceID='C:'" get FreeSpace /format:value'
) do for %%y in (%%x) do set "FreeSpace=%pad%%%y"
if "%FreeSpace:~-15%" geq "%NeededSpace:~-15%" echo Drive has at least 4 GB free space.
dbenham
  • 661
3

Take out the "s from around the number, and the script almost works correctly. Using the "s forces a string comparison instead of a numerical comparison.

As dbenham notes, CMD only stores (and compares) numbers as 32-bit signed ints. Since we're checking for GB, we can reasonably ignore several of less significant digits. If we remove the last 6 digits, then we'll still have MB resolution while being able to detect correctly up to 2 Exabytes of free space. Also, as noted, we have to trim "Number of Digits Removed" + 1 from the WMIC result, due to an extra character at the end.

@ECHO off
SETLOCAL EnableDelayedExpansion
FOR /f "usebackq delims== tokens=2" %%x IN (`wmic logicaldisk where "DeviceID='C:'" get FreeSpace /format:value`) DO SET "FreeSpaceBig=%%x"
SET FreeSpace=!FreeSpaceBig:~0,-7!
IF %FreeSpace% GTR 2147 (ECHO C Drive Has Enough Available Disk For Install %FreeSpace%) else (ECHO C Drive Is FULL %FreeSpace%)
ENDLOCAL

NOTE: you really don't need the /i here either, since it's just for string comparison, and we're doing integer comparison. Also, we could use dir c:\ /-C | find "bytes free" instead of wmic logicaldisk where "DeviceID='C:'" get FreeSpace /format:value, if you want to avoid invoking WMI for this operation (which allows us to omit the EnableDelayedExpansion and use % instead of ! around FreeSpaceBig on line 4. Anyway, it's scripting, there's usually many ways to get the job done.

RELATED:

https://stackoverflow.com/questions/293780/free-space-in-a-cmd-shell https://stackoverflow.com/questions/9099138/save-values-batch-file/9099542#9099542 https://stackoverflow.com/questions/7769918/comparing-2-numbers-in-dos-batch-not-working

austinian
  • 1,729
  • 2
  • 15
  • 30
1

If you just need to check if the drive have enough free space (to install or copy something for example) you can try wmic query like this:

wmic LogicalDisk where "DeviceID='c:' and FreeSpace > 10737418240" get DeviceID 2>&1 ^ | find /i "c:" >nul || (echo not enough space&exit 1)

this will break batch file execution if there is less than 10Gb free on C:

anilech
  • 113
-2

Here's a different way of going about it... but it is not very precise.

This method uses string length operations against the "number of bytes free" listed under dir and the drive properties.

for /f "tokens=3" %%a in ('dir T:\') do (
 set bytesfree=%%a
)
ECHO %bytesfree%>x&FOR %%? IN (x) DO SET /A strlen=%%~z? - 2&del x
IF %strlen% LEQ 13 (

)

The specific example above determines if there is less than 10GB of free space on the T drive.

I just wanted to share this unorthodox way of going about it for those who don't like a lot of code.