Answered by:
Get Absolute Path of Drive mapped to local folder

Question
-
Can anyone help me find out how to get the absolute path of a drive which is mapped to a local folder?
For example, I have a "c:\test" folder and an "x:" drive which is mapped to c:\test.
I'm looking for a function which will return "c:\test" when I pass in "x:"
Thanks
rr12
Monday, November 6, 2006 4:22 PM
Answers
-
SUBST uses DefineDosDevice (XP and later) to create the drive/path mapping. You can use the QueryDosDevice to get the path of a SUBSTed drive:
[DllImport("kernel32.dll")]
private static extern uint QueryDosDevice(string lpDeviceName, StringBuilder lpTargetPath, int ucchMax);
static String GetPhysicalPath(String path)
{
if (String.IsNullOrEmpty(path))
{
throw new ArgumentNullException("path");
}
// Get the drive letter
string pathRoot = Path.GetPathRoot(path);
if(String.IsNullOrEmpty(pathRoot))
{
throw new ArgumentNullException("path");
}
string lpDeviceName = pathRoot.Replace("\\", "");
const String substPrefix = @"\??\";
StringBuilder lpTargetPath = new StringBuilder(260);
if (0 != QueryDosDevice(lpDeviceName, lpTargetPath, lpTargetPath.Capacity))
{
string result;
// If drive is substed, the result will be in the format of "\??\C:\RealPath\".
if (lpTargetPath..ToString().StartsWith(substPrefix))
{
// Strip the \??\ prefix.
string root = lpTargetPath.ToString().Remove(0, substPrefix.Length);
result = Path.Combine(root, path.Replace(Path.GetPathRoot(path), ""));
}
else
{
// TODO: deal with other types of mappings.
// if not SUBSTed, just assume it's not mapped.
result = path;
}
return result;
}
else
{
// TODO: error reporting
return null;
}
}
Based slightly on http://www.pinvoke.net/default.aspx/kernel32/QueryDosDevice.html
Monday, November 6, 2006 6:52 PMModerator
All replies
-
To confirm... you are looking for some sort of API call that can give you the same data that is provided when you run 'net share' from the commandline?Monday, November 6, 2006 6:01 PMModerator
-
No.
More like the api for the results of subst.
Thanks.
Monday, November 6, 2006 6:08 PM -
SUBST uses DefineDosDevice (XP and later) to create the drive/path mapping. You can use the QueryDosDevice to get the path of a SUBSTed drive:
[DllImport("kernel32.dll")]
private static extern uint QueryDosDevice(string lpDeviceName, StringBuilder lpTargetPath, int ucchMax);
static String GetPhysicalPath(String path)
{
if (String.IsNullOrEmpty(path))
{
throw new ArgumentNullException("path");
}
// Get the drive letter
string pathRoot = Path.GetPathRoot(path);
if(String.IsNullOrEmpty(pathRoot))
{
throw new ArgumentNullException("path");
}
string lpDeviceName = pathRoot.Replace("\\", "");
const String substPrefix = @"\??\";
StringBuilder lpTargetPath = new StringBuilder(260);
if (0 != QueryDosDevice(lpDeviceName, lpTargetPath, lpTargetPath.Capacity))
{
string result;
// If drive is substed, the result will be in the format of "\??\C:\RealPath\".
if (lpTargetPath..ToString().StartsWith(substPrefix))
{
// Strip the \??\ prefix.
string root = lpTargetPath.ToString().Remove(0, substPrefix.Length);
result = Path.Combine(root, path.Replace(Path.GetPathRoot(path), ""));
}
else
{
// TODO: deal with other types of mappings.
// if not SUBSTed, just assume it's not mapped.
result = path;
}
return result;
}
else
{
// TODO: error reporting
return null;
}
}
Based slightly on http://www.pinvoke.net/default.aspx/kernel32/QueryDosDevice.html
Monday, November 6, 2006 6:52 PMModerator -
Yes, works great! Thanks.
I'm posting the vb code...
<DllImport(
"kernel32.dll", CharSet:=CharSet.Auto)> _ Function QueryDosDevice(ByVal lpDeviceName As String, ByVal lpTargetPath As String, ByVal ucchMax As Integer) As Integer End Function Private Function GetPhysicalPath(ByVal sPath As String) As String If String.IsNullOrEmpty(sPath) Then Throw New ArgumentNullException("sPath") End If ' *** Get the drive letter *** Dim sPathRoot As String = Path.GetPathRoot(sPath) If String.IsNullOrEmpty(sPathRoot) Then Throw New ArgumentNullException("sPath") End If Dim sDeviceName As String = sPathRoot.Replace("\\", "") Const sSubstPrefix As String = "\??\" Dim sbTargetPath As String = Space(260) If 0 <> QueryDosDevice(sDeviceName, sbTargetPath, 260) Then Dim sResult As String ' *** If drive is substed, the result will be in the format of "\??\C:\RealPath\". If sbTargetPath.ToString.StartsWith(sSubstPrefix) Then ' *** Strip the \??\ prefix Dim sRoot As String = sbTargetPath.ToString.Remove(0, sSubstPrefix.Length) Dim sTemp As StringsTemp = Path.GetPathRoot(sPath)
sTemp = sPath.Replace(sTemp,
"") If Not String.IsNullOrEmpty(sTemp) ThensRoot = Path.Combine(sRoot, sTemp)
End IfsResult = sRoot
Else ' *** TODO: deal with other types of mappings. ' *** if not SUBSTed, just assume it's not mapped.sResult = sPath
End If Return sResult Else ' *** TODO: Error reporting... Return Nothing End If End FunctionTuesday, November 7, 2006 1:13 AM