public static string GetDirectoryRoot(string path) => MSIOD.GetDirectoryRoot(path);
private static SafeFileHandle OpenHandle(string fullPath, bool asDirectory) { string root = fullPath.Substring(0, PathInternal.GetRootLength(fullPath)); if (root == fullPath && root[1] == Path.VolumeSeparatorChar) { // intentionally not fullpath, most upstack public APIs expose this as path. throw new ArgumentException(SR.Arg_PathIsVolume, "path"); } SafeFileHandle handle = Interop.Kernel32.CreateFile( fullPath, Interop.Kernel32.GenericOperations.GENERIC_WRITE, FileShare.ReadWrite | FileShare.Delete, FileMode.Open, asDirectory ? Interop.Kernel32.FileOperations.FILE_FLAG_BACKUP_SEMANTICS : 0); if (handle.IsInvalid) { int errorCode = Marshal.GetLastWin32Error(); // NT5 oddity - when trying to open "C:\" as a File, // we usually get ERROR_PATH_NOT_FOUND from the OS. We should // probably be consistent w/ every other directory. if (!asDirectory && errorCode == Interop.Errors.ERROR_PATH_NOT_FOUND && fullPath.Equals(Directory.GetDirectoryRoot(fullPath))) { errorCode = Interop.Errors.ERROR_ACCESS_DENIED; } throw Win32Marshal.GetExceptionForWin32Error(errorCode, fullPath); } return(handle); }
private static SafeFileHandle OpenHandleToWriteAttributes(string fullPath, bool asDirectory) { if (fullPath.Length == PathInternal.GetRootLength(fullPath) && fullPath[1] == Path.VolumeSeparatorChar) { // intentionally not fullpath, most upstack public APIs expose this as path. throw new ArgumentException(SR.Arg_PathIsVolume, "path"); } int dwFlagsAndAttributes = Interop.Kernel32.FileOperations.FILE_FLAG_OPEN_REPARSE_POINT; if (asDirectory) { dwFlagsAndAttributes |= Interop.Kernel32.FileOperations.FILE_FLAG_BACKUP_SEMANTICS; } SafeFileHandle handle = Interop.Kernel32.CreateFile( fullPath, Interop.Kernel32.FileOperations.FILE_WRITE_ATTRIBUTES, FileShare.ReadWrite | FileShare.Delete, FileMode.Open, dwFlagsAndAttributes); if (handle.IsInvalid) { int errorCode = Marshal.GetLastWin32Error(); // NT5 oddity - when trying to open "C:\" as a File, // we usually get ERROR_PATH_NOT_FOUND from the OS. We should // probably be consistent w/ every other directory. if (!asDirectory && errorCode == Interop.Errors.ERROR_PATH_NOT_FOUND && fullPath.Equals(Directory.GetDirectoryRoot(fullPath))) { errorCode = Interop.Errors.ERROR_ACCESS_DENIED; } throw Win32Marshal.GetExceptionForWin32Error(errorCode, fullPath); } return(handle); }
private static SafeFileHandle OpenHandle(string fullPath, bool asDirectory) { String root = fullPath.Substring(0, PathHelpers.GetRootLength(fullPath)); if (root == fullPath && root[1] == Path.VolumeSeparatorChar) { throw new ArgumentException(SR.Arg_PathIsVolume); } Interop.mincore.SECURITY_ATTRIBUTES secAttrs = default(Interop.mincore.SECURITY_ATTRIBUTES); SafeFileHandle handle = Helpers.SafeCreateFile( fullPath, (int)Interop.mincore.GenericOperations.GENERIC_WRITE, FileShare.ReadWrite | FileShare.Delete, ref secAttrs, FileMode.Open, asDirectory ? (int)Interop.mincore.FileOperations.FILE_FLAG_BACKUP_SEMANTICS : (int)FileOptions.None, IntPtr.Zero ); if (handle.IsInvalid) { int errorCode = Marshal.GetLastWin32Error(); // NT5 oddity - when trying to open "C:\" as a File, // we usually get ERROR_PATH_NOT_FOUND from the OS. We should // probably be consistent w/ every other directory. if (!asDirectory && errorCode == Interop.mincore.Errors.ERROR_PATH_NOT_FOUND && fullPath.Equals(Directory.GetDirectoryRoot(fullPath))) { errorCode = Interop.mincore.Errors.ERROR_ACCESS_DENIED; } throw Win32Marshal.GetExceptionForWin32Error(errorCode, fullPath); } return(handle); }