@@ -7,9 +7,23 @@ import (
7
7
"fmt"
8
8
"strconv"
9
9
10
+ "github.com/go-ole/go-ole"
10
11
"github.com/microsoft/wmi/pkg/base/query"
11
12
"github.com/microsoft/wmi/pkg/errors"
12
13
"github.com/microsoft/wmi/server2019/root/microsoft/windows/storage"
14
+ "k8s.io/klog/v2"
15
+ )
16
+
17
+ const (
18
+ FileSystemUnknown = 0
19
+ )
20
+
21
+ var (
22
+ VolumeSelectorListForFileSystemType = []string {"FileSystemType" }
23
+ VolumeSelectorListForStats = []string {"UniqueId" , "SizeRemaining" , "Size" }
24
+ VolumeSelectorListUniqueID = []string {"UniqueId" }
25
+
26
+ PartitionSelectorListObjectID = []string {"ObjectId" }
13
27
)
14
28
15
29
// QueryVolumeByUniqueID retrieves a specific volume by its unique identifier,
@@ -78,6 +92,68 @@ func ListVolumes(selectorList []string) ([]*storage.MSFT_Volume, error) {
78
92
return volumes , nil
79
93
}
80
94
95
+ // FormatVolume formats the specified volume.
96
+ //
97
+ // Refer to https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/format-msft-volume
98
+ // for the WMI method definition.
99
+ func FormatVolume (volume * storage.MSFT_Volume , params ... interface {}) (int , error ) {
100
+ result , err := volume .InvokeMethodWithReturn ("Format" , params ... )
101
+ return int (result ), err
102
+ }
103
+
104
+ // FlushVolume flushes the cached data in the volume's file system to disk.
105
+ //
106
+ // Refer to https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/msft-volume-flush
107
+ // for the WMI method definition.
108
+ func FlushVolume (volume * storage.MSFT_Volume ) (int , error ) {
109
+ result , err := volume .Flush ()
110
+ return int (result ), err
111
+ }
112
+
113
+ // GetVolumeUniqueID returns the unique ID (object ID) of a volume.
114
+ func GetVolumeUniqueID (volume * storage.MSFT_Volume ) (string , error ) {
115
+ return volume .GetPropertyUniqueId ()
116
+ }
117
+
118
+ // GetVolumeFileSystemType returns the file system type of a volume.
119
+ func GetVolumeFileSystemType (volume * storage.MSFT_Volume ) (int32 , error ) {
120
+ fsType , err := volume .GetProperty ("FileSystemType" )
121
+ if err != nil {
122
+ return 0 , err
123
+ }
124
+ return fsType .(int32 ), nil
125
+ }
126
+
127
+ // GetVolumeSize returns the size of a volume.
128
+ func GetVolumeSize (volume * storage.MSFT_Volume ) (int64 , error ) {
129
+ volumeSizeVal , err := volume .GetProperty ("Size" )
130
+ if err != nil {
131
+ return - 1 , err
132
+ }
133
+
134
+ volumeSize , err := strconv .ParseInt (volumeSizeVal .(string ), 10 , 64 )
135
+ if err != nil {
136
+ return - 1 , err
137
+ }
138
+
139
+ return volumeSize , err
140
+ }
141
+
142
+ // GetVolumeSizeRemaining returns the remaining size of a volume.
143
+ func GetVolumeSizeRemaining (volume * storage.MSFT_Volume ) (int64 , error ) {
144
+ volumeSizeRemainingVal , err := volume .GetProperty ("SizeRemaining" )
145
+ if err != nil {
146
+ return - 1 , err
147
+ }
148
+
149
+ volumeSizeRemaining , err := strconv .ParseInt (volumeSizeRemainingVal .(string ), 10 , 64 )
150
+ if err != nil {
151
+ return - 1 , err
152
+ }
153
+
154
+ return volumeSizeRemaining , err
155
+ }
156
+
81
157
// ListPartitionsOnDisk retrieves all partitions or a partition with the specified number on a disk.
82
158
//
83
159
// The equivalent WMI query is:
@@ -245,3 +321,78 @@ func GetPartitionDiskNumber(part *storage.MSFT_Partition) (uint32, error) {
245
321
246
322
return uint32 (diskNumber .(int32 )), nil
247
323
}
324
+
325
+ // SetPartitionState takes a partition online or offline.
326
+ //
327
+ // Refer to https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/msft-partition-online and
328
+ // https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/msft-partition-offline
329
+ // for the WMI method definition.
330
+ func SetPartitionState (part * storage.MSFT_Partition , online bool ) (int , string , error ) {
331
+ method := "Offline"
332
+ if online {
333
+ method = "Online"
334
+ }
335
+
336
+ var status string
337
+ result , err := part .InvokeMethodWithReturn (method , & status )
338
+ return int (result ), status , err
339
+ }
340
+
341
+ // GetPartitionSupportedSize retrieves the minimum and maximum sizes that the partition can be resized to using the ResizePartition method.
342
+ //
343
+ // Refer to https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/msft-partition-getsupportedsizes
344
+ // for the WMI method definition.
345
+ func GetPartitionSupportedSize (part * storage.MSFT_Partition ) (result int , sizeMin , sizeMax int64 , status string , err error ) {
346
+ sizeMin = - 1
347
+ sizeMax = - 1
348
+
349
+ var sizeMinVar , sizeMaxVar ole.VARIANT
350
+ invokeResult , err := part .InvokeMethodWithReturn ("GetSupportedSize" , & sizeMinVar , & sizeMaxVar , & status )
351
+ if invokeResult != 0 || err != nil {
352
+ result = int (invokeResult )
353
+ }
354
+ klog .V (5 ).Infof ("got sizeMin (%v) sizeMax (%v) from partition (%v), status: %s" , sizeMinVar , sizeMaxVar , part , status )
355
+
356
+ sizeMin , err = strconv .ParseInt (sizeMinVar .ToString (), 10 , 64 )
357
+ if err != nil {
358
+ return
359
+ }
360
+
361
+ sizeMax , err = strconv .ParseInt (sizeMaxVar .ToString (), 10 , 64 )
362
+ return
363
+ }
364
+
365
+ // ResizePartition resizes a partition.
366
+ //
367
+ // Refer to https://learn.microsoft.com/en-us/windows-hardware/drivers/storage/msft-partition-resize
368
+ // for the WMI method definition.
369
+ func ResizePartition (part * storage.MSFT_Partition , size int64 ) (int , string , error ) {
370
+ var status string
371
+ result , err := part .InvokeMethodWithReturn ("Resize" , strconv .Itoa (int (size )), & status )
372
+ return int (result ), status , err
373
+ }
374
+
375
+ // GetPartitionSize returns the size of a partition.
376
+ func GetPartitionSize (part * storage.MSFT_Partition ) (int64 , error ) {
377
+ sizeProp , err := part .GetProperty ("Size" )
378
+ if err != nil {
379
+ return - 1 , err
380
+ }
381
+
382
+ size , err := strconv .ParseInt (sizeProp .(string ), 10 , 64 )
383
+ if err != nil {
384
+ return - 1 , err
385
+ }
386
+
387
+ return size , err
388
+ }
389
+
390
+ // FilterForPartitionOnDisk creates a WMI query filter to query a disk by its number.
391
+ func FilterForPartitionOnDisk (diskNumber uint32 ) * query.WmiQueryFilter {
392
+ return query .NewWmiQueryFilter ("DiskNumber" , strconv .Itoa (int (diskNumber )), query .Equals )
393
+ }
394
+
395
+ // FilterForPartitionsOfTypeNormal creates a WMI query filter for all non-reserved partitions.
396
+ func FilterForPartitionsOfTypeNormal () * query.WmiQueryFilter {
397
+ return query .NewWmiQueryFilter ("GptType" , GPTPartitionTypeMicrosoftReserved , query .NotEquals )
398
+ }
0 commit comments