public static FileIdentityInformation GetVolumeIdAndUniqueIdForFile(string fullPathWithFileName) { var fileHandleInformation = new FileSystemInteractor.BY_HANDLE_FILE_INFORMATION(); var fileInformation = new FileInfo(fullPathWithFileName); try { var fileStream = fileInformation.Open(FileMode.Open, FileAccess.Read); // The "Dangerous" aspect here refers to the 'SetHandleAsInvalid'. This allows the handle to be re-used // and, potentially, to point to another resource. This can pose a security risk should the attempt be // made by external code to retrieve objects on the file system, itself, using this newly invalid IntPtr // as it could point to another resource, entirely. This does not appear to be an issue for Sync as we // do not expose this information. FileSystemInteractor.GetFileInformationByHandle(fileStream.SafeFileHandle.DangerousGetHandle(), out fileHandleInformation); fileStream.Close(); // The cast is very important. If you omit the cast, you'll be shifting a 32 bit value 32 bits to // the left. Shift operators on 32 bit variables will use shift stuff by right-hand-side mod 32. // Effectively, shifting a uint 32 bits to the left is a no-op. Casting to ulong prevents this. return (new FileIdentityInformation ( fileHandleInformation.VolumeSerialNumber, fileHandleInformation.FileIndexHigh, fileHandleInformation.FileIndexLow )); } catch (Exception ex) { throw ex; } }
public static FileIdentityInformation GetVolumeIdAndUniqueIdForFolder(string fullPathWithFolderName) { var directoryHandleInformation = new FileSystemInteractor.BY_HANDLE_FILE_INFORMATION(); try { // OPEN_EXISTING (FileMode.Open) is specified as we know the folder exists when passed into this method; // however, if it doesn't, a FileNotFoundException is thrown var createdFolder = FileSystemInteractor.CreateFile( fullPathWithFolderName, FileAccess.Read, FileShare.Read, IntPtr.Zero, FileMode.Open, Kernel32.FILE_FLAG_BACKUP_SEMANTICS, IntPtr.Zero ); FileSystemInteractor.GetFileInformationByHandle(createdFolder.DangerousGetHandle(), out directoryHandleInformation); return (new FileIdentityInformation ( directoryHandleInformation.VolumeSerialNumber, directoryHandleInformation.FileIndexHigh, directoryHandleInformation.FileIndexLow )); } catch (Exception ex) { throw ex; } }