/// <summary> /// Creates a volume root handle or retrieves an existing one. /// </summary> /// <remarks> /// This is the un-synchronized get-or-add operation resulting in <see cref="VolumeAccessor"/> /// not being thread-safe. /// The returned handle should not be disposed. /// </remarks> private SafeFileHandle TryGetVolumeHandle(ulong volumeSerial) { SafeFileHandle volumeHandle; if (!m_volumeHandles.TryGetValue(volumeSerial, out volumeHandle)) { VolumeGuidPath volumeRootPath = m_map.TryGetVolumePathBySerial(volumeSerial); if (!volumeRootPath.IsValid) { return(null); } OpenFileResult openResult = FileUtilities.TryCreateOrOpenFile( volumeRootPath.GetDevicePath(), FileDesiredAccess.GenericRead, FileShare.ReadWrite | FileShare.Delete, FileMode.Open, FileFlagsAndAttributes.None, out volumeHandle); if (!openResult.Succeeded) { Contract.Assert(volumeHandle == null); return(null); } m_volumeHandles.Add(volumeSerial, volumeHandle); } return(volumeHandle); }
/// <summary> /// Creates a volume root handle or retrieves an existing one. /// </summary> /// <remarks> /// This is the un-synchronized get-or-add operation resulting in <see cref="FileAccessor"/> /// not being thread-safe. /// </remarks> private SafeFileHandle TryGetVolumeRoot(ulong volumeSerial) { SafeFileHandle volumeRootHandle; if (!m_volumeRootHandles.TryGetValue(volumeSerial, out volumeRootHandle)) { VolumeGuidPath volumeRootPath = m_map.TryGetVolumePathBySerial(volumeSerial); if (!volumeRootPath.IsValid) { return(null); } if ( !FileUtilities.TryOpenDirectory( volumeRootPath.Path, FileShare.ReadWrite | FileShare.Delete, out volumeRootHandle).Succeeded) { Contract.Assert(volumeRootHandle == null); return(null); } m_volumeRootHandles.Add(volumeSerial, volumeRootHandle); } return(volumeRootHandle); }