#2
nohairmonk2020-11-28 20:55
这里是全部代码:
程序代码: using System; using System.Collections.Generic; using System.Linq; using System.Text; using using PInvoke; using using System.Runtime.InteropServices; using Microsoft.Win32.SafeHandles; namespace UsnJournal { public class NtfsUsnJournal : IDisposable { #region enum(s) public enum UsnJournalReturnCode { INVALID_HANDLE_VALUE = -1, USN_JOURNAL_SUCCESS = 0, ERROR_INVALID_FUNCTION = 1, ERROR_FILE_NOT_FOUND = 2, ERROR_PATH_NOT_FOUND = 3, ERROR_TOO_MANY_OPEN_FILES = 4, ERROR_ACCESS_DENIED = 5, ERROR_INVALID_HANDLE = 6, ERROR_INVALID_DATA = 13, ERROR_HANDLE_EOF = 38, ERROR_NOT_SUPPORTED = 50, ERROR_INVALID_PARAMETER = 87, ERROR_JOURNAL_DELETE_IN_PROGRESS = 1178, USN_JOURNAL_NOT_ACTIVE = 1179, ERROR_JOURNAL_ENTRY_DELETED = 1181, ERROR_INVALID_USER_BUFFER = 1784, USN_JOURNAL_INVALID = 17001, VOLUME_NOT_NTFS = 17003, INVALID_FILE_REFERENCE_NUMBER = 17004, USN_JOURNAL_ERROR = 17005 } public enum UsnReasonCode { USN_REASON_DATA_OVERWRITE = 0x00000001, USN_REASON_DATA_EXTEND = 0x00000002, USN_REASON_DATA_TRUNCATION = 0x00000004, USN_REASON_NAMED_DATA_OVERWRITE = 0x00000010, USN_REASON_NAMED_DATA_EXTEND = 0x00000020, USN_REASON_NAMED_DATA_TRUNCATION = 0x00000040, USN_REASON_FILE_CREATE = 0x00000100, USN_REASON_FILE_DELETE = 0x00000200, USN_REASON_EA_CHANGE = 0x00000400, USN_REASON_SECURITY_CHANGE = 0x00000800, USN_REASON_RENAME_OLD_NAME = 0x00001000, USN_REASON_RENAME_NEW_NAME = 0x00002000, USN_REASON_INDEXABLE_CHANGE = 0x00004000, USN_REASON_BASIC_INFO_CHANGE = 0x00008000, USN_REASON_HARD_LINK_CHANGE = 0x00010000, USN_REASON_COMPRESSION_CHANGE = 0x00020000, USN_REASON_ENCRYPTION_CHANGE = 0x00040000, USN_REASON_OBJECT_ID_CHANGE = 0x00080000, USN_REASON_REPARSE_POINT_CHANGE = 0x00100000, USN_REASON_STREAM_CHANGE = 0x00200000, USN_REASON_CLOSE = -1 } #endregion #region private member variables private DriveInfo _driveInfo = null; private uint _volumeSerialNumber; private IntPtr _usnJournalRootHandle; private bool bNtfsVolume; #endregion #region properties private static TimeSpan _elapsedTime; public static TimeSpan ElapsedTime { get { return _elapsedTime; } } public string VolumeName { get { return _driveInfo.Name; } } public long AvailableFreeSpace { get { return _driveInfo.AvailableFreeSpace; } } public long TotalFreeSpace { get { return _driveInfo.TotalFreeSpace; } } public string Format { get { return _driveInfo.DriveFormat; } } public DirectoryInfo RootDirectory { get { return _driveInfo.RootDirectory; } } public long TotalSize { get { return _driveInfo.TotalSize; } } public string VolumeLabel { get { return _driveInfo.VolumeLabel; } } public uint VolumeSerialNumber { get { return _volumeSerialNumber; } } #endregion #region constructor(s) public NtfsUsnJournal(DriveInfo driveInfo) { DateTime start = DateTime.Now; _driveInfo = driveInfo; if (0 == string.Compare(_driveInfo.DriveFormat, "ntfs", true)) { bNtfsVolume = true; IntPtr rootHandle = IntPtr.Zero; UsnJournalReturnCode usnRtnCode = GetRootHandle(out rootHandle); if (usnRtnCode == UsnJournalReturnCode.USN_JOURNAL_SUCCESS) { _usnJournalRootHandle = rootHandle; usnRtnCode = GetVolumeSerialNumber(_driveInfo, out _volumeSerialNumber); if (usnRtnCode != UsnJournalReturnCode.USN_JOURNAL_SUCCESS) { _elapsedTime = DateTime.Now - start; throw new Win32Exception((int)usnRtnCode); } } else { _elapsedTime = DateTime.Now - start; throw new Win32Exception((int)usnRtnCode); } } else { _elapsedTime = DateTime.Now - start; throw new Exception(string.Format("{0} is not an 'NTFS' volume.", _driveInfo.Name)); } _elapsedTime = DateTime.Now - start; } #endregion #region public methods public UsnJournalReturnCode CreateUsnJournal(ulong maxSize, ulong allocationDelta) { UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS; DateTime startTime = DateTime.Now; if (bNtfsVolume) { if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; UInt32 cb; Win32Api.CREATE_USN_JOURNAL_DATA cujd = new Win32Api.CREATE_USN_JOURNAL_DATA(); cujd.MaximumSize = maxSize; cujd.AllocationDelta = allocationDelta; int sizeCujd = Marshal.SizeOf(cujd); IntPtr cujdBuffer = Marshal.AllocHGlobal(sizeCujd); Win32Api.ZeroMemory(cujdBuffer, sizeCujd); Marshal.StructureToPtr(cujd, cujdBuffer, true); bool fOk = Win32Api.DeviceIoControl( _usnJournalRootHandle, Win32Api.FSCTL_CREATE_USN_JOURNAL, cujdBuffer, sizeCujd, IntPtr.Zero, 0, out cb, IntPtr.Zero); if (!fOk) { usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error()); } Marshal.FreeHGlobal(cujdBuffer); } else { usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE; } } _elapsedTime = DateTime.Now - startTime; return usnRtnCode; } public UsnJournalReturnCode DeleteUsnJournal(Win32Api.USN_JOURNAL_DATA journalState) { UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS; DateTime startTime = DateTime.Now; if (bNtfsVolume) { if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; UInt32 cb; Win32Api.DELETE_USN_JOURNAL_DATA dujd = new Win32Api.DELETE_USN_JOURNAL_DATA(); dujd.UsnJournalID = journalState.UsnJournalID; dujd.DeleteFlags = (UInt32)Win32Api.UsnJournalDeleteFlags.USN_DELETE_FLAG_DELETE; int sizeDujd = Marshal.SizeOf(dujd); IntPtr dujdBuffer = Marshal.AllocHGlobal(sizeDujd); Win32Api.ZeroMemory(dujdBuffer, sizeDujd); Marshal.StructureToPtr(dujd, dujdBuffer, true); bool fOk = Win32Api.DeviceIoControl( _usnJournalRootHandle, Win32Api.FSCTL_DELETE_USN_JOURNAL, dujdBuffer, sizeDujd, IntPtr.Zero, 0, out cb, IntPtr.Zero); if (!fOk) { usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error()); } Marshal.FreeHGlobal(dujdBuffer); } else { usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE; } } _elapsedTime = DateTime.Now - startTime; return usnRtnCode; } public UsnJournalReturnCode GetNtfsVolumeFolders(out List<Win32Api.UsnEntry> folders) { DateTime startTime = DateTime.Now; folders = new List<Win32Api.UsnEntry>(); UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS; Int32 FoldersCount = 0; if (bNtfsVolume) { if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; Win32Api.USN_JOURNAL_DATA usnState = new Win32Api.USN_JOURNAL_DATA(); usnRtnCode = QueryUsnJournal(ref usnState); if (usnRtnCode == UsnJournalReturnCode.USN_JOURNAL_SUCCESS) { Win32Api.MFT_ENUM_DATA med; med.StartFileReferenceNumber = 0; med.LowUsn = 0; med.HighUsn = usnState.NextUsn; Int32 sizeMftEnumData = Marshal.SizeOf(med); IntPtr medBuffer = Marshal.AllocHGlobal(sizeMftEnumData); Win32Api.ZeroMemory(medBuffer, sizeMftEnumData); Marshal.StructureToPtr(med, medBuffer, true); int pDataSize = sizeof(UInt64) + 10000; IntPtr pData = Marshal.AllocHGlobal(pDataSize); Win32Api.ZeroMemory(pData, pDataSize); uint outBytesReturned = 0; Win32Api.UsnEntry usnEntry = null; while (false != Win32Api.DeviceIoControl( _usnJournalRootHandle, Win32Api.FSCTL_ENUM_USN_DATA, medBuffer, sizeMftEnumData, pData, pDataSize, out outBytesReturned, IntPtr.Zero)) { IntPtr pUsnRecord = new IntPtr(pData.ToInt32() + sizeof(Int64)); while (outBytesReturned > 60) { usnEntry = new Win32Api.UsnEntry(pUsnRecord); if (usnEntry.IsFolder) { folders.Add(usnEntry); FoldersCount += 1; } pUsnRecord = new IntPtr(pUsnRecord.ToInt32() + usnEntry.RecordLength); outBytesReturned -= usnEntry.RecordLength; } Marshal.WriteInt64(medBuffer, Marshal.ReadInt64(pData, 0)); } Marshal.FreeHGlobal(pData); usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error()); if (usnRtnCode == UsnJournalReturnCode.ERROR_HANDLE_EOF) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; } } } else { usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE; } } folders.Sort(); System.Windows.MessageBox.Show(Convert.ToString(FoldersCount)); //return FoldersCount; //我想返回FoldersCount的值 return usnRtnCode; } public UsnJournalReturnCode GetFilesMatchingFilter(string filter, out List<Win32Api.UsnEntry> files) { Int32 FilesCount = 0; DateTime startTime = DateTime.Now; filter = filter.ToLower(); files = new List<Win32Api.UsnEntry>(); string[] fileTypes = filter.Split(' ', ',', ';'); UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS; if (bNtfsVolume) { if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; Win32Api.USN_JOURNAL_DATA usnState = new Win32Api.USN_JOURNAL_DATA(); usnRtnCode = QueryUsnJournal(ref usnState); if (usnRtnCode == UsnJournalReturnCode.USN_JOURNAL_SUCCESS) { Win32Api.MFT_ENUM_DATA med; med.StartFileReferenceNumber = 0; med.LowUsn = 0; med.HighUsn = usnState.NextUsn; Int32 sizeMftEnumData = Marshal.SizeOf(med); IntPtr medBuffer = Marshal.AllocHGlobal(sizeMftEnumData); Win32Api.ZeroMemory(medBuffer, sizeMftEnumData); Marshal.StructureToPtr(med, medBuffer, true); int pDataSize = sizeof(UInt64) + 10000; IntPtr pData = Marshal.AllocHGlobal(pDataSize); Win32Api.ZeroMemory(pData, pDataSize); uint outBytesReturned = 0; Win32Api.UsnEntry usnEntry = null; while (false != Win32Api.DeviceIoControl( _usnJournalRootHandle, Win32Api.FSCTL_ENUM_USN_DATA, medBuffer, sizeMftEnumData, pData, pDataSize, out outBytesReturned, IntPtr.Zero)) { IntPtr pUsnRecord = new IntPtr(pData.ToInt32() + sizeof(Int64)); while (outBytesReturned > 60) { usnEntry = new Win32Api.UsnEntry(pUsnRecord); if (usnEntry.IsFile) { string extension = Path.GetExtension(usnEntry.Name).ToLower(); if (0 == string.Compare(filter, "*")) { files.Add(usnEntry); } else if (!string.IsNullOrEmpty(extension)) { foreach (string fileType in fileTypes) { if (extension.Contains(fileType)) { files.Add(usnEntry); FilesCount += 1; } } } } pUsnRecord = new IntPtr(pUsnRecord.ToInt32() + usnEntry.RecordLength); outBytesReturned -= usnEntry.RecordLength; } Marshal.WriteInt64(medBuffer, Marshal.ReadInt64(pData, 0)); } Marshal.FreeHGlobal(pData); usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error()); if (usnRtnCode == UsnJournalReturnCode.ERROR_HANDLE_EOF) { usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; } } } else { usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE; } } files.Sort(); System.Windows.MessageBox.Show(Convert.ToString(FilesCount)); return usnRtnCode; } public bool IsUsnJournalActive() { DateTime start = DateTime.Now; bool bRtnCode = false; if (bNtfsVolume) { if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { Win32Api.USN_JOURNAL_DATA usnJournalCurrentState = new Win32Api.USN_JOURNAL_DATA(); UsnJournalReturnCode usnError = QueryUsnJournal(ref usnJournalCurrentState); if (usnError == UsnJournalReturnCode.USN_JOURNAL_SUCCESS) { bRtnCode = true; } } } _elapsedTime = DateTime.Now - start; return bRtnCode; } #endregion #region private member functions /// <summary> /// Converts a Win32 Error to a UsnJournalReturnCode /// </summary> /// <param name="Win32LastError">The 'last' Win32 error.</param> /// <returns> /// INVALID_HANDLE_VALUE error generated by Win32 Api calls. /// USN_JOURNAL_SUCCESS usn journal function succeeded. /// ERROR_INVALID_FUNCTION error generated by Win32 Api calls. /// ERROR_FILE_NOT_FOUND error generated by Win32 Api calls. /// ERROR_PATH_NOT_FOUND error generated by Win32 Api calls. /// ERROR_TOO_MANY_OPEN_FILES error generated by Win32 Api calls. /// ERROR_ACCESS_DENIED accessing the usn journal requires admin rights. /// ERROR_INVALID_HANDLE error generated by Win32 Api calls. /// ERROR_INVALID_DATA error generated by Win32 Api calls. /// ERROR_HANDLE_EOF error generated by Win32 Api calls. /// ERROR_NOT_SUPPORTED error generated by Win32 Api calls. /// ERROR_INVALID_PARAMETER error generated by Win32 Api calls. /// ERROR_JOURNAL_DELETE_IN_PROGRESS usn journal delete is in progress. /// ERROR_JOURNAL_ENTRY_DELETED usn journal entry lost, no longer available. /// ERROR_INVALID_USER_BUFFER error generated by Win32 Api calls. /// USN_JOURNAL_INVALID usn journal is invalid, id's don't match or required entries lost. /// USN_JOURNAL_NOT_ACTIVE usn journal is not active on volume. /// VOLUME_NOT_NTFS volume is not an NTFS volume. /// INVALID_FILE_REFERENCE_NUMBER bad file reference number - see remarks. /// USN_JOURNAL_ERROR unspecified usn journal error. /// </returns> private UsnJournalReturnCode ConvertWin32ErrorToUsnError(Win32Api.GetLastErrorEnum Win32LastError) { UsnJournalReturnCode usnRtnCode; switch (Win32LastError) { case Win32Api.GetLastErrorEnum.ERROR_JOURNAL_NOT_ACTIVE: usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_NOT_ACTIVE; break; case Win32Api.GetLastErrorEnum.ERROR_SUCCESS: usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; break; case Win32Api.GetLastErrorEnum.ERROR_HANDLE_EOF: usnRtnCode = UsnJournalReturnCode.ERROR_HANDLE_EOF; break; default: usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_ERROR; break; } return usnRtnCode; } /// <summary> /// Gets a Volume Serial Number for the volume represented by driveInfo. /// </summary> /// <param name="driveInfo">DriveInfo object representing the volume in question.</param> /// <param name="volumeSerialNumber">out parameter to hold the volume serial number.</param> /// <returns></returns> private UsnJournalReturnCode GetVolumeSerialNumber(DriveInfo driveInfo, out uint volumeSerialNumber) { Console.WriteLine("GetVolumeSerialNumber() function entered for drive '{0}'", driveInfo.Name); volumeSerialNumber = 0; UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; string pathRoot = string.Concat("\\\\.\\", driveInfo.Name); IntPtr hRoot = Win32Api.CreateFile(pathRoot, 0, Win32Api.FILE_SHARE_READ | Win32Api.FILE_SHARE_WRITE, IntPtr.Zero, Win32Api.OPEN_EXISTING, Win32Api.FILE_FLAG_BACKUP_SEMANTICS, IntPtr.Zero); if (hRoot.ToInt32() != Win32Api.INVALID_HANDLE_VALUE) { Win32Api.BY_HANDLE_FILE_INFORMATION fi = new Win32Api.BY_HANDLE_FILE_INFORMATION(); bool bRtn = Win32Api.GetFileInformationByHandle(hRoot, out fi); if (bRtn) { UInt64 fileIndexHigh = (UInt64)fi.FileIndexHigh; UInt64 indexRoot = (fileIndexHigh << 32) | fi.FileIndexLow; volumeSerialNumber = fi.VolumeSerialNumber; } else { usnRtnCode = (UsnJournalReturnCode)Marshal.GetLastWin32Error(); } Win32Api.CloseHandle(hRoot); } else { usnRtnCode = (UsnJournalReturnCode)Marshal.GetLastWin32Error(); } return usnRtnCode; } private UsnJournalReturnCode GetRootHandle(out IntPtr rootHandle) { // // private functions don't need to check for an NTFS volume or // a valid _usnJournalRootHandle handle // UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; rootHandle = IntPtr.Zero; string vol = string.Concat("\\\\.\\", _driveInfo.Name.TrimEnd('\\')); rootHandle = Win32Api.CreateFile(vol, Win32Api.GENERIC_READ | Win32Api.GENERIC_WRITE, Win32Api.FILE_SHARE_READ | Win32Api.FILE_SHARE_WRITE, IntPtr.Zero, Win32Api.OPEN_EXISTING, 0, IntPtr.Zero); if (rootHandle.ToInt32() == Win32Api.INVALID_HANDLE_VALUE) { usnRtnCode = (UsnJournalReturnCode)Marshal.GetLastWin32Error(); } return usnRtnCode; } /// <summary> /// This function queries the usn journal on the volume. /// </summary> /// <param name="usnJournalState">the USN_JOURNAL_DATA object that is associated with this volume</param> /// <returns></returns> private UsnJournalReturnCode QueryUsnJournal(ref Win32Api.USN_JOURNAL_DATA usnJournalState) { // // private functions don't need to check for an NTFS volume or // a valid _usnJournalRootHandle handle // UsnJournalReturnCode usnReturnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS; int sizeUsnJournalState = Marshal.SizeOf(usnJournalState); UInt32 cb; bool fOk = Win32Api.DeviceIoControl( _usnJournalRootHandle, Win32Api.FSCTL_QUERY_USN_JOURNAL, IntPtr.Zero, 0, out usnJournalState, sizeUsnJournalState, out cb, IntPtr.Zero); if (!fOk) { int lastWin32Error = Marshal.GetLastWin32Error(); usnReturnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error()); } return usnReturnCode; } #endregion #region IDisposable Members public void Dispose() { Win32Api.CloseHandle(_usnJournalRootHandle); } #endregion } } |
程序代码:
public UsnJournalReturnCode
GetNtfsVolumeFolders(out List<Win32Api.UsnEntry> folders)
{
DateTime startTime = DateTime.Now;
folders = new List<Win32Api.UsnEntry>();
UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS;
Int32 FoldersCount = 0;
if (bNtfsVolume)
{
if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE)
{
usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS;
Win32Api.USN_JOURNAL_DATA usnState = new Win32Api.USN_JOURNAL_DATA();
usnRtnCode = QueryUsnJournal(ref usnState);
if (usnRtnCode == UsnJournalReturnCode.USN_JOURNAL_SUCCESS)
{
//
// set up MFT_ENUM_DATA structure
//
Win32Api.MFT_ENUM_DATA med;
med.StartFileReferenceNumber = 0;
med.LowUsn = 0;
med.HighUsn = usnState.NextUsn;
Int32 sizeMftEnumData = Marshal.SizeOf(med);
IntPtr medBuffer = Marshal.AllocHGlobal(sizeMftEnumData);
Win32Api.ZeroMemory(medBuffer, sizeMftEnumData);
Marshal.StructureToPtr(med, medBuffer, true);
//
// set up the data buffer which receives the USN_RECORD data
//
int pDataSize = sizeof(UInt64) + 10000;
IntPtr pData = Marshal.AllocHGlobal(pDataSize);
Win32Api.ZeroMemory(pData, pDataSize);
uint outBytesReturned = 0;
Win32Api.UsnEntry usnEntry = null;
//
// Gather up volume's directories
//
while (false != Win32Api.DeviceIoControl(
_usnJournalRootHandle,
Win32Api.FSCTL_ENUM_USN_DATA,
medBuffer,
sizeMftEnumData,
pData,
pDataSize,
out outBytesReturned,
IntPtr.Zero))
{
IntPtr pUsnRecord = new IntPtr(pData.ToInt32() + sizeof(Int64));
while (outBytesReturned > 60)
{
usnEntry = new Win32Api.UsnEntry(pUsnRecord);
//
// check for directory entries
//
if (usnEntry.IsFolder)
{
folders.Add(usnEntry);
FoldersCount += 1;
}
pUsnRecord = new IntPtr(pUsnRecord.ToInt32() + usnEntry.RecordLength);
outBytesReturned -= usnEntry.RecordLength;
}
Marshal.WriteInt64(medBuffer, Marshal.ReadInt64(pData, 0));
}
Marshal.FreeHGlobal(pData);
usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error());
if (usnRtnCode == UsnJournalReturnCode.ERROR_HANDLE_EOF)
{
usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS;
}
}
}
else
{
usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE;
}
}
folders.Sort();
System.Windows.MessageBox.Show(Convert.ToString(FoldersCount));
//return FoldersCount; //我想返回FoldersCount的值
return usnRtnCode;
}
GetNtfsVolumeFolders(out List<Win32Api.UsnEntry> folders)
{
DateTime startTime = DateTime.Now;
folders = new List<Win32Api.UsnEntry>();
UsnJournalReturnCode usnRtnCode = UsnJournalReturnCode.VOLUME_NOT_NTFS;
Int32 FoldersCount = 0;
if (bNtfsVolume)
{
if (_usnJournalRootHandle.ToInt32() != Win32Api.INVALID_HANDLE_VALUE)
{
usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS;
Win32Api.USN_JOURNAL_DATA usnState = new Win32Api.USN_JOURNAL_DATA();
usnRtnCode = QueryUsnJournal(ref usnState);
if (usnRtnCode == UsnJournalReturnCode.USN_JOURNAL_SUCCESS)
{
//
// set up MFT_ENUM_DATA structure
//
Win32Api.MFT_ENUM_DATA med;
med.StartFileReferenceNumber = 0;
med.LowUsn = 0;
med.HighUsn = usnState.NextUsn;
Int32 sizeMftEnumData = Marshal.SizeOf(med);
IntPtr medBuffer = Marshal.AllocHGlobal(sizeMftEnumData);
Win32Api.ZeroMemory(medBuffer, sizeMftEnumData);
Marshal.StructureToPtr(med, medBuffer, true);
//
// set up the data buffer which receives the USN_RECORD data
//
int pDataSize = sizeof(UInt64) + 10000;
IntPtr pData = Marshal.AllocHGlobal(pDataSize);
Win32Api.ZeroMemory(pData, pDataSize);
uint outBytesReturned = 0;
Win32Api.UsnEntry usnEntry = null;
//
// Gather up volume's directories
//
while (false != Win32Api.DeviceIoControl(
_usnJournalRootHandle,
Win32Api.FSCTL_ENUM_USN_DATA,
medBuffer,
sizeMftEnumData,
pData,
pDataSize,
out outBytesReturned,
IntPtr.Zero))
{
IntPtr pUsnRecord = new IntPtr(pData.ToInt32() + sizeof(Int64));
while (outBytesReturned > 60)
{
usnEntry = new Win32Api.UsnEntry(pUsnRecord);
//
// check for directory entries
//
if (usnEntry.IsFolder)
{
folders.Add(usnEntry);
FoldersCount += 1;
}
pUsnRecord = new IntPtr(pUsnRecord.ToInt32() + usnEntry.RecordLength);
outBytesReturned -= usnEntry.RecordLength;
}
Marshal.WriteInt64(medBuffer, Marshal.ReadInt64(pData, 0));
}
Marshal.FreeHGlobal(pData);
usnRtnCode = ConvertWin32ErrorToUsnError((Win32Api.GetLastErrorEnum)Marshal.GetLastWin32Error());
if (usnRtnCode == UsnJournalReturnCode.ERROR_HANDLE_EOF)
{
usnRtnCode = UsnJournalReturnCode.USN_JOURNAL_SUCCESS;
}
}
}
else
{
usnRtnCode = UsnJournalReturnCode.INVALID_HANDLE_VALUE;
}
}
folders.Sort();
System.Windows.MessageBox.Show(Convert.ToString(FoldersCount));
//return FoldersCount; //我想返回FoldersCount的值
return usnRtnCode;
}