Get-cimInstance

Greetings,
When I execute this code, I am getting an ‘Invalid query’ powershell error. Have I formatted the code correctly?

Get-CimInstance -ClassName cim_storagevolume -Filter “DriveLetter=‘C:’”

That particular class doesn’t appear to like filtering via the Get-CimInstance cmdlet. I’ll ask around to see if someone can explain exactly why.

In the meantime, I’ve found that this works.

(Get-CimInstance -ClassName Cim_StorageVolume).where({$PSItem.DriveLetter -eq 'C:'})

This also works

Get-CimInstance -ClassName cim_storagevolume | where driveletter -eq “C:”

I’m not able to get it to filter either, I did something similar to Will to get the results. Many ways to skin the PowerShell cat!

Get-CimInstance -ClassName CIM_StorageVolume | where driveletter -eq "C:"

ETA: Beat me by a min Simon! :wink:

Simon is pretty quick. :wink:

Surprisingly, Where-Object does appear to be faster in this instance too.

PS C:\WINDOWS\system32> Measure-Command {(Get-CimInstance -ClassName Cim_StorageVolume).where({$PSItem.DriveLetter -eq 'C:'})}
Measure-Command {Get-CimInstance -ClassName Cim_StorageVolume | Where-Object DriveLetter -EQ 'C:'}


Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 50
Ticks             : 504126
TotalDays         : 5.83479166666667E-07
TotalHours        : 1.40035E-05
TotalMinutes      : 0.00084021
TotalSeconds      : 0.0504126
TotalMilliseconds : 50.4126

Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 28
Ticks             : 284677
TotalDays         : 3.29487268518518E-07
TotalHours        : 7.90769444444444E-06
TotalMinutes      : 0.000474461666666667
TotalSeconds      : 0.0284677
TotalMilliseconds : 28.4677

Explanation per Mr. Richard Siddaway - who is way better at WMI things than I am:

The class

doesn’t appear to have a DriveLetter property so filter won’t work

Interestingly

PS> Get-CimInstance -ClassName cim_storagevolume | gm

TypeName: Microsoft.Management.Infrastructure.CimInstance#root/cimv2/Win32_Volume

Win32_volume derives from cim_storagevolume

PS> Get-WmiObject -Class Win32_volume | select -f 1 | select -expand __derivation

CIM_StorageVolume

CIM_StorageExtent

CIM_LogicalDevice

CIM_LogicalElement

CIM_ManagedSystemElement

Looks to me like the call to CIM_StorageVolume actually ends up calling Win32_Volume

CIM_StorageVolume doesn’t appear to have a driveletter property so you can’t filter on it BUT Win32_Volume does have a drive letter property which is what is displayed

I always recommend using the Win32-* classes rather than the CIM_ classes because the Win32_* classes were designed fro Windows whereas the CIM_* classes are generic

“doesn’t appear to have a DriveLetter property so filter won’t work”

Pardon my ignorance, if that is the case then why would the below commands return a value if their is not a property? Are they something else than properties?

Get-CimInstance -ClassName CIM_StorageVolume | select driveletter
Get-CimInstance -ClassName CIM_StorageVolume | where driveletter -eq "C:"

Notice the type being returned

PS> Get-CimInstance -ClassName CIM_StorageVolume | gm

TypeName: Microsoft.Management.Infrastructure.CimInstance#root/cimv2/Win32_Volume

When you’re calling CIM_StorageVolume your getting back Win32_Volume which is derived from CIM_StorageVolume. Win32_Volume HAS a DriveLetter property which is why your use of Select_Object and Where-Object works

So select/where can read what is in win32_volume but -filter is unable to?

What I think they are saying is that the CIM_ class call is actually fulfilled by making a call to Win32_Volume behind the scenes, but apparently after an attempt is made to apply the filter. When you query CIM_StorageVolume, and provide a filter it is failing because CIM_StorageVolume doesn’t have that DriveLetter property, and I’ll even go out on a limb a guess that it actually has no properties. The data returned has properties thanks to Win32_Volume. So, when I do a Get-CIMInstance Win32_Volume -Filter ‘DriveLetter = “E:”’, I get back info just for the E drive.

COM_StorageVolume does have properties

Get-CimClass Win32_Volume
and
Get-CimClass CIM_storagevolume

will show the difference

DriveLetters are a Windows thing which is probably why they aren’t present on CIM_SrorageVolume which is meant to be generic

Thanks all for your great insights on the CIM_StorageVolume and Win32_Volume…

Thanks Richard…by the way, your book ‘Powershell and WMI’ is a great resource. I’m really enjoying the book…