! Good afternoon,
! I’m developing a filter driver to read all the volumes in the system and get the GUID for the same, so that I can apply encryption/Decryption for the desired volume.
! First i’m working on getting all the volume in the system using FltGetVolumeName, below is the code for the same.
FLT_PREOP_CALLBACK_STATUS PreFileOperationCallback(__inout PFLT_CALLBACK_DATA Data,
__in PCFLT_RELATED_OBJECTS FltObjects, __deref_out_opt PVOID* CompletionContext)
{
DbgPrint("\n-------Inside ---PreFileOperationCallback--------");
NTSTATUS status, ntStatus;
//PFLT_INSTANCE retInstance = NULL;
PFLT_VOLUME pVolumeList[MAX_VOLUME_CHARS];
ULONG VolumeListSize = MAX_VOLUME_CHARS;
ULONG VolumeNameLength, index = 0;
PULONG NumberVolumesReturned = NULL;
WCHAR wszNameBuffer[SHORT_NAME_LEN] = { 0 };
FILTER_VOLUME_INFORMATION_CLASS FilterVolumeStandardInformation;
FILTER_VOLUME_STANDARD_INFORMATION FltVolumeStdInfo;
PULONG BufferSizeNeeded;
SIZE_T bytesRequired;
ULONG MEMTAG_VOL_GUID = 0;
PVOLUME_CONTEXT volumeContext = NULL;
UNICODE_STRING volumeGuidName, VolumeNameString;
PVOID VolumeNameBuffer = NULL;
DbgPrint("\n---------Before FltEnumerateVolumes--------");
ntStatus = FltEnumerateVolumes(fileHandler, pVolumeList, VolumeListSize, &NumberVolumesReturned); //Get volume information
if (!NT_SUCCESS(ntStatus)) {
return ntStatus;
}
DbgPrint("\n-------After FltEnumerateVolumes---------");
DbgPrint("\nNumberVolumesReturned - %d",NumberVolumesReturned);
DbgPrint("\n-------------------------------------------");
for (index = 1; index <= NumberVolumesReturned; index++)
{
if (index == NumberVolumesReturned) {
break; //break from forLoop
}
VolumeNameString.Length = MAX_VOLUME_LENGTH;
VolumeNameString.Buffer = wszNameBuffer;
VolumeNameString.MaximumLength = SHORT_NAME_LEN * sizeof(WCHAR);
DbgPrint("\n---------(1) Before FltGetVolumeName --------");
// Query the volume name length.
ntStatus = FltGetVolumeName(pVolumeList[index], NULL, &VolumeNameLength);
DbgPrint("\n-------------------------------------------");
if ((!NT_SUCCESS(ntStatus) && ntStatus != STATUS_BUFFER_TOO_SMALL)) {
return FLT_PREOP_SUCCESS_NO_CALLBACK;
}
// Allocate a buffer for the name.
ntStatus = STATUS_SUCCESS;
VolumeNameLength += (VolumeNameLength + VolumeNameLength); //increase size to allocate more PagePool memory
VolumeNameString.Length = (ULONG)VolumeNameLength;
VolumeNameBuffer = ExAllocatePoolWithTag(PagedPool, VolumeNameLength, MEMTAG_VOL_GUID);
if (VolumeNameBuffer == NULL) {
ntStatus = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlInitEmptyUnicodeString(&VolumeNameString, VolumeNameBuffer, (ULONG)VolumeNameLength);
ntStatus = FltGetVolumeName(pVolumeList[index], &VolumeNameString, NULL); //Get name using volume information & with max pagePool memory
DbgPrint("\n-------- Buffered FltGetVolumeName ---------");
DbgPrint("\nVolumeNameString Length - %ld",VolumeNameString.Length);
DbgPrint("\nVolumeNameString Buffer - %s", (PWCH)VolumeNameString.Buffer); // Please review this point
DbgPrint("\nVolumeNameString MaximumLength-%ld",VolumeNameString.MaximumLength);
DbgPrint("\n------------------------------");
}//End of Index forLoop
for (index = 0; index < NumberVolumesReturned; index++)
{
FltObjectDereference(pVolumeList[index]);
}
//return pInstance;
return FLT_PREOP_SUCCESS_NO_CALLBACK;
}
! --------------------- The output is -----------------
! VolumeNameString Length - 36
! VolumeNameString Buffer -
! VolumeNameString MaximumLength- 36
! ----------------------------------------------------------
! But the Microsoft documentation for FltGetVolumeName function says,
! //A pointer to a caller-allocated UNICODE_STRING structure that contains the volume’s non-persistent device object name (for example, “\Device\HarddiskVolume1”)
! Im unable to get the complete “\Device\HarddiskVolume1” information.
! I need help on this.