Using WMI

This is a simple project to enumerate drives and their serial numbers.

The project is available here on GitHub.

Error reading form

It uses WMI, the only tricky part were the associator queries:

{ query constants }
            
CPartitionQuery = '''
                  ASSOCIATORS OF {Win32_DiskDrive.DeviceID="%s"} 
                  WHERE AssocClass = Win32_DiskDriveToDiskPartition
                  ''';

CDiskQuery      = '''
                  ASSOCIATORS OF {Win32_DiskPartition.DeviceID="%s"} 
                  WHERE AssocClass = Win32_LogicalDiskToPartition
                  ''';

{ core code }

// the WMI Locator
WmiServices := CreateOleObject('WbemScripting.SWbemLocator');

// the connected services object
var WmiServicesConnect := WmiServices.ConnectServer('localhost', 'root\CIMV2');

Drives := WmiServicesConnect.ExecQuery('SELECT * FROM Win32_DiskDrive');
DrivesEnum := IUnknown(Drives._NewEnum) as IEnumVariant;

while DrivesEnum.Next(1, Drive, DriveValue) = 0 do 
begin
    DeviceId       := Format('%s', [Drive.DeviceId]).Replace('\', '\\');
    PartitionQuery := Format(CPartitionQuery, [DeviceId]);

    Partitions     := WmiServicesConnect.ExecQuery(PartitionQuery);
    PartitionsEnum := IUnknown(Partitions._NewEnum) as IEnumVariant;

    while PartitionsEnum.Next(1, Partition, PartitionValue) = 0 do 
    begin
        DiskQuery := Format(CDiskQuery, [Partition.DeviceID]);

        Disks     := WmiServicesConnect.ExecQuery(DiskQuery);
        DisksEnum := IUnknown(Disks._NewEnum) as IEnumVariant;

        while DisksEnum.Next(1, Disk, DiskValue) = 0 do 
        begin
            var info := TDriveInfo.Create( 
                disk.DeviceId, 
                drive.Caption, 
                drive.DeviceId, 
                partition.DeviceId, 
                drive.SerialNumber);

            Result.Add(info);

            Disk := Unassigned;
        end;

        Partition := Unassigned;
    end;

    Drive := Unassigned;
end;

The first query associates each physical drive with its partitions, while the second associates those partitions with their logical drives.