Home > Article > Backend Development > How Can You Efficiently Detect File Changes on an NTFS Volume Using FSCTL_ENUM_USN_DATA?
Existing backup methods, which check each file's archive bit, can become slow and inefficient for large file systems. This approach requires scanning all files, including temporary files, and may result in lengthy backup processes.
A more efficient method involves using the File System USN (Update Sequence Number) change journal. Filesystem USN provides a record for each change made to the file system, including file creation, deletion, and modification.
To detect changes on an NTFS volume, we can utilize the FSCTL_ENUM_USN_DATA control code. This control code:
Retrieves critical data for each file, including:
To detect changes:
Here's a code snippet that demonstrates the approach:
<code class="c++">DWORDLONG nextid; DWORDLONG filecount = 0; DWORD starttick, endtick; // Allocate memory for USN records void * buffer = VirtualAlloc(NULL, BUFFER_SIZE, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); // Open volume handle HANDLE drive = CreateFile(L"\\?\c:", GENERIC_READ, FILE_SHARE_DELETE | FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_ALWAYS, FILE_FLAG_NO_BUFFERING, NULL); // Get volume USN journal data USN_JOURNAL_DATA * journal = (USN_JOURNAL_DATA *)buffer; if (!DeviceIoControl(drive, FSCTL_QUERY_USN_JOURNAL, NULL, 0, buffer, BUFFER_SIZE, &bytecount, NULL)) { (...) } maxusn = journal->MaxUsn; MFT_ENUM_DATA mft_enum_data; mft_enum_data.StartFileReferenceNumber = 0; mft_enum_data.LowUsn = 0; mft_enum_data.HighUsn = maxusn; while (...) { if (!DeviceIoControl(drive, FSCTL_ENUM_USN_DATA, &mft_enum_data, sizeof(mft_enum_data), buffer, BUFFER_SIZE, &bytecount, NULL)) { (...) } nextid = *((DWORDLONG *)buffer); USN_RECORD * record = (USN_RECORD *)((USN *)buffer + 1); USN_RECORD * recordend = (USN_RECORD *)(((BYTE *)buffer) + bytecount); while (record < recordend) { filecount++; // Check flags and USNs to identify changes (...) record = (USN_RECORD *)(((BYTE *)record) + record->RecordLength); } mft_enum_data.StartFileReferenceNumber = nextid; }</code>
The approach using FSCTL_ENUM_USN_DATA offers:
The above is the detailed content of How Can You Efficiently Detect File Changes on an NTFS Volume Using FSCTL_ENUM_USN_DATA?. For more information, please follow other related articles on the PHP Chinese website!