1

我有一个带有很多挂载点的 Exchange 服务器。给定数据库文件的路径,有没有办法找出它们所在的卷?问题是它们通常不在卷安装点,而是在树的更下方。我正在使用 Powershell,因此我需要一个最好使用 WMI 但也可以使用任何 .NET 或 COM 对象的解决方案。

4

2 回答 2

2

PSCX包括一个 Get-ReparsePoint cmdlet:

C:\temp> Get-ReparsePoint d | ft -auto

Target                                           Path      ReparsePointTag
------                                           ----      ---------------
\??\Volume{a5908e7a-eca5-11dd-be98-005056c00008} C:\temp\d      MountPoint

您可以使用注册表将卷 GUID 映射到熟悉的驱动器名称:

Get-ItemProperty HKLM:\SYSTEM\MountedDevices

[...]
\DosDevices\D:                                   : {22, 35, 171, 65...}
[...]
\??\Volume{a5908e7a-eca5-11dd-be98-005056c00008} : {22, 35, 171, 65...}

综上所述,我们可以获得安装在 c:\temp\d 的物理驱动器的序列号:

$guid = (Get-ReparsePoint d).target
$serial = (get-itemproperty HKLM:\SYSTEM\MountedDevices).$guid

您可以将该序列号与其他逻辑卷(例如带有 DOS 字母的卷)的序列号进行比较。

> function ArrayEqual([psobject[]]$arr1, [psobject[]]$arr2) 
      { @(Compare-Object $arr1 $arr2 -sync 0).Length -eq 0 }

> (gi HKLM:\SYSTEM\MountedDevices).property | ?{ $_ -like "\dos*" } | 
      ?{ ArrayEqual$serial (gp HKLM:\SYSTEM\MountedDevices).$_ }

\DosDevices\D:

有关数组比较函数的说明,请参阅Keith Hill 的博客。

为了完整起见,请注意这似乎与 COM 报告的序列不同...

> $comSerial = (new-object -com scripting.filesystemobject).getdrive("d")
> [bitconverter]::GetBytes($comSerial)
18
208
242
202
于 2009-08-03T21:25:20.920 回答
1

我刚刚发现了 ReparsePoint 属性。

抓取我所在的目录后,我可以沿着树向上走,直到到达 Root 并沿途检查 ReparsePoints。

$dbDir = (get-item (Get-MailboxDatabase $db).edbfilepath).directory
$dbDir
if($dbdir.parent){
  #todo make this recursive
}

#test if it's a reparse point.    
if ($dbdir.attributes -band [System.IO.FileAttributes]::ReparsePoint ){
  #it's a mountpoint.
}

从这里有“mountvol /L”工具,或者更好的 WMI 协会类Win32_MountPointWin32_Volume.

有点涉及 - 但我没有看到一个简单的方法来问“我在什么音量?” 一旦我把它们放在一起,我会发布一个完整的解释。

编辑 - 更多细节在这里:http ://slipsec.com/blog/?p=126

于 2009-08-03T22:43:29.937 回答