mirror of
https://github.com/reactos/reactos.git
synced 2024-10-08 02:13:56 +00:00
[NTFS]
Finally, implement NtfsGetFreeClusters() which will just read the $Data stream from $BITMAP file record to get the amount of free clusters to allow estimating the free space on a volume. The implementation is likely under-optimized... But wwell, the rest of the FSD is not better. Who talked about caching?! ;-) Because pictures are more relevant than words in such case: http://www.heisspiter.net/~Pierre/rostests/NTFS_disksize.png svn path=/trunk/; revision=65082
This commit is contained in:
parent
2c3bb20acb
commit
135e926315
|
@ -36,10 +36,69 @@ static
|
||||||
ULONGLONG
|
ULONGLONG
|
||||||
NtfsGetFreeClusters(PDEVICE_EXTENSION DeviceExt)
|
NtfsGetFreeClusters(PDEVICE_EXTENSION DeviceExt)
|
||||||
{
|
{
|
||||||
UNIMPLEMENTED;
|
NTSTATUS Status;
|
||||||
|
PFILE_RECORD_HEADER BitmapRecord;
|
||||||
|
PNTFS_ATTR_CONTEXT DataContext;
|
||||||
|
ULONGLONG BitmapDataSize;
|
||||||
|
PCHAR BitmapData;
|
||||||
|
ULONGLONG FreeClusters = 0;
|
||||||
|
ULONG Read = 0;
|
||||||
|
RTL_BITMAP Bitmap;
|
||||||
|
|
||||||
|
DPRINT1("NtfsGetFreeClusters(%p)\n", DeviceExt);
|
||||||
|
|
||||||
|
BitmapRecord = ExAllocatePoolWithTag(NonPagedPool,
|
||||||
|
DeviceExt->NtfsInfo.BytesPerFileRecord,
|
||||||
|
TAG_NTFS);
|
||||||
|
if (BitmapRecord == NULL)
|
||||||
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Status = ReadFileRecord(DeviceExt, NTFS_FILE_BITMAP, BitmapRecord);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
ExFreePoolWithTag(BitmapRecord, TAG_NTFS);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
Status = FindAttribute(DeviceExt, BitmapRecord, AttributeData, L"", 0, &DataContext);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
ExFreePoolWithTag(BitmapRecord, TAG_NTFS);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
BitmapDataSize = AttributeDataLength(&DataContext->Record);
|
||||||
|
ASSERT((BitmapDataSize * 8) >= (DeviceExt->NtfsInfo.SectorCount / DeviceExt->NtfsInfo.SectorsPerCluster));
|
||||||
|
BitmapData = ExAllocatePoolWithTag(NonPagedPool, BitmapDataSize, TAG_NTFS);
|
||||||
|
if (BitmapData == NULL)
|
||||||
|
{
|
||||||
|
ReleaseAttributeContext(DataContext);
|
||||||
|
ExFreePoolWithTag(BitmapRecord, TAG_NTFS);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* FIXME: Totally underoptimized! */
|
||||||
|
for (; Read < BitmapDataSize; Read += DeviceExt->NtfsInfo.BytesPerSector)
|
||||||
|
{
|
||||||
|
ReadAttribute(DeviceExt, DataContext, Read, (PCHAR)((ULONG_PTR)BitmapData + Read), DeviceExt->NtfsInfo.BytesPerSector);
|
||||||
|
}
|
||||||
|
ReleaseAttributeContext(DataContext);
|
||||||
|
|
||||||
|
DPRINT1("Total clusters: %I64x\n", DeviceExt->NtfsInfo.SectorCount / DeviceExt->NtfsInfo.SectorsPerCluster);
|
||||||
|
DPRINT1("Total clusters in bitmap: %I64x\n", BitmapDataSize * 8);
|
||||||
|
DPRINT1("Diff in size: %I64d B\n", ((BitmapDataSize * 8) - (DeviceExt->NtfsInfo.SectorCount / DeviceExt->NtfsInfo.SectorsPerCluster)) * DeviceExt->NtfsInfo.SectorsPerCluster * DeviceExt->NtfsInfo.BytesPerSector);
|
||||||
|
|
||||||
|
RtlInitializeBitMap(&Bitmap, (PULONG)BitmapData, DeviceExt->NtfsInfo.SectorCount / DeviceExt->NtfsInfo.SectorsPerCluster);
|
||||||
|
FreeClusters = RtlNumberOfClearBits(&Bitmap);
|
||||||
|
|
||||||
|
ExFreePoolWithTag(BitmapData, TAG_NTFS);
|
||||||
|
ExFreePoolWithTag(BitmapRecord, TAG_NTFS);
|
||||||
|
|
||||||
|
return FreeClusters;
|
||||||
|
}
|
||||||
|
|
||||||
static
|
static
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
NtfsGetFsVolumeInformation(PDEVICE_OBJECT DeviceObject,
|
NtfsGetFsVolumeInformation(PDEVICE_OBJECT DeviceObject,
|
||||||
|
|
Loading…
Reference in a new issue