tags:

views:

72

answers:

3

Hi all,

In short I have a volume that I need to assign a drive letter to (using diskpart). The problem now comes in that the volume does not remain the same. You enter disk part a do a "list volume" and the specific volume would be volume 0, then "exit". Enter again and the do a "list volume" again and this time it is volume 4. And so it continues. Now if this was done by a person it would not be an issue, however this is an automated task, that will "disconnect" the volume on windows 2003 and used on other servers and mounted again on the windows 2003 server.

I'm trying to write a script in powershell that will be able to identify the volume based on a few unique field(s). The problem comes in that I'm getting stuck on interpreting the output of diskpart's "list volume" command with powershell.

The following command provides the output that I need to work with but there after I'm lost.

cls
$dp = "list volume" | diskpart | ? { $_ -match "^  [^-]" }
$dp | format-table  -auto

and this is the output it provides and the volume that I'm looking for is Volume 1.

  Volume ###  Ltr  Label        Fs     Type        Size     Status     Info
  Volume 0     F                       DVD-ROM         0 B  Healthy            
  *Volume 1                             Partition    100 GB  Healthy*            
  Volume 2     E   DATA         NTFS   Partition    547 GB  Healthy            
  Volume 3     C   OS           NTFS   Partition     39 GB  Healthy    System  
  Volume 4     D   APPS         NTFS   Partition     98 GB  Healthy            

Can anybody help me in the right direction here please. I'm at my tether's end.

A: 

You can just use Powershell and WMI to set the drive letter. Shoudn't need diskpart unless you are doing something else (I'm unfamiliar with that tool)

So (assuming you are trying to set the drive letter of the one volume that doesn't have a letter) this should work:

$drive = gwmi Win32_Volume | where {$_.DriveLetter -eq ""}

$drive.DriveLetter = "X:"

$drive.Put()

If you aren't sure about the drive, just query it first and make sure you are only getting the one you want:

gwmi Win32_Volume | where {$_.DriveLetter -eq ""}
Taylor
If my assumption on what volume you are targeting is wrong, please let me know. The same principles should still work, but just need to make the WMI query look for exactly what you want.
Taylor
Ok, I have managed to pickup the volume by the deviceid and using a like. I assume that the PUT command is to commit the changes? Problem is that it is giving errors I tried to create a new object and setting type etc but it will not accept the call to the Put method.$PutOptions = New-Object System.Management.PutOptions$PutOptions.Type = 2$drive.Put($PutOptions)Please me where am I being daft.
Maartin
Can I see your full code? You shouldnt need to use any put options, just query down to the item, store in a variable, change it, and put() it
Taylor
Taylor below is the two options that I try and the output of each. I will post each separately (comment limit)Option 1========script------cls$drive = get-wmiobject Win32_Volume | where {$_.DeviceID -like "*b0f012f6-82b1-11df-a41c-001f29e8f0be*"}$drive.DriveLetter = "T:"$drive.Put()output------Exception calling "Put" with "0" argument(s): "Not supported "At D:\transport_actions\get_vol_id4.ps1:5 char:11+ $drive.Put <<<< () + CategoryInfo : NotSpecified: (:) [], MethodInvocationException + FullyQualifiedErrorId : DotNetMethodException
Maartin
Option 2========script------cls$drive = get-wmiobject Win32_Volume | where {$_.DeviceID -like "*b0f012f6-82b1-11df-a41c-001f29e8f0be*"}$drive.DriveLetter = "T:"$PutOptions = New-Object System.Management.PutOptions$PutOptions.Type = 2$drive.Put($PutOptions)output------Exception calling "Put" with "1" argument(s): "Unsupported parameter "At D:\transport_actions\get_vol_id4.ps1:10 char:11+ $drive.Put <<<< ($PutOptions) + CategoryInfo : NotSpecified: (:) [], MethodInvocationException + FullyQualifiedErrorId : DotNetMethodException
Maartin
and obviously none of the changes are applied when there is an error. I did a bit of reading on the Put method and in most cases the Put method does not need parameters.
Maartin
Taylor, any suggestions on this? I have not been able to pickup anything on this.
Maartin
Can anybody help me with this please? I'm so close I can smell victory but it is just out of my grasp.
Maartin
A: 

Yep. This is a "feature" of diskpart.

Suggestions from MS (not very useful in your case)

  • Keep the Disk Management console (Diskmgmt.msc) running while you process scripts. Or, keep an instance of the Diskpart.exe utility running in the background while you process scripts. When you do this, the volume numbers should not change between instances of the Diskpart.exe utility. Use the volume Label information instead of the volume number to track particular volumes.

    See bug report here.

belisarius
Belisaruis, thanks for that info. Very sad to have to revert to tactics like keeping it open to try and keep the vol no the same.In this case it is not possible to keep it open.
Maartin
A: 

Yes I got it!!

Here is the answer.
Using VB Script I managed to create a script that did what I was looking for, this I then translated to Powershell and below is the script.

$drive = gwmi Win32_Volume | where {$_.DeviceID -like "*b0f012f6-82b1-11df-a41c-001f29e8f0be*"}
$drive.AddMountPoint("T:\")
$drive.DriveLetter = "T:"
$drive.Put_
$drive.Mount()

The Device ID I obtained by running the following script:

# get volumes on this system
$volumes = get-wmiobject Win32_Volume
# display volume info
# There are {0} volumes on this system, as follows: " -f ($volumes.length)
# Iterate through volumes and display information
foreach ($vol in $volumes) {
    "Volume: {0}" -f ++$i
    "============================="
    $vol | Format-List Access,Automount,Availability,BlockSize,BootVolume,Capacity,Caption,Compressed,ConfigManagerErrorCode,ConfigManagerUserConfig,CreationClassName,Description,DeviceID,DirtyBitSet,DriveLetter,DriveType,ErrorCleared,ErrorDescription,ErrorMethodology,FileSystem,FreeSpace,IndexingEnabled,InstallDate,Label,LastErrorCode,MaximumFileNameLength,Name,NumberOfBlocks,PageFilePresent,PNPDeviceID,PowerManagementCapabilities,PowerManagementSupported,Purpose,QuotasEnabled,QuotasIncomplete,QuotasRebuilding,SerialNumber,Status,StatusInfo,SupportsDiskQuotas,SupportsFileBasedCompression,SystemCreationClassName,SystemName,SystemVolume
}

from a post on msdn on the class Win32_Volume.

I hope this might help somebody else

Thank you to everybody that help!

Maartin