Source code of Windows XP (NT5)
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.

208 lines
7.3 KiB

  1. /*++
  2. Copyright (c) 1998 Microsoft Corporation
  3. Module Name:
  4. FTMan
  5. File Name:
  6. DiskMap.h
  7. Abstract:
  8. Definition of classes used to keep the disk array map in memory. Used in retrieving partitions and free spaces,
  9. in creating and deleting partitions
  10. Author:
  11. Cristian Teodorescu November 20, 1998
  12. Notes:
  13. Revision History:
  14. --*/
  15. /////////////////////////////////////////////////////////////////////////////
  16. #if !defined(AFX_DISKMAP_H_INCLUDED_)
  17. #define AFX_DISKMAP_H_INCLUDED_
  18. #if _MSC_VER > 1000
  19. #pragma once
  20. #endif // _MSC_VER > 1000
  21. #include <winioctl.h>
  22. #include "FTManDef.h"
  23. ////////////////////////////////////////////////////////////////////////////////////////////////////
  24. // Class CDiskMap
  25. class CItemData;
  26. class CDiskMap
  27. {
  28. public:
  29. // Constructor
  30. CDiskMap();
  31. // Constructor providing the disk number
  32. CDiskMap( DWORD dwDiskNumber );
  33. ~CDiskMap();
  34. // Operations
  35. public:
  36. // Set the disk number and reset m_bLoaded
  37. void SetDiskNumber( DWORD dwDiskNumber );
  38. // Load disk layout and geometry
  39. BOOL LoadDiskInfo( CString& strErrors, BOOL& bMissingDisk );
  40. // Save the disk layout on disk
  41. BOOL SaveDiskInfo( CString& strErrors, BOOL& bMissingDisk );
  42. // Retrieve all non-container partitions on the disk and create CPhysicalPartitionData instances for them
  43. // If the disk info is not loaded the method calls LoadDiskInfo first
  44. BOOL ReadPartitions( CObArray& arrPartitions, CString& strErrors, BOOL& bMissingDisk, CItemData* pParentData = NULL );
  45. // Retrieve all free spaces on the disk and create CFreeSpaceData instances for them
  46. // If the disk info is not loaded the method calls LoadDiskInfo first
  47. BOOL ReadFreeSpaces( CObArray& arrFreeSpaces, CString& strErrors, BOOL& bMissingDisk, CItemData* pParentData = NULL );
  48. // Retrieve a non-container partition information from the disk layout given the partition offset
  49. BOOL ReadPartitionInformation( LONGLONG llPartStartOffset, PARTITION_INFORMATION& partInfo,
  50. PARTITION_TYPE& wPartitionType, CString& strErrors, BOOL& bMissingDisk );
  51. // Delete a non-container partition from the disk
  52. BOOL DeletePartition( LONGLONG llPartStartOffset );
  53. // Deletes an extended partition from the disk
  54. // The extended partition should not be contained by another extended partition
  55. BOOL DeleteExtendedPartition( LONGLONG llPartStartOffset );
  56. // Create a partition on the disk ( m_dwDiskNumber )
  57. BOOL CreatePartition( LONGLONG llPartStartOffset, LONGLONG llPartSize, LONGLONG& llExactPartStartOffset );
  58. // Create an extended partition on the disk ( m_dwDiskNumber )
  59. BOOL CreateExtendedPartition( LONGLONG llPartStartOffset, LONGLONG llPartSize, LONGLONG& llNewFreeSpaceOffset );
  60. //Data members
  61. public:
  62. protected:
  63. // Disk number
  64. DWORD m_dwDiskNumber;
  65. // Disk geometry
  66. LONGLONG m_llTrackSize;
  67. LONGLONG m_llSectorSize;
  68. LONGLONG m_llCylinderSize;
  69. LONGLONG m_llDiskSize;
  70. // Pointer to the drive layout buffer
  71. PDRIVE_LAYOUT_INFORMATION m_pBuffer;
  72. // The size of the drive layout buffer
  73. DWORD m_dwBufferSize;
  74. // Is the information related to disk m_dwDiskNumber loaded into this object ?
  75. BOOL m_bLoaded;
  76. protected:
  77. // Some recursive methods
  78. // Given an extended partition table index in m_pBuffer->PartitionInfo, scan recursively
  79. // the extended partition tree and find the chunk of m_pBuffer->PartitionInfo filled with
  80. // members of the extended partition
  81. // Then return the next index. This index is the index of the following extended partition
  82. // from the same ( or superior ) level as the given extended partition
  83. DWORD GetNextIndex( DWORD dwTableIndex );
  84. // Search for free spaces inside an extended partition given its starting offset, size and partitions table
  85. // index inside m_pBuffer
  86. // For every found free space create a CFreeSpace instance and add it to arrFreeSpaces
  87. void GetExtendedPartitionFreeSpaces( LONGLONG llExtPartStartOffset, LONGLONG llExtPartEndOffset,
  88. DWORD dwTableIndex, DWORD& dwNextIndex, CObArray& arrFreeSpaces,
  89. CItemData* pParentData = NULL );
  90. // Search recursively for a partition inside an extended partition
  91. // This method may be called also to search for a partition inside the whole disk.
  92. BOOL SearchForPartitionInExtendedPartition( LONGLONG llPartOffset, DWORD dwExtPartIndex, DWORD dwTableIndex,
  93. DWORD& dwNextIndex, DWORD& dwPartIndex, DWORD& dwParentIndex );
  94. // Given an offset and size search recursively for an appropriate free space
  95. // inside an extended partition ( or the whole disk ).
  96. // Return the start and end offset of the whole free space and the index in the partition table
  97. // where a new partition having the given offset and size might be inserted.
  98. BOOL SearchForFreeSpaceInExtendedPartition( LONGLONG llOffset, LONGLONG llSize, LONGLONG llExtPartStartOffset,
  99. LONGLONG llExtPartEndOffset, DWORD dwTableIndex,
  100. LONGLONG& llFreeSpaceStartOffset, LONGLONG& llFreeSpaceEndOffset,
  101. BOOL &bAtBeginningOfExtendedPartition, DWORD& dwNewPartIndex);
  102. // Sort a partition table by starting offset without actually changing the table
  103. DWORD SortPartitionsByOffset( PARTITION_INFORMATION* arrTable, DWORD dwSize, DWORD* arrOrder );
  104. // Get the greatest cylinder border less than or equal with an offset
  105. LONGLONG GetCylinderBorderBefore( LONGLONG llOffset );
  106. // Get the lowest cylinder border greater than or equal with an offset
  107. LONGLONG GetCylinderBorderAfter( LONGLONG llOffset );
  108. // Delete a partition from m_pBuffer->PartitionInfo table
  109. void DeletePartitionFromTable( DWORD dwPartIndex );
  110. // Update / Delete an extended partition after one of its members was deleted
  111. // If the extended partition remains empty then it must be deleted
  112. // If only one member is left and this member is an extended partition too then replace the
  113. // extended partition with its member ( promote the member on the superior level )
  114. // All other situations are unlikely to happen so I don't treat them here
  115. void UpdateExtendedPartitionAfterMemberDeletion( DWORD dwPartIndex, DWORD dwTableIndex );
  116. // Add a new container partition AND/OR a new non-container partition to m_pBuffer->PartitionInfo table
  117. // and make all necessary changes to the partition table
  118. BOOL AddPartitionToTable( LONGLONG llPartStartOffset, LONGLONG llPartSize,
  119. DWORD dwNewPartIndex, BOOL bCreateContainer, BOOL bCreateNonContainer );
  120. // Fill a PARTITION_INFORMATION structure with the info of a new partition
  121. void FillNewPartitionInfo( LONGLONG llPartStartOffset, LONGLONG llPartSize,
  122. PARTITION_INFORMATION* pPartInfo, BOOL bContainer );
  123. // Add a error message to a string
  124. // The error message will be formatted like this:
  125. // <Disk Number: >< My error message > [ System error message ]
  126. void AddError( CString& strErrors, UINT unErrorMsg, BOOL bAddSystemMsg = FALSE );
  127. };
  128. inline CDiskMap::CDiskMap()
  129. : m_dwDiskNumber(-1), m_pBuffer(NULL), m_dwBufferSize(0), m_bLoaded(FALSE)
  130. {
  131. }
  132. inline CDiskMap::CDiskMap( DWORD dwDiskNumber )
  133. : m_dwDiskNumber( dwDiskNumber ), m_pBuffer(NULL), m_dwBufferSize(0), m_bLoaded(FALSE)
  134. {
  135. ASSERT( dwDiskNumber >= 0 );
  136. }
  137. inline CDiskMap::~CDiskMap()
  138. {
  139. if( m_pBuffer )
  140. LocalFree( m_pBuffer );
  141. }
  142. inline void CDiskMap::SetDiskNumber( DWORD dwDiskNumber )
  143. {
  144. ASSERT( dwDiskNumber >= 0 );
  145. if( m_dwDiskNumber != dwDiskNumber )
  146. {
  147. m_dwDiskNumber = dwDiskNumber;
  148. m_bLoaded = FALSE;
  149. }
  150. }
  151. #endif // !defined(AFX_DISKMAP_H_INCLUDED_)