You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
730 lines
21 KiB
730 lines
21 KiB
/*++
|
|
|
|
Copyright (c) 2000 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
fsinfo.c
|
|
|
|
Abstract:
|
|
|
|
This file contains code for commands that affect
|
|
information specific to the file system.
|
|
|
|
Author:
|
|
|
|
Wesley Witt [wesw] 1-March-2000
|
|
|
|
Revision History:
|
|
|
|
--*/
|
|
|
|
#include <precomp.h>
|
|
|
|
|
|
INT
|
|
FsInfoHelp(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
{
|
|
DisplayMsg( MSG_USAGE_FSINFO );
|
|
return EXIT_CODE_SUCCESS;
|
|
}
|
|
|
|
typedef struct _NTFS_FILE_SYSTEM_STATISTICS {
|
|
FILESYSTEM_STATISTICS Common;
|
|
NTFS_STATISTICS Ntfs;
|
|
UCHAR Pad[64-(sizeof(FILESYSTEM_STATISTICS)+sizeof(NTFS_STATISTICS))%64];
|
|
} NTFS_FILE_SYSTEM_STATISTICS, *PNTFS_FILE_SYSTEM_STATISTICS;
|
|
|
|
typedef struct _FAT_FILE_SYSTEM_STATISTICS {
|
|
FILESYSTEM_STATISTICS Common;
|
|
FAT_STATISTICS Fat;
|
|
UCHAR Pad[64-(sizeof(FILESYSTEM_STATISTICS)+sizeof(NTFS_STATISTICS))%64];
|
|
} FAT_FILE_SYSTEM_STATISTICS, *PFAT_FILE_SYSTEM_STATISTICS;
|
|
|
|
|
|
|
|
ULONGLONG
|
|
FsStat(
|
|
IN PVOID FsStats,
|
|
IN ULONG FsSize,
|
|
IN ULONG Offset,
|
|
IN ULONG NumProcs
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine iterates through the file system statistics structure
|
|
and accumulates a total amount for a given statistic field.
|
|
|
|
Note: This function assumes that the width of the field being accumulated
|
|
is a ULONG. If this assumption is invalidated then a width argument
|
|
should be added to this function.
|
|
|
|
Arguments:
|
|
|
|
FsStats - Pointer to an array of file system statistics structures
|
|
FsSize - Size of the individual file system statistics structures in the array
|
|
Offset - Offset of the desired field from the beginning of the file system statistics structure
|
|
NumProcs - Number of processors on the machine where the stats were gathered
|
|
|
|
Return Value:
|
|
|
|
Accumulated total.
|
|
|
|
--*/
|
|
{
|
|
ULONG i;
|
|
ULONGLONG Total = 0;
|
|
|
|
for (i=0; i<NumProcs; i++) {
|
|
Total += *(PULONG)((PUCHAR)FsStats + Offset);
|
|
FsStats = (PVOID)((PUCHAR)FsStats + FsSize);
|
|
}
|
|
|
|
return Total;
|
|
}
|
|
|
|
|
|
INT
|
|
ListDrives(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine lists all the drive names in the system.
|
|
|
|
Arguments:
|
|
|
|
argc - The argument count
|
|
argv - Array of Strings of the form : 'fscutl lsdrv'.
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
{
|
|
DWORD nBufferLen = MAX_PATH;
|
|
DWORD Length;
|
|
LPWSTR lpBuffer = NULL;
|
|
int Index;
|
|
INT ExitCode = EXIT_CODE_SUCCESS;
|
|
|
|
try {
|
|
|
|
if (argc != 0) {
|
|
DisplayMsg( MSG_LISTDRIVES_USAGE );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
lpBuffer = (LPWSTR) malloc( nBufferLen * sizeof(WCHAR) );
|
|
if (!lpBuffer) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
Length = GetLogicalDriveStrings( nBufferLen, lpBuffer );
|
|
if (!Length) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
OutputMessage( L"\r\n" );
|
|
DisplayMsg( MSG_DRIVES );
|
|
Index = 0;
|
|
while ((Length = wcslen( &lpBuffer[Index] )) != 0) {
|
|
OutputMessageLength( &lpBuffer[Index], Length );
|
|
OutputMessage( L" " );
|
|
Index += Length + 1;
|
|
}
|
|
OutputMessage( L"\r\n" );
|
|
|
|
} finally {
|
|
|
|
if (lpBuffer) {
|
|
free( lpBuffer );
|
|
}
|
|
|
|
}
|
|
return ExitCode;
|
|
}
|
|
|
|
|
|
INT
|
|
DriveType(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine describes the drive type of the drive passed in.
|
|
|
|
Arguments:
|
|
|
|
argc - The argument count
|
|
argv - Array of Strings of the form :
|
|
'fscutl dt <drive name>' or
|
|
'fscutl drivetype <drive name>'
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
{
|
|
if (argc != 1) {
|
|
DisplayMsg( MSG_USAGE_DRIVETYPE );
|
|
if (argc != 0) {
|
|
return EXIT_CODE_FAILURE;
|
|
} else {
|
|
return EXIT_CODE_SUCCESS;
|
|
}
|
|
}
|
|
|
|
switch (GetDriveType( argv[0] )) {
|
|
case DRIVE_NO_ROOT_DIR:
|
|
DisplayMsg( MSG_DRIVE_NO_ROOT_DIR, argv[0] );
|
|
break;
|
|
case DRIVE_REMOVABLE:
|
|
DisplayMsg( MSG_DRIVE_REMOVABLE, argv[0] );
|
|
break;
|
|
case DRIVE_FIXED:
|
|
DisplayMsg( MSG_DRIVE_FIXED, argv[0] );
|
|
break;
|
|
case DRIVE_REMOTE:
|
|
DisplayMsg( MSG_DRIVE_REMOTE, argv[0] );
|
|
break;
|
|
case DRIVE_CDROM:
|
|
DisplayMsg( MSG_DRIVE_CDROM, argv[0] );
|
|
break;
|
|
case DRIVE_RAMDISK:
|
|
DisplayMsg( MSG_DRIVE_RAMDISK, argv[0] );
|
|
break;
|
|
case DRIVE_UNKNOWN:
|
|
default:
|
|
DisplayMsg( MSG_DRIVE_UNKNOWN, argv[0] );
|
|
break;
|
|
}
|
|
return EXIT_CODE_SUCCESS;
|
|
}
|
|
|
|
|
|
INT
|
|
VolumeInfo(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine provides the information about the Volume.
|
|
|
|
Arguments:
|
|
|
|
argc - The argument count
|
|
argv - Array of Strings of the form :
|
|
'fscutl infov <root pathname>'.
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
{
|
|
LPWSTR lpVolumeNameBuffer = NULL; // address of name of the volume
|
|
DWORD nVolumeNameSize; // length of lpVolumeNameBuffer
|
|
LPDWORD lpVolumeSerialNumber = NULL; // address of volume serial number
|
|
LPDWORD lpMaximumComponentLength = NULL; // address of system's maximum
|
|
// filename length
|
|
LPDWORD lpFileSystemFlags = NULL; // address of file system flags
|
|
LPWSTR lpFileSystemNameBuffer = NULL; // address of name of file system
|
|
DWORD nFileSystemNameSize; // length of lpFileSystemNameBuffer
|
|
BOOL Status; // return status
|
|
DWORD dwMask; // FileSystem Flag Mask
|
|
DWORD Index;
|
|
DWORD FsFlag;
|
|
INT ExitCode = EXIT_CODE_SUCCESS;
|
|
|
|
|
|
try {
|
|
|
|
if (argc != 1) {
|
|
DisplayMsg( MSG_USAGE_INFOV );
|
|
if (argc != 0) {
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
}
|
|
leave ;
|
|
}
|
|
|
|
nVolumeNameSize = MAX_PATH;
|
|
|
|
lpVolumeNameBuffer = (LPWSTR) malloc ( MAX_PATH * sizeof(WCHAR) );
|
|
if (lpVolumeNameBuffer == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
lpVolumeSerialNumber = (LPDWORD) malloc( sizeof(DWORD) );
|
|
if (lpVolumeSerialNumber == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
lpFileSystemFlags = (LPDWORD) malloc ( sizeof(DWORD) );
|
|
if (lpFileSystemFlags == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
lpMaximumComponentLength = (LPDWORD) malloc ( sizeof(DWORD) );
|
|
if (lpMaximumComponentLength == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
nFileSystemNameSize = MAX_PATH;
|
|
lpFileSystemNameBuffer = (LPWSTR) malloc ( MAX_PATH * sizeof(WCHAR) );
|
|
if (lpFileSystemNameBuffer == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
Status = GetVolumeInformation (
|
|
argv[0],
|
|
lpVolumeNameBuffer,
|
|
nVolumeNameSize,
|
|
lpVolumeSerialNumber,
|
|
lpMaximumComponentLength,
|
|
lpFileSystemFlags,
|
|
lpFileSystemNameBuffer,
|
|
nFileSystemNameSize
|
|
);
|
|
if (!Status) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
DisplayMsg( MSG_VOLNAME, lpVolumeNameBuffer );
|
|
DisplayMsg( MSG_SERIALNO, *lpVolumeSerialNumber );
|
|
DisplayMsg( MSG_MAX_COMP_LEN, *lpMaximumComponentLength );
|
|
DisplayMsg( MSG_FS_NAME, lpFileSystemNameBuffer );
|
|
|
|
dwMask = 1 ;
|
|
FsFlag = *lpFileSystemFlags;
|
|
|
|
for ( Index=0 ; Index<32 ; Index++ ) {
|
|
switch (FsFlag & dwMask) {
|
|
case FILE_CASE_SENSITIVE_SEARCH:
|
|
DisplayMsg( MSG_FILE_CASE_SENSITIVE_SEARCH );
|
|
break;
|
|
|
|
case FILE_CASE_PRESERVED_NAMES:
|
|
DisplayMsg( MSG_FILE_CASE_PRESERVED_NAMES );
|
|
break;
|
|
|
|
case FILE_UNICODE_ON_DISK:
|
|
DisplayMsg( MSG_FILE_UNICODE_ON_DISK );
|
|
break;
|
|
|
|
case FILE_PERSISTENT_ACLS:
|
|
DisplayMsg( MSG_FILE_PERSISTENT_ACLS );
|
|
break;
|
|
|
|
case FILE_FILE_COMPRESSION:
|
|
DisplayMsg( MSG_FILE_FILE_COMPRESSION );
|
|
break;
|
|
|
|
case FILE_VOLUME_QUOTAS:
|
|
DisplayMsg( MSG_FILE_VOLUME_QUOTAS );
|
|
break;
|
|
|
|
case FILE_SUPPORTS_SPARSE_FILES:
|
|
DisplayMsg( MSG_FILE_SUPPORTS_SPARSE_FILES );
|
|
break;
|
|
|
|
case FILE_SUPPORTS_REPARSE_POINTS:
|
|
DisplayMsg( MSG_FILE_SUPPORTS_REPARSE_POINTS );
|
|
break;
|
|
|
|
case FILE_SUPPORTS_REMOTE_STORAGE:
|
|
DisplayMsg( MSG_FILE_SUPPORTS_REMOTE_STORAGE );
|
|
break;
|
|
|
|
case FILE_VOLUME_IS_COMPRESSED:
|
|
DisplayMsg( MSG_FILE_VOLUME_IS_COMPRESSED );
|
|
break;
|
|
|
|
case FILE_SUPPORTS_OBJECT_IDS:
|
|
DisplayMsg( MSG_FILE_SUPPORTS_OBJECT_IDS );
|
|
break;
|
|
|
|
case FILE_SUPPORTS_ENCRYPTION:
|
|
DisplayMsg( MSG_FILE_SUPPORTS_ENCRYPTION );
|
|
break;
|
|
|
|
case FILE_NAMED_STREAMS:
|
|
DisplayMsg( MSG_FILE_NAMED_STREAMS );
|
|
break;
|
|
}
|
|
dwMask <<= 1;
|
|
}
|
|
|
|
} finally {
|
|
|
|
free( lpVolumeNameBuffer );
|
|
free( lpVolumeSerialNumber );
|
|
free( lpFileSystemFlags );
|
|
free( lpMaximumComponentLength );
|
|
free( lpFileSystemNameBuffer );
|
|
}
|
|
|
|
return ExitCode;
|
|
}
|
|
|
|
|
|
INT
|
|
GetNtfsVolumeData(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine gets the NTFS volume data for the volume
|
|
specified.
|
|
|
|
Arguments:
|
|
|
|
argc - The argument count.
|
|
argv - Array of Strings of the form :
|
|
' fscutl getntfsdv <volume pathname>'.
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
{
|
|
HANDLE FileHandle = INVALID_HANDLE_VALUE;
|
|
WCHAR FileName[MAX_PATH];
|
|
BOOL Status;
|
|
BYTE Buffer[sizeof( NTFS_VOLUME_DATA_BUFFER ) + sizeof( NTFS_EXTENDED_VOLUME_DATA )];
|
|
PNTFS_VOLUME_DATA_BUFFER pvdb = (PNTFS_VOLUME_DATA_BUFFER)Buffer;
|
|
PNTFS_EXTENDED_VOLUME_DATA pevd = (PNTFS_EXTENDED_VOLUME_DATA)(pvdb + 1);
|
|
DWORD BytesReturned;
|
|
INT ExitCode = EXIT_CODE_SUCCESS;
|
|
|
|
try {
|
|
|
|
if (argc != 1) {
|
|
DisplayMsg( MSG_USAGE_NTFSINFO );
|
|
if (argc != 0) {
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
}
|
|
leave;
|
|
}
|
|
|
|
if (!IsVolumeLocalNTFS( argv[0][0] )) {
|
|
DisplayMsg( MSG_NTFS_REQUIRED );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
if (wcslen( DotPrefix ) + wcslen( argv[0] ) + 1 > MAX_PATH) {
|
|
DisplayMsg( MSG_FILENAME_TOO_LONG );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
wcscpy( FileName, DotPrefix );
|
|
wcscat( FileName, argv[0] );
|
|
|
|
FileHandle = CreateFile(
|
|
FileName,
|
|
GENERIC_READ,
|
|
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
|
NULL,
|
|
OPEN_EXISTING,
|
|
FILE_ATTRIBUTE_NORMAL,
|
|
NULL
|
|
);
|
|
if (FileHandle == INVALID_HANDLE_VALUE) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
Status = DeviceIoControl(
|
|
FileHandle,
|
|
FSCTL_GET_NTFS_VOLUME_DATA,
|
|
NULL,
|
|
0,
|
|
pvdb,
|
|
sizeof( Buffer ),
|
|
&BytesReturned,
|
|
(LPOVERLAPPED)NULL
|
|
);
|
|
if (!Status) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
DisplayMsg(
|
|
MSG_NTFSINFO_STATS,
|
|
QuadToPaddedHexText( pvdb->VolumeSerialNumber.QuadPart ), // Serial number in hex
|
|
pevd->MajorVersion,
|
|
pevd->MinorVersion,
|
|
QuadToPaddedHexText( pvdb->NumberSectors.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->TotalClusters.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->FreeClusters.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->TotalReserved.QuadPart ),
|
|
pvdb->BytesPerSector,
|
|
pvdb->BytesPerCluster,
|
|
pvdb->BytesPerFileRecordSegment,
|
|
pvdb->ClustersPerFileRecordSegment,
|
|
QuadToPaddedHexText( pvdb->MftValidDataLength.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->MftStartLcn.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->Mft2StartLcn.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->MftZoneStart.QuadPart ),
|
|
QuadToPaddedHexText( pvdb->MftZoneEnd.QuadPart )
|
|
);
|
|
|
|
} finally {
|
|
|
|
if (FileHandle != INVALID_HANDLE_VALUE) {
|
|
CloseHandle( FileHandle );
|
|
}
|
|
|
|
}
|
|
return ExitCode;
|
|
}
|
|
|
|
|
|
INT
|
|
GetFileSystemStatistics(
|
|
IN INT argc,
|
|
IN PWSTR argv[]
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine gets the file system statistics for the volume
|
|
specified.
|
|
|
|
Arguments:
|
|
|
|
argc - The argument count.
|
|
argv - Array of Strings of the form :
|
|
' fscutl getfss <volume pathname>'.
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
{
|
|
#define FS_STAT(_f) FsStat( FsStats, StrucSize, offsetof(FILESYSTEM_STATISTICS,_f), SysInfo.dwNumberOfProcessors )
|
|
#define FAT_STAT(_f) FsStat( FatFsStats, StrucSize, offsetof(FAT_FILE_SYSTEM_STATISTICS,_f), SysInfo.dwNumberOfProcessors )
|
|
#define NTFS_STAT(_f) FsStat( NtfsFsStats, StrucSize, offsetof(NTFS_FILE_SYSTEM_STATISTICS,_f), SysInfo.dwNumberOfProcessors )
|
|
|
|
BOOL Status;
|
|
HANDLE FileHandle = INVALID_HANDLE_VALUE;
|
|
WCHAR FileName[MAX_PATH];
|
|
PFILESYSTEM_STATISTICS FsStats = NULL;
|
|
DWORD OutBufferSize;
|
|
DWORD BytesReturned;
|
|
SYSTEM_INFO SysInfo;
|
|
PNTFS_FILE_SYSTEM_STATISTICS NtfsFsStats = NULL;
|
|
PFAT_FILE_SYSTEM_STATISTICS FatFsStats = NULL;
|
|
ULONG StrucSize;
|
|
INT ExitCode = EXIT_CODE_SUCCESS;
|
|
|
|
try {
|
|
|
|
if (argc != 1) {
|
|
DisplayMsg( MSG_USAGE_GETFSS );
|
|
if (argc != 0) {
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
}
|
|
leave;
|
|
}
|
|
|
|
if (!IsVolumeLocalNTFS( argv[0][0] )) {
|
|
DisplayMsg( MSG_NTFS_REQUIRED );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
if (wcslen( DotPrefix ) + wcslen( argv[0] ) + 1 > MAX_PATH) {
|
|
DisplayMsg( MSG_FILENAME_TOO_LONG );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
wcscpy( FileName, DotPrefix );
|
|
wcscat( FileName, argv[0] );
|
|
|
|
FileHandle = CreateFile(
|
|
FileName,
|
|
GENERIC_READ,
|
|
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
|
NULL,
|
|
OPEN_EXISTING,
|
|
FILE_ATTRIBUTE_NORMAL,
|
|
NULL
|
|
);
|
|
if (FileHandle == INVALID_HANDLE_VALUE) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
GetSystemInfo( &SysInfo );
|
|
|
|
OutBufferSize = max(sizeof(NTFS_FILE_SYSTEM_STATISTICS),sizeof(FAT_FILE_SYSTEM_STATISTICS)) * SysInfo.dwNumberOfProcessors;
|
|
|
|
FsStats = (PFILESYSTEM_STATISTICS) malloc ( OutBufferSize );
|
|
if (FsStats == NULL) {
|
|
DisplayErrorMsg( ERROR_NOT_ENOUGH_MEMORY );
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
Status = DeviceIoControl(
|
|
FileHandle,
|
|
FSCTL_FILESYSTEM_GET_STATISTICS,
|
|
NULL,
|
|
0,
|
|
FsStats,
|
|
OutBufferSize,
|
|
&BytesReturned,
|
|
(LPOVERLAPPED)NULL
|
|
);
|
|
if (!Status) {
|
|
DisplayError();
|
|
ExitCode = EXIT_CODE_FAILURE;
|
|
leave;
|
|
}
|
|
|
|
switch (FsStats->FileSystemType) {
|
|
case FILESYSTEM_STATISTICS_TYPE_NTFS:
|
|
DisplayMsg( MSG_FSTYPE_NTFS );
|
|
NtfsFsStats = (PNTFS_FILE_SYSTEM_STATISTICS) FsStats;
|
|
StrucSize = sizeof(NTFS_FILE_SYSTEM_STATISTICS);
|
|
break;
|
|
|
|
case FILESYSTEM_STATISTICS_TYPE_FAT:
|
|
DisplayMsg( MSG_FSTYPE_FAT );
|
|
FatFsStats = (PFAT_FILE_SYSTEM_STATISTICS) FsStats;
|
|
StrucSize = sizeof(FAT_FILE_SYSTEM_STATISTICS);
|
|
break;
|
|
}
|
|
|
|
DisplayMsg(
|
|
MSG_GENERAL_FSSTAT,
|
|
QuadToDecimalText( FS_STAT(UserFileReads)),
|
|
QuadToDecimalText( FS_STAT(UserFileReadBytes)),
|
|
QuadToDecimalText( FS_STAT(UserDiskReads)),
|
|
QuadToDecimalText( FS_STAT(UserFileWrites)),
|
|
QuadToDecimalText( FS_STAT(UserFileWriteBytes)),
|
|
QuadToDecimalText( FS_STAT(UserDiskWrites)),
|
|
QuadToDecimalText( FS_STAT(MetaDataReads)),
|
|
QuadToDecimalText( FS_STAT(MetaDataReadBytes)),
|
|
QuadToDecimalText( FS_STAT(MetaDataDiskReads)),
|
|
QuadToDecimalText( FS_STAT(MetaDataWrites)),
|
|
QuadToDecimalText( FS_STAT(MetaDataWriteBytes)),
|
|
QuadToDecimalText( FS_STAT(MetaDataDiskWrites))
|
|
);
|
|
|
|
//
|
|
// Print FileSystem specific data
|
|
//
|
|
|
|
switch (FsStats->FileSystemType) {
|
|
case FILESYSTEM_STATISTICS_TYPE_FAT:
|
|
DisplayMsg(
|
|
MSG_FAT_FSSTA,
|
|
QuadToDecimalText( FAT_STAT(Fat.CreateHits)),
|
|
QuadToDecimalText( FAT_STAT(Fat.SuccessfulCreates)),
|
|
QuadToDecimalText( FAT_STAT(Fat.FailedCreates)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedReads)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedReadBytes)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedWrites)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedWriteBytes)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedDiskReads)),
|
|
QuadToDecimalText( FAT_STAT(Fat.NonCachedDiskWrites))
|
|
);
|
|
break;
|
|
|
|
case FILESYSTEM_STATISTICS_TYPE_NTFS:
|
|
DisplayMsg(
|
|
MSG_NTFS_FSSTA,
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftWriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.Mft2Writes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.Mft2WriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.RootIndexReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.RootIndexReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.RootIndexWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.RootIndexWriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.BitmapReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.BitmapReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.BitmapWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.BitmapWriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftBitmapReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftBitmapReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftBitmapWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.MftBitmapWriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.UserIndexReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.UserIndexReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.UserIndexWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.UserIndexWriteBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.LogFileReads)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.LogFileReadBytes)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.LogFileWrites)),
|
|
QuadToDecimalText( NTFS_STAT(Ntfs.LogFileWriteBytes))
|
|
);
|
|
|
|
//
|
|
// Still some more fields left
|
|
//
|
|
break;
|
|
}
|
|
|
|
} finally {
|
|
|
|
if (FileHandle != INVALID_HANDLE_VALUE) {
|
|
CloseHandle( FileHandle );
|
|
}
|
|
if (FsStats) {
|
|
free( FsStats );
|
|
}
|
|
|
|
}
|
|
return ExitCode;
|
|
}
|
|
|