ReactOS  0.4.13-dev-257-gfabbd7c
partlist.c File Reference
#include "precomp.h"
#include <ntddscsi.h>
#include "partlist.h"
#include "fsutil.h"
#include <debug.h>
#include <pshpack1.h>
#include <poppack.h>
Include dependency graph for partlist.c:

Go to the source code of this file.

Classes

struct  _REG_DISK_MOUNT_INFO
 

Macros

#define NDEBUG
 
#define ROOT_NAME   L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION\\System\\MultifunctionAdapter"
 

Typedefs

typedef struct _REG_DISK_MOUNT_INFO REG_DISK_MOUNT_INFO
 
typedef struct _REG_DISK_MOUNT_INFOPREG_DISK_MOUNT_INFO
 

Functions

ULONGLONG AlignDown (IN ULONGLONG Value, IN ULONG Alignment)
 
ULONGLONG AlignUp (IN ULONGLONG Value, IN ULONG Alignment)
 
ULONGLONG RoundingDivide (IN ULONGLONG Dividend, IN ULONGLONG Divisor)
 
static VOID GetDriverName (IN PDISKENTRY DiskEntry)
 
static VOID AssignDriveLetters (IN PPARTLIST List)
 
static NTSTATUS NTAPI DiskIdentifierQueryRoutine (PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
 
static NTSTATUS NTAPI DiskConfigurationDataQueryRoutine (PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
 
static NTSTATUS NTAPI SystemConfigurationDataQueryRoutine (PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
 
static VOID EnumerateBiosDiskEntries (IN PPARTLIST PartList)
 
BOOLEAN IsSuperFloppy (IN PDISKENTRY DiskEntry)
 
static VOID InsertDiskRegion (IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN BOOLEAN LogicalPartition)
 
static PPARTENTRY CreateInsertBlankRegion (IN PDISKENTRY DiskEntry, IN OUT PLIST_ENTRY ListHead, IN ULONGLONG StartSector, IN ULONGLONG SectorCount, IN BOOLEAN LogicalSpace)
 
static PPARTENTRY InitializePartitionEntry (IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
 
static VOID AddPartitionToDisk (IN ULONG DiskNumber, IN PDISKENTRY DiskEntry, IN ULONG PartitionIndex, IN BOOLEAN LogicalPartition)
 
static VOID ScanForUnpartitionedDiskSpace (IN PDISKENTRY DiskEntry)
 
static VOID SetDiskSignature (IN PPARTLIST List, IN PDISKENTRY DiskEntry)
 
static VOID UpdateDiskSignatures (IN PPARTLIST List)
 
static VOID UpdateHwDiskNumbers (IN PPARTLIST List)
 
static VOID AddDiskToList (IN HANDLE FileHandle, IN ULONG DiskNumber, IN PPARTLIST List)
 
PPARTLIST CreatePartitionList (VOID)
 
VOID DestroyPartitionList (IN PPARTLIST List)
 
PDISKENTRY GetDiskByBiosNumber (IN PPARTLIST List, IN ULONG HwDiskNumber)
 
PDISKENTRY GetDiskByNumber (IN PPARTLIST List, IN ULONG DiskNumber)
 
PDISKENTRY GetDiskBySCSI (IN PPARTLIST List, IN USHORT Port, IN USHORT Bus, IN USHORT Id)
 
PDISKENTRY GetDiskBySignature (IN PPARTLIST List, IN ULONG Signature)
 
PPARTENTRY GetPartition (IN PDISKENTRY DiskEntry, IN ULONG PartitionNumber)
 
BOOLEAN GetDiskOrPartition (IN PPARTLIST List, IN ULONG DiskNumber, IN ULONG PartitionNumber OPTIONAL, OUT PDISKENTRY *pDiskEntry, OUT PPARTENTRY *pPartEntry OPTIONAL)
 
PPARTENTRY SelectPartition (IN PPARTLIST List, IN ULONG DiskNumber, IN ULONG PartitionNumber)
 
PPARTENTRY GetNextPartition (IN PPARTLIST List, IN PPARTENTRY CurrentPart OPTIONAL)
 
PPARTENTRY GetPrevPartition (IN PPARTLIST List, IN PPARTENTRY CurrentPart OPTIONAL)
 
FORCEINLINE BOOLEAN IsEmptyLayoutEntry (IN PPARTITION_INFORMATION PartitionInfo)
 
FORCEINLINE BOOLEAN IsSamePrimaryLayoutEntry (IN PPARTITION_INFORMATION PartitionInfo, IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry)
 
static ULONG GetPrimaryPartitionCount (IN PDISKENTRY DiskEntry)
 
static ULONG GetLogicalPartitionCount (IN PDISKENTRY DiskEntry)
 
static BOOLEAN ReAllocateLayoutBuffer (IN PDISKENTRY DiskEntry)
 
static VOID UpdateDiskLayout (IN PDISKENTRY DiskEntry)
 
static PPARTENTRY GetPrevUnpartitionedEntry (IN PPARTENTRY PartEntry)
 
static PPARTENTRY GetNextUnpartitionedEntry (IN PPARTENTRY PartEntry)
 
BOOLEAN CreatePrimaryPartition (IN PPARTLIST List, IN PPARTENTRY SelectedEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
 
static VOID AddLogicalDiskSpace (IN PDISKENTRY DiskEntry)
 
BOOLEAN CreateExtendedPartition (IN PPARTLIST List, IN PPARTENTRY SelectedEntry, IN ULONGLONG SectorCount)
 
BOOLEAN CreateLogicalPartition (IN PPARTLIST List, IN PPARTENTRY SelectedEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
 
static NTSTATUS DismountVolume (IN PPARTENTRY PartEntry)
 
BOOLEAN DeletePartition (IN PPARTLIST List, IN PPARTENTRY PartEntry, OUT PPARTENTRY *FreeRegion OPTIONAL)
 
static PPARTENTRY GetActiveDiskPartition (IN PDISKENTRY DiskEntry)
 
static BOOLEAN IsSupportedActivePartition (IN PPARTENTRY PartEntry)
 
VOID CheckActiveSystemPartition (IN PPARTLIST List, IN BOOLEAN ForceSelect, IN PDISKENTRY AlternateDisk OPTIONAL, IN PPARTENTRY AlternatePart OPTIONAL)
 
NTSTATUS WritePartitions (IN PDISKENTRY DiskEntry)
 
BOOLEAN WritePartitionsToDisk (IN PPARTLIST List)
 
BOOLEAN SetMountedDeviceValue (IN WCHAR Letter, IN ULONG Signature, IN LARGE_INTEGER StartingOffset)
 
BOOLEAN SetMountedDeviceValues (IN PPARTLIST List)
 
VOID SetPartitionType (IN PPARTENTRY PartEntry, IN UCHAR PartitionType)
 
ERROR_NUMBER PrimaryPartitionCreationChecks (IN PPARTENTRY PartEntry)
 
ERROR_NUMBER ExtendedPartitionCreationChecks (IN PPARTENTRY PartEntry)
 
ERROR_NUMBER LogicalPartitionCreationChecks (IN PPARTENTRY PartEntry)
 
BOOLEAN GetNextUnformattedPartition (IN PPARTLIST List, OUT PDISKENTRY *pDiskEntry OPTIONAL, OUT PPARTENTRY *pPartEntry)
 
BOOLEAN GetNextUncheckedPartition (IN PPARTLIST List, OUT PDISKENTRY *pDiskEntry OPTIONAL, OUT PPARTENTRY *pPartEntry)
 

Variables

PARTITION_TYPE PartitionTypes [NUM_PARTITION_TYPE_ENTRIES]
 

Macro Definition Documentation

◆ NDEBUG

#define NDEBUG

Definition at line 15 of file partlist.c.

◆ ROOT_NAME

#define ROOT_NAME   L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION\\System\\MultifunctionAdapter"

Typedef Documentation

◆ PREG_DISK_MOUNT_INFO

◆ REG_DISK_MOUNT_INFO

Function Documentation

◆ AddDiskToList()

static VOID AddDiskToList ( IN HANDLE  FileHandle,
IN ULONG  DiskNumber,
IN PPARTLIST  List 
)
static

Definition at line 1435 of file partlist.c.

1439 {
1440  DISK_GEOMETRY DiskGeometry;
1441  SCSI_ADDRESS ScsiAddress;
1442  PDISKENTRY DiskEntry;
1444  NTSTATUS Status;
1445  PPARTITION_SECTOR Mbr;
1446  PULONG Buffer;
1448  WCHAR Identifier[20];
1449  ULONG Checksum;
1450  ULONG Signature;
1451  ULONG i;
1452  PLIST_ENTRY ListEntry;
1453  PBIOSDISKENTRY BiosDiskEntry;
1454  ULONG LayoutBufferSize;
1455  PDRIVE_LAYOUT_INFORMATION NewLayoutBuffer;
1456 
1457  /* Retrieve the drive geometry */
1459  NULL,
1460  NULL,
1461  NULL,
1462  &Iosb,
1464  NULL,
1465  0,
1466  &DiskGeometry,
1467  sizeof(DiskGeometry));
1468  if (!NT_SUCCESS(Status))
1469  return;
1470 
1471  if (DiskGeometry.MediaType != FixedMedia &&
1472  DiskGeometry.MediaType != RemovableMedia)
1473  {
1474  return;
1475  }
1476 
1477  /*
1478  * FIXME: Here we suppose the disk is always SCSI. What if it is
1479  * of another type? To check this we need to retrieve the name of
1480  * the driver the disk device belongs to.
1481  */
1483  NULL,
1484  NULL,
1485  NULL,
1486  &Iosb,
1488  NULL,
1489  0,
1490  &ScsiAddress,
1491  sizeof(ScsiAddress));
1492  if (!NT_SUCCESS(Status))
1493  return;
1494 
1495  /*
1496  * Check whether the disk is initialized, by looking at its MBR.
1497  * NOTE that this must be generalized to GPT disks as well!
1498  */
1499 
1501  0,
1502  DiskGeometry.BytesPerSector);
1503  if (Mbr == NULL)
1504  return;
1505 
1506  FileOffset.QuadPart = 0;
1508  NULL,
1509  NULL,
1510  NULL,
1511  &Iosb,
1512  (PVOID)Mbr,
1513  DiskGeometry.BytesPerSector,
1514  &FileOffset,
1515  NULL);
1516  if (!NT_SUCCESS(Status))
1517  {
1518  RtlFreeHeap(ProcessHeap, 0, Mbr);
1519  DPRINT1("NtReadFile failed, status=%x\n", Status);
1520  return;
1521  }
1522  Signature = Mbr->Signature;
1523 
1524  /* Calculate the MBR checksum */
1525  Checksum = 0;
1526  Buffer = (PULONG)Mbr;
1527  for (i = 0; i < 128; i++)
1528  {
1529  Checksum += Buffer[i];
1530  }
1531  Checksum = ~Checksum + 1;
1532 
1533  RtlStringCchPrintfW(Identifier, ARRAYSIZE(Identifier),
1534  L"%08x-%08x-%c",
1535  Checksum, Signature,
1536  (Mbr->Magic == PARTITION_MAGIC) ? L'A' : L'X');
1537  DPRINT("Identifier: %S\n", Identifier);
1538 
1539  DiskEntry = RtlAllocateHeap(ProcessHeap,
1541  sizeof(DISKENTRY));
1542  if (DiskEntry == NULL)
1543  {
1544  RtlFreeHeap(ProcessHeap, 0, Mbr);
1545  DPRINT1("Failed to allocate a new disk entry.\n");
1546  return;
1547  }
1548 
1549  DiskEntry->PartList = List;
1550 
1551 #if 0
1552  {
1553  FILE_FS_DEVICE_INFORMATION FileFsDevice;
1554 
1555  /* Query the device for its type */
1557  &Iosb,
1558  &FileFsDevice,
1559  sizeof(FileFsDevice),
1561  if (!NT_SUCCESS(Status))
1562  {
1563  DPRINT1("Couldn't detect device type for disk %lu of identifier '%S'...\n", DiskNumber, Identifier);
1564  }
1565  else
1566  {
1567  DPRINT1("Disk %lu : DeviceType: 0x%08x ; Characteristics: 0x%08x\n", DiskNumber, FileFsDevice.DeviceType, FileFsDevice.Characteristics);
1568  }
1569  }
1570  // NOTE: We may also use NtQueryVolumeInformationFile(FileFsDeviceInformation).
1571 #endif
1572  DiskEntry->MediaType = DiskGeometry.MediaType;
1573  if (DiskEntry->MediaType == RemovableMedia)
1574  {
1575  DPRINT1("Disk %lu of identifier '%S' is removable\n", DiskNumber, Identifier);
1576  }
1577  else // if (DiskEntry->MediaType == FixedMedia)
1578  {
1579  DPRINT1("Disk %lu of identifier '%S' is fixed\n", DiskNumber, Identifier);
1580  }
1581 
1582 // DiskEntry->Checksum = Checksum;
1583 // DiskEntry->Signature = Signature;
1584  DiskEntry->BiosFound = FALSE;
1585 
1586  /*
1587  * Check if this disk has a valid MBR: verify its signature,
1588  * and whether its two first bytes are a valid instruction
1589  * (related to this, see IsThereAValidBootSector() in partlist.c).
1590  *
1591  * See also ntoskrnl/fstub/fstubex.c!FstubDetectPartitionStyle().
1592  */
1593 
1594  // DiskEntry->NoMbr = (Mbr->Magic != PARTITION_MAGIC || (*(PUSHORT)Mbr->BootCode) == 0x0000);
1595 
1596  /* If we have not the 0xAA55 then it's raw partition */
1597  if (Mbr->Magic != PARTITION_MAGIC)
1598  {
1599  DiskEntry->DiskStyle = PARTITION_STYLE_RAW;
1600  }
1601  /* Check partitions types: if first is 0xEE and all the others 0, we have GPT */
1602  else if (Mbr->Partition[0].PartitionType == EFI_PMBR_OSTYPE_EFI &&
1603  Mbr->Partition[1].PartitionType == 0 &&
1604  Mbr->Partition[2].PartitionType == 0 &&
1605  Mbr->Partition[3].PartitionType == 0)
1606  {
1607  DiskEntry->DiskStyle = PARTITION_STYLE_GPT;
1608  }
1609  /* Otherwise, partition table is in MBR */
1610  else
1611  {
1612  DiskEntry->DiskStyle = PARTITION_STYLE_MBR;
1613  }
1614 
1615  /* Free the MBR sector buffer */
1616  RtlFreeHeap(ProcessHeap, 0, Mbr);
1617 
1618 
1619  for (ListEntry = List->BiosDiskListHead.Flink;
1620  ListEntry != &List->BiosDiskListHead;
1621  ListEntry = ListEntry->Flink)
1622  {
1623  BiosDiskEntry = CONTAINING_RECORD(ListEntry, BIOSDISKENTRY, ListEntry);
1624  /* FIXME:
1625  * Compare the size from bios and the reported size from driver.
1626  * If we have more than one disk with a zero or with the same signature
1627  * we must create new signatures and reboot. After the reboot,
1628  * it is possible to identify the disks.
1629  */
1630  if (BiosDiskEntry->Signature == Signature &&
1631  BiosDiskEntry->Checksum == Checksum &&
1632  BiosDiskEntry->DiskEntry == NULL)
1633  {
1634  if (!DiskEntry->BiosFound)
1635  {
1636  DiskEntry->HwAdapterNumber = BiosDiskEntry->AdapterNumber;
1637  DiskEntry->HwControllerNumber = BiosDiskEntry->ControllerNumber;
1638  DiskEntry->HwDiskNumber = BiosDiskEntry->DiskNumber;
1639 
1640  if (DiskEntry->MediaType == RemovableMedia)
1641  {
1642  /* Set the removable disk number to zero */
1643  DiskEntry->HwFixedDiskNumber = 0;
1644  }
1645  else // if (DiskEntry->MediaType == FixedMedia)
1646  {
1647  /* The fixed disk number will later be adjusted using the number of removable disks */
1648  DiskEntry->HwFixedDiskNumber = BiosDiskEntry->DiskNumber;
1649  }
1650 
1651  DiskEntry->BiosFound = TRUE;
1652  BiosDiskEntry->DiskEntry = DiskEntry;
1653  break;
1654  }
1655  else
1656  {
1657  // FIXME: What to do?
1658  DPRINT1("Disk %lu of identifier '%S' has already been found?!\n", DiskNumber, Identifier);
1659  }
1660  }
1661  }
1662 
1663  if (!DiskEntry->BiosFound)
1664  {
1665  DPRINT1("WARNING: Setup could not find a matching BIOS disk entry. Disk %lu may not be bootable by the BIOS!\n", DiskNumber);
1666  }
1667 
1668  DiskEntry->Cylinders = DiskGeometry.Cylinders.QuadPart;
1669  DiskEntry->TracksPerCylinder = DiskGeometry.TracksPerCylinder;
1670  DiskEntry->SectorsPerTrack = DiskGeometry.SectorsPerTrack;
1671  DiskEntry->BytesPerSector = DiskGeometry.BytesPerSector;
1672 
1673  DPRINT("Cylinders %I64u\n", DiskEntry->Cylinders);
1674  DPRINT("TracksPerCylinder %lu\n", DiskEntry->TracksPerCylinder);
1675  DPRINT("SectorsPerTrack %lu\n", DiskEntry->SectorsPerTrack);
1676  DPRINT("BytesPerSector %lu\n", DiskEntry->BytesPerSector);
1677 
1678  DiskEntry->SectorCount.QuadPart = DiskGeometry.Cylinders.QuadPart *
1679  (ULONGLONG)DiskGeometry.TracksPerCylinder *
1680  (ULONGLONG)DiskGeometry.SectorsPerTrack;
1681 
1682  DiskEntry->SectorAlignment = DiskGeometry.SectorsPerTrack;
1683  DiskEntry->CylinderAlignment = DiskGeometry.TracksPerCylinder *
1684  DiskGeometry.SectorsPerTrack;
1685 
1686  DPRINT("SectorCount %I64u\n", DiskEntry->SectorCount.QuadPart);
1687  DPRINT("SectorAlignment %lu\n", DiskEntry->SectorAlignment);
1688 
1689  DiskEntry->DiskNumber = DiskNumber;
1690  DiskEntry->Port = ScsiAddress.PortNumber;
1691  DiskEntry->Bus = ScsiAddress.PathId;
1692  DiskEntry->Id = ScsiAddress.TargetId;
1693 
1694  GetDriverName(DiskEntry);
1695  /*
1696  * Actually it would be more correct somehow to use:
1697  *
1698  * OBJECT_NAME_INFORMATION NameInfo; // ObjectNameInfo;
1699  * ULONG ReturnedLength;
1700  *
1701  * Status = NtQueryObject(SomeHandleToTheDisk,
1702  * ObjectNameInformation,
1703  * &NameInfo,
1704  * sizeof(NameInfo),
1705  * &ReturnedLength);
1706  * etc...
1707  *
1708  * See examples in https://git.reactos.org/?p=reactos.git;a=blob;f=reactos/ntoskrnl/io/iomgr/error.c;hb=2f3a93ee9cec8322a86bf74b356f1ad83fc912dc#l267
1709  */
1710 
1713 
1714  InsertAscendingList(&List->DiskListHead, DiskEntry, DISKENTRY, ListEntry, DiskNumber);
1715 
1716 
1717  /*
1718  * We now retrieve the disk partition layout
1719  */
1720 
1721  /*
1722  * Stop there now if the disk is GPT-partitioned,
1723  * since we currently do not support such disks.
1724  */
1725  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
1726  {
1727  DPRINT1("GPT-partitioned disk detected, not currently supported by SETUP!\n");
1728  return;
1729  }
1730 
1731  /* Allocate a layout buffer with 4 partition entries first */
1732  LayoutBufferSize = sizeof(DRIVE_LAYOUT_INFORMATION) +
1733  ((4 - ANYSIZE_ARRAY) * sizeof(PARTITION_INFORMATION));
1736  LayoutBufferSize);
1737  if (DiskEntry->LayoutBuffer == NULL)
1738  {
1739  DPRINT1("Failed to allocate the disk layout buffer!\n");
1740  return;
1741  }
1742 
1743  /* Keep looping while the drive layout buffer is too small */
1744  for (;;)
1745  {
1746  DPRINT1("Buffer size: %lu\n", LayoutBufferSize);
1748  NULL,
1749  NULL,
1750  NULL,
1751  &Iosb,
1753  NULL,
1754  0,
1755  DiskEntry->LayoutBuffer,
1756  LayoutBufferSize);
1757  if (NT_SUCCESS(Status))
1758  break;
1759 
1761  {
1762  DPRINT1("NtDeviceIoControlFile() failed (Status: 0x%08lx)\n", Status);
1763  return;
1764  }
1765 
1766  LayoutBufferSize += 4 * sizeof(PARTITION_INFORMATION);
1767  NewLayoutBuffer = RtlReAllocateHeap(ProcessHeap,
1769  DiskEntry->LayoutBuffer,
1770  LayoutBufferSize);
1771  if (NewLayoutBuffer == NULL)
1772  {
1773  DPRINT1("Failed to reallocate the disk layout buffer!\n");
1774  return;
1775  }
1776 
1777  DiskEntry->LayoutBuffer = NewLayoutBuffer;
1778  }
1779 
1780  DPRINT1("PartitionCount: %lu\n", DiskEntry->LayoutBuffer->PartitionCount);
1781 
1782 #ifdef DUMP_PARTITION_TABLE
1783  DumpPartitionTable(DiskEntry);
1784 #endif
1785 
1786  if (IsSuperFloppy(DiskEntry))
1787  DPRINT1("Disk %lu is a super-floppy\n", DiskNumber);
1788 
1789  if (DiskEntry->LayoutBuffer->PartitionEntry[0].StartingOffset.QuadPart != 0 &&
1790  DiskEntry->LayoutBuffer->PartitionEntry[0].PartitionLength.QuadPart != 0 &&
1792  {
1793  if ((DiskEntry->LayoutBuffer->PartitionEntry[0].StartingOffset.QuadPart / DiskEntry->BytesPerSector) % DiskEntry->SectorsPerTrack == 0)
1794  {
1795  DPRINT("Use %lu Sector alignment!\n", DiskEntry->SectorsPerTrack);
1796  }
1797  else if (DiskEntry->LayoutBuffer->PartitionEntry[0].StartingOffset.QuadPart % (1024 * 1024) == 0)
1798  {
1799  DPRINT1("Use megabyte (%lu Sectors) alignment!\n", (1024 * 1024) / DiskEntry->BytesPerSector);
1800  }
1801  else
1802  {
1803  DPRINT1("No matching alignment found! Partition 1 starts at %I64u\n", DiskEntry->LayoutBuffer->PartitionEntry[0].StartingOffset.QuadPart);
1804  }
1805  }
1806  else
1807  {
1808  DPRINT1("No valid partition table found! Use megabyte (%lu Sectors) alignment!\n", (1024 * 1024) / DiskEntry->BytesPerSector);
1809  }
1810 
1811  if (DiskEntry->LayoutBuffer->PartitionCount == 0)
1812  {
1813  DiskEntry->NewDisk = TRUE;
1814  DiskEntry->LayoutBuffer->PartitionCount = 4;
1815 
1816  for (i = 0; i < 4; i++)
1817  {
1819  }
1820  }
1821  else
1822  {
1823  /* Enumerate and add the first four primary partitions */
1824  for (i = 0; i < 4; i++)
1825  {
1826  AddPartitionToDisk(DiskNumber, DiskEntry, i, FALSE);
1827  }
1828 
1829  /* Enumerate and add the remaining partitions as logical ones */
1830  for (i = 4; i < DiskEntry->LayoutBuffer->PartitionCount; i += 4)
1831  {
1832  AddPartitionToDisk(DiskNumber, DiskEntry, i, TRUE);
1833  }
1834  }
1835 
1836  ScanForUnpartitionedDiskSpace(DiskEntry);
1837 }
UCHAR PathId
Definition: scsi_port.h:149
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
struct _PARTLIST * PartList
Definition: partlist.h:80
UCHAR PortNumber
Definition: scsi_port.h:148
USHORT Id
Definition: partlist.h:109
#define TRUE
Definition: types.h:120
LARGE_INTEGER PartitionLength
Definition: ntdddisk.h:394
#define IOCTL_SCSI_GET_ADDRESS
Definition: scsi_port.h:52
ULONG HwControllerNumber
Definition: partlist.h:98
ULONG CylinderAlignment
Definition: partlist.h:93
#define ANYSIZE_ARRAY
Definition: typedefs.h:45
USHORT Bus
Definition: partlist.h:108
ULONG HwAdapterNumber
Definition: partlist.h:97
ULONG Checksum
Definition: partlist.h:140
ULONG Signature
Definition: partlist.h:139
LONG NTSTATUS
Definition: precomp.h:26
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:603
ULONG ControllerNumber
Definition: partlist.h:137
ULONG DiskNumber
Definition: partlist.h:105
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
ULONG BytesPerSector
Definition: ntdddisk.h:376
ULONG TracksPerCylinder
Definition: ntdddisk.h:374
NTSYSAPI NTSTATUS NTAPI NtDeviceIoControlFile(IN HANDLE hFile, IN HANDLE hEvent OPTIONAL, IN PIO_APC_ROUTINE IoApcRoutine OPTIONAL, IN PVOID IoApcContext OPTIONAL, OUT PIO_STATUS_BLOCK pIoStatusBlock, IN ULONG DeviceIoControlCode, IN PVOID InBuffer OPTIONAL, IN ULONG InBufferLength, OUT PVOID OutBuffer OPTIONAL, IN ULONG OutBufferLength)
struct _PARTITION_INFORMATION PARTITION_INFORMATION
NTSYSAPI PVOID WINAPI RtlReAllocateHeap(HANDLE, ULONG, PVOID, SIZE_T)
Definition: heap.c:2561
UCHAR TargetId
Definition: scsi_port.h:150
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:64
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
HANDLE FileHandle
Definition: stats.c:38
static VOID GetDriverName(IN PDISKENTRY DiskEntry)
Definition: partlist.c:283
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
struct _DRIVE_LAYOUT_INFORMATION DRIVE_LAYOUT_INFORMATION
smooth NULL
Definition: ftsmooth.c:416
PARTITION_INFORMATION PartitionEntry[1]
Definition: ntdddisk.h:467
NTSTATUS NTAPI NtQueryVolumeInformationFile(IN HANDLE FileHandle, OUT PIO_STATUS_BLOCK IoStatusBlock, OUT PVOID FsInformation, IN ULONG Length, IN FS_INFORMATION_CLASS FsInformationClass)
Definition: iofunc.c:4084
void DPRINT(...)
Definition: polytest.cpp:61
Definition: bufpool.h:45
MEDIA_TYPE MediaType
Definition: partlist.h:82
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
ULARGE_INTEGER SectorCount
Definition: partlist.h:91
ULONG SectorAlignment
Definition: partlist.h:92
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
ULONG AdapterNumber
Definition: partlist.h:136
BOOLEAN BiosFound
Definition: partlist.h:96
ULONG BytesPerSector
Definition: partlist.h:89
LIST_ENTRY List
Definition: psmgr.c:57
#define EFI_PMBR_OSTYPE_EFI
Definition: partlist.h:175
__wchar_t WCHAR
Definition: xmlstorage.h:180
return Iosb
Definition: create.c:4426
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
LARGE_INTEGER StartingOffset
Definition: ntdddisk.h:393
uint64_t ULONGLONG
Definition: typedefs.h:65
LARGE_INTEGER Cylinders
Definition: ntdddisk.h:372
ULONG SectorsPerTrack
Definition: ntdddisk.h:375
MEDIA_TYPE MediaType
Definition: ntdddisk.h:373
ULONG HwDiskNumber
Definition: partlist.h:99
unsigned char PartitionType
Definition: partlist.h:185
BOOLEAN RewritePartition
Definition: ntdddisk.h:400
static VOID ScanForUnpartitionedDiskSpace(IN PDISKENTRY DiskEntry)
Definition: partlist.c:1068
PDISKENTRY DiskEntry
Definition: partlist.h:141
static const WCHAR L[]
Definition: oid.c:1250
ULONG SectorsPerTrack
Definition: partlist.h:88
Definition: typedefs.h:117
#define InsertAscendingList(ListHead, NewEntry, Type, ListEntryField, SortField)
Definition: partlist.c:17
ULONGLONG Cylinders
Definition: partlist.h:86
HANDLE ProcessHeap
Definition: servman.c:15
Status
Definition: gdiplustypes.h:24
#define IOCTL_DISK_GET_DRIVE_LAYOUT
Definition: ntdddisk.h:76
BOOLEAN IsSuperFloppy(IN PDISKENTRY DiskEntry)
Definition: partlist.c:679
ULONG DiskNumber
Definition: partlist.h:138
_In_ PFCB _In_ LONGLONG FileOffset
Definition: cdprocs.h:151
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
PARTITION Partition[PARTITION_TBL_SIZE]
Definition: partlist.h:198
ULONG HwFixedDiskNumber
Definition: partlist.h:100
USHORT Port
Definition: partlist.h:107
unsigned int * PULONG
Definition: retypes.h:1
#define HEAP_ZERO_MEMORY
Definition: compat.h:123
ULONG TracksPerCylinder
Definition: partlist.h:87
#define DPRINT1
Definition: precomp.h:8
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
unsigned int ULONG
Definition: retypes.h:1
IN BOOLEAN OUT PSTR Buffer
Definition: progress.h:34
#define PARTITION_MAGIC
Definition: partlist.h:172
static const WCHAR Signature[]
Definition: parser.c:141
PDRIVE_LAYOUT_INFORMATION LayoutBuffer
Definition: partlist.h:119
BOOLEAN NewDisk
Definition: partlist.h:114
#define IOCTL_DISK_GET_DRIVE_GEOMETRY
Definition: cdrw_usr.h:169
NTSTATUS NTAPI NtReadFile(HANDLE FileHandle, HANDLE Event, PIO_APC_ROUTINE ApcRoutine, PVOID ApcContext, PIO_STATUS_BLOCK IoStatusBlock, PVOID Buffer, ULONG Length, PLARGE_INTEGER ByteOffset, PULONG Key)
LONGLONG QuadPart
Definition: typedefs.h:112
static VOID AddPartitionToDisk(IN ULONG DiskNumber, IN PDISKENTRY DiskEntry, IN ULONG PartitionIndex, IN BOOLEAN LogicalPartition)
Definition: partlist.c:921

Referenced by CreatePartitionList().

◆ AddLogicalDiskSpace()

static VOID AddLogicalDiskSpace ( IN PDISKENTRY  DiskEntry)
static

Definition at line 2809 of file partlist.c.

2811 {
2812  ULONGLONG StartSector;
2814  PPARTENTRY NewPartEntry;
2815 
2816  DPRINT1("AddLogicalDiskSpace()\n");
2817 
2818  /* Create a partition entry that represents the empty space in the container partition */
2819 
2820  StartSector = DiskEntry->ExtendedPartition->StartSector.QuadPart + (ULONGLONG)DiskEntry->SectorAlignment;
2821  SectorCount = DiskEntry->ExtendedPartition->SectorCount.QuadPart - (ULONGLONG)DiskEntry->SectorAlignment;
2822 
2823  NewPartEntry = CreateInsertBlankRegion(DiskEntry,
2824  &DiskEntry->LogicalPartListHead,
2825  StartSector,
2826  SectorCount,
2827  TRUE);
2828  if (NewPartEntry == NULL)
2829  {
2830  DPRINT1("Failed to create a new empty region for extended partition space!\n");
2831  return;
2832  }
2833  NewPartEntry->LogicalPartition = TRUE;
2834 }
#define TRUE
Definition: types.h:120
BOOLEAN LogicalPartition
Definition: partlist.h:57
smooth NULL
Definition: ftsmooth.c:416
static PPARTENTRY CreateInsertBlankRegion(IN PDISKENTRY DiskEntry, IN OUT PLIST_ENTRY ListHead, IN ULONGLONG StartSector, IN ULONGLONG SectorCount, IN BOOLEAN LogicalSpace)
Definition: partlist.c:817
uint64_t ULONGLONG
Definition: typedefs.h:65
ULONG SectorCount
Definition: part_xbox.c:32
#define DPRINT1
Definition: precomp.h:8

Referenced by CreateExtendedPartition().

◆ AddPartitionToDisk()

static VOID AddPartitionToDisk ( IN ULONG  DiskNumber,
IN PDISKENTRY  DiskEntry,
IN ULONG  PartitionIndex,
IN BOOLEAN  LogicalPartition 
)
static

Definition at line 921 of file partlist.c.

926 {
929  PPARTENTRY PartEntry;
930  HANDLE PartitionHandle;
933  WCHAR PathBuffer[MAX_PATH];
935  UCHAR LabelBuffer[sizeof(FILE_FS_VOLUME_INFORMATION) + 256 * sizeof(WCHAR)];
937 
938  PartitionInfo = &DiskEntry->LayoutBuffer->PartitionEntry[PartitionIndex];
939 
940  if (PartitionInfo->PartitionType == PARTITION_ENTRY_UNUSED ||
941  ((LogicalPartition != FALSE) && IsContainerPartition(PartitionInfo->PartitionType)))
942  {
943  return;
944  }
945 
946  PartEntry = RtlAllocateHeap(ProcessHeap,
948  sizeof(PARTENTRY));
949  if (PartEntry == NULL)
950  return;
951 
952  PartEntry->DiskEntry = DiskEntry;
953 
954  PartEntry->StartSector.QuadPart = (ULONGLONG)PartitionInfo->StartingOffset.QuadPart / DiskEntry->BytesPerSector;
955  PartEntry->SectorCount.QuadPart = (ULONGLONG)PartitionInfo->PartitionLength.QuadPart / DiskEntry->BytesPerSector;
956 
957  PartEntry->BootIndicator = PartitionInfo->BootIndicator;
958  PartEntry->PartitionType = PartitionInfo->PartitionType;
959  PartEntry->HiddenSectors = PartitionInfo->HiddenSectors;
960 
961  PartEntry->LogicalPartition = LogicalPartition;
962  PartEntry->IsPartitioned = TRUE;
963  PartEntry->OnDiskPartitionNumber = PartitionInfo->PartitionNumber;
964  PartEntry->PartitionNumber = PartitionInfo->PartitionNumber;
965  PartEntry->PartitionIndex = PartitionIndex;
966 
967  /* Specify the partition as initially unformatted */
968  PartEntry->FormatState = Unformatted;
969  PartEntry->FileSystem[0] = L'\0';
970 
971  /* Initialize the partition volume label */
972  RtlZeroMemory(PartEntry->VolumeLabel, sizeof(PartEntry->VolumeLabel));
973 
974  if (IsContainerPartition(PartEntry->PartitionType))
975  {
976  PartEntry->FormatState = Unformatted;
977 
978  if (LogicalPartition == FALSE && DiskEntry->ExtendedPartition == NULL)
979  DiskEntry->ExtendedPartition = PartEntry;
980  }
981  else if (IsRecognizedPartition(PartEntry->PartitionType))
982  {
983  ASSERT(PartitionInfo->RecognizedPartition);
984  ASSERT(PartEntry->IsPartitioned && PartEntry->PartitionNumber != 0);
985 
986  /* Open the volume, ignore any errors */
987  RtlStringCchPrintfW(PathBuffer, ARRAYSIZE(PathBuffer),
988  L"\\Device\\Harddisk%lu\\Partition%lu",
989  DiskEntry->DiskNumber,
990  PartEntry->PartitionNumber);
991  RtlInitUnicodeString(&Name, PathBuffer);
992 
994  &Name,
996  NULL,
997  NULL);
998 
999  PartitionHandle = NULL;
1000  Status = NtOpenFile(&PartitionHandle,
1003  &IoStatusBlock,
1006  if (!NT_SUCCESS(Status))
1007  {
1008  DPRINT1("NtOpenFile() failed, Status 0x%08lx\n", Status);
1009  }
1010 
1011  if (/* NT_SUCCESS(Status) && */ PartitionHandle)
1012  {
1013  /* We don't have a FS, try to guess one */
1014  Status = InferFileSystemByHandle(PartitionHandle,
1015  PartEntry->PartitionType,
1016  PartEntry->FileSystem,
1017  sizeof(PartEntry->FileSystem));
1018  if (!NT_SUCCESS(Status))
1019  DPRINT1("InferFileSystemByHandle() failed, Status 0x%08lx\n", Status);
1020  }
1021  if (*PartEntry->FileSystem)
1022  {
1023  if (wcsicmp(PartEntry->FileSystem, L"RAW") == 0)
1024  PartEntry->FormatState = Unformatted;
1025  else
1026  PartEntry->FormatState = Preformatted;
1027  }
1028  else
1029  {
1030  PartEntry->FormatState = UnknownFormat;
1031  }
1032 
1033  /* Retrieve the partition volume label */
1034  if (PartitionHandle)
1035  {
1036  Status = NtQueryVolumeInformationFile(PartitionHandle,
1037  &IoStatusBlock,
1038  &LabelBuffer,
1039  sizeof(LabelBuffer),
1041  if (NT_SUCCESS(Status))
1042  {
1043  /* Copy the (possibly truncated) volume label and NULL-terminate it */
1044  RtlStringCbCopyNW(PartEntry->VolumeLabel, sizeof(PartEntry->VolumeLabel),
1045  LabelInfo->VolumeLabel, LabelInfo->VolumeLabelLength);
1046  }
1047  else
1048  {
1049  DPRINT1("NtQueryVolumeInformationFile() failed, Status 0x%08lx\n", Status);
1050  }
1051  }
1052 
1053  /* Close the partition */
1054  if (PartitionHandle)
1055  NtClose(PartitionHandle);
1056  }
1057  else
1058  {
1059  /* Unknown partition, hence unknown partition format (may or may not be actually formatted) */
1060  PartEntry->FormatState = UnknownFormat;
1061  }
1062 
1063  InsertDiskRegion(DiskEntry, PartEntry, LogicalPartition);
1064 }
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:35
ULONG PartitionNumber
Definition: partlist.h:49
ULARGE_INTEGER StartSector
Definition: partlist.h:42
#define TRUE
Definition: types.h:120
WCHAR VolumeLabel[20]
Definition: partlist.h:53
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
LONG NTSTATUS
Definition: precomp.h:26
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
#define FILE_SHARE_WRITE
Definition: nt_native.h:681
#define FILE_SHARE_READ
Definition: compat.h:125
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
BOOLEAN LogicalPartition
Definition: partlist.h:57
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
NTSTATUS InferFileSystemByHandle(IN HANDLE PartitionHandle, IN UCHAR PartitionType, IN OUT PWSTR FileSystemName, IN SIZE_T FileSystemNameSize)
Definition: fsutil.c:225
FORMATSTATE FormatState
Definition: partlist.h:55
#define FILE_READ_DATA
Definition: nt_native.h:628
NTSTRSAFEAPI RtlStringCbCopyNW(_Out_writes_bytes_(cbDest) NTSTRSAFE_PWSTR pszDest, _In_ size_t cbDest, _In_reads_bytes_(cbToCopy) STRSAFE_LPCWSTR pszSrc, _In_ size_t cbToCopy)
Definition: ntstrsafe.h:411
struct NameRec_ * Name
Definition: cdprocs.h:464
smooth NULL
Definition: ftsmooth.c:416
NTSTATUS NTAPI NtQueryVolumeInformationFile(IN HANDLE FileHandle, OUT PIO_STATUS_BLOCK IoStatusBlock, OUT PVOID FsInformation, IN ULONG Length, IN FS_INFORMATION_CLASS FsInformationClass)
Definition: iofunc.c:4084
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
struct _FILE_FS_VOLUME_INFORMATION * PFILE_FS_VOLUME_INFORMATION
NTSYSAPI NTSTATUS NTAPI NtOpenFile(OUT PHANDLE phFile, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes, OUT PIO_STATUS_BLOCK pIoStatusBlock, IN ULONG ShareMode, IN ULONG OpenMode)
Definition: file.c:3951
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
uint64_t ULONGLONG
Definition: typedefs.h:65
ULONG OnDiskPartitionNumber
Definition: partlist.h:48
#define IsRecognizedPartition(PartitionType)
Definition: ntdddisk.h:271
#define MAX_PATH
Definition: compat.h:26
_In_ ULONG _In_ struct _SET_PARTITION_INFORMATION_EX * PartitionInfo
Definition: iofuncs.h:2101
WCHAR FileSystem[MAX_PATH+1]
Definition: partlist.h:54
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3399
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
unsigned char UCHAR
Definition: xmlstorage.h:181
static const WCHAR L[]
Definition: oid.c:1250
#define SYNCHRONIZE
Definition: nt_native.h:61
#define wcsicmp
Definition: string.h:1152
HANDLE ProcessHeap
Definition: servman.c:15
Status
Definition: gdiplustypes.h:24
static OUT PIO_STATUS_BLOCK IoStatusBlock
Definition: pipe.c:75
#define HEAP_ZERO_MEMORY
Definition: compat.h:123
#define DPRINT1
Definition: precomp.h:8
BOOLEAN BootIndicator
Definition: partlist.h:45
#define FILE_SYNCHRONOUS_IO_NONALERT
Definition: from_kernel.h:31
struct _FILE_FS_VOLUME_INFORMATION FILE_FS_VOLUME_INFORMATION
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:261
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
ULONG HiddenSectors
Definition: partlist.h:47
BOOLEAN IsPartitioned
Definition: partlist.h:60
static VOID InsertDiskRegion(IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN BOOLEAN LogicalPartition)
Definition: partlist.c:752
ULONG PartitionIndex
Definition: partlist.h:50

Referenced by AddDiskToList().

◆ AlignDown()

ULONGLONG AlignDown ( IN ULONGLONG  Value,
IN ULONG  Alignment 
)

Definition at line 245 of file partlist.c.

248 {
249  ULONGLONG Temp;
250 
251  Temp = Value / Alignment;
252 
253  return Temp * Alignment;
254 }
_In_opt_ ULONG _Out_ PULONG Value
Definition: rtlfuncs.h:2327
union Alignment_ Alignment
uint64_t ULONGLONG
Definition: typedefs.h:65

Referenced by InitializePartitionEntry(), and ScanForUnpartitionedDiskSpace().

◆ AlignUp()

ULONGLONG AlignUp ( IN ULONGLONG  Value,
IN ULONG  Alignment 
)

Definition at line 257 of file partlist.c.

260 {
261  ULONGLONG Temp, Result;
262 
263  Temp = Value / Alignment;
264 
265  Result = Temp * Alignment;
266  if (Value % Alignment)
267  Result += Alignment;
268 
269  return Result;
270 }
_In_opt_ ULONG _Out_ PULONG Value
Definition: rtlfuncs.h:2327
union Alignment_ Alignment
_At_(*)(_In_ PWSK_CLIENT Client, _In_opt_ PUNICODE_STRING NodeName, _In_opt_ PUNICODE_STRING ServiceName, _In_opt_ ULONG NameSpace, _In_opt_ GUID *Provider, _In_opt_ PADDRINFOEXW Hints, _Outptr_ PADDRINFOEXW *Result, _In_opt_ PEPROCESS OwningProcess, _In_opt_ PETHREAD OwningThread, _Inout_ PIRP Irp Result)(Mem)) NTSTATUS(WSKAPI *PFN_WSK_GET_ADDRESS_INFO
Definition: wsk.h:426
uint64_t ULONGLONG
Definition: typedefs.h:65

Referenced by PeFmtCreateSection().

◆ AssignDriveLetters()

static VOID AssignDriveLetters ( IN PPARTLIST  List)
static

Definition at line 316 of file partlist.c.

318 {
319  PDISKENTRY DiskEntry;
320  PPARTENTRY PartEntry;
321  PLIST_ENTRY Entry1;
322  PLIST_ENTRY Entry2;
323  WCHAR Letter;
324 
325  Letter = L'C';
326 
327  /* Assign drive letters to primary partitions */
328  for (Entry1 = List->DiskListHead.Flink;
329  Entry1 != &List->DiskListHead;
330  Entry1 = Entry1->Flink)
331  {
332  DiskEntry = CONTAINING_RECORD(Entry1, DISKENTRY, ListEntry);
333 
334  for (Entry2 = DiskEntry->PrimaryPartListHead.Flink;
335  Entry2 != &DiskEntry->PrimaryPartListHead;
336  Entry2 = Entry2->Flink)
337  {
338  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
339 
340  PartEntry->DriveLetter = 0;
341 
342  if (PartEntry->IsPartitioned &&
343  !IsContainerPartition(PartEntry->PartitionType))
344  {
346 
347  if (IsRecognizedPartition(PartEntry->PartitionType) ||
348  PartEntry->SectorCount.QuadPart != 0LL)
349  {
350  if (Letter <= L'Z')
351  {
352  PartEntry->DriveLetter = Letter;
353  Letter++;
354  }
355  }
356  }
357  }
358  }
359 
360  /* Assign drive letters to logical drives */
361  for (Entry1 = List->DiskListHead.Flink;
362  Entry1 != &List->DiskListHead;
363  Entry1 = Entry1->Flink)
364  {
365  DiskEntry = CONTAINING_RECORD(Entry1, DISKENTRY, ListEntry);
366 
367  for (Entry2 = DiskEntry->LogicalPartListHead.Flink;
368  Entry2 != &DiskEntry->LogicalPartListHead;
369  Entry2 = Entry2->Flink)
370  {
371  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
372 
373  PartEntry->DriveLetter = 0;
374 
375  if (PartEntry->IsPartitioned)
376  {
378 
379  if (IsRecognizedPartition(PartEntry->PartitionType) ||
380  PartEntry->SectorCount.QuadPart != 0LL)
381  {
382  if (Letter <= L'Z')
383  {
384  PartEntry->DriveLetter = Letter;
385  Letter++;
386  }
387  }
388  }
389  }
390  }
391 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
WCHAR DriveLetter
Definition: partlist.h:52
#define LL
Definition: tui.h:72
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
UCHAR PartitionType
Definition: partlist.h:46
LIST_ENTRY List
Definition: psmgr.c:57
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define IsRecognizedPartition(PartitionType)
Definition: ntdddisk.h:271
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
WCHAR Letter
Definition: typedefs.h:117
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by CreateExtendedPartition(), CreateLogicalPartition(), CreatePartitionList(), CreatePrimaryPartition(), and DeletePartition().

◆ CheckActiveSystemPartition()

VOID CheckActiveSystemPartition ( IN PPARTLIST  List,
IN BOOLEAN  ForceSelect,
IN PDISKENTRY AlternateDisk  OPTIONAL,
IN PPARTENTRY AlternatePart  OPTIONAL 
)

Definition at line 3324 of file partlist.c.

3329 {
3330  PLIST_ENTRY ListEntry;
3331  PDISKENTRY DiskEntry;
3332  PPARTENTRY PartEntry;
3333  PPARTENTRY ActivePartition;
3334  PPARTENTRY CandidatePartition = NULL;
3335 
3336  /* Check for empty disk list */
3337  if (IsListEmpty(&List->DiskListHead))
3338  {
3339  /* No system partition! */
3340  List->SystemPartition = NULL;
3341  List->OriginalSystemPartition = NULL;
3342  goto NoSystemPartition;
3343  }
3344 
3345  if (List->SystemPartition != NULL)
3346  {
3347  /* We already have an active system partition */
3348  DPRINT1("Use the current system partition %lu in disk %lu, drive letter %C\n",
3349  List->SystemPartition->PartitionNumber,
3350  List->SystemPartition->DiskEntry->DiskNumber,
3351  (List->SystemPartition->DriveLetter == 0) ? L'-' : List->SystemPartition->DriveLetter);
3352  return;
3353  }
3354 
3355  /* Start fresh */
3356  List->SystemPartition = NULL;
3357  List->OriginalSystemPartition = NULL;
3358 
3359  /* Adjust the optional alternate disk if needed */
3360  if (!AlternateDisk && AlternatePart)
3361  AlternateDisk = AlternatePart->DiskEntry;
3362 
3363  /* Ensure that the alternate partition is on the alternate disk */
3364  if (AlternatePart)
3365  ASSERT(AlternateDisk && (AlternatePart->DiskEntry == AlternateDisk));
3366 
3367  /* Ensure that the alternate disk is in the list */
3368  if (AlternateDisk)
3369  ASSERT(AlternateDisk->PartList == List);
3370 
3371 //
3372 // Pass == 1 : Check the first (system) disk.
3373 //
3374 
3375  /*
3376  * First, check whether the first disk (the one that will be booted
3377  * by default by the hardware) contains an active partition. If so
3378  * this should be our system partition.
3379  */
3380  DiskEntry = CONTAINING_RECORD(List->DiskListHead.Flink,
3381  DISKENTRY, ListEntry);
3382 
3383  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
3384  {
3385  DPRINT1("First (system) disk -- GPT-partitioned disk detected, not currently supported by SETUP!\n");
3386  goto UseAlternateDisk;
3387  }
3388 
3389  ActivePartition = GetActiveDiskPartition(DiskEntry);
3390  if (ActivePartition)
3391  {
3392  /* Save the actual system partition */
3393  List->OriginalSystemPartition = ActivePartition;
3394 
3395  /* If we get a candidate active partition in the first disk, validate it */
3396  if (IsSupportedActivePartition(ActivePartition))
3397  {
3398  CandidatePartition = ActivePartition;
3399  goto SystemPartitionFound;
3400  }
3401  }
3402 
3403  /* If this first disk is not the optional alternate disk, perform the minimal checks */
3404  if (DiskEntry != AlternateDisk)
3405  {
3406  /*
3407  * No active partition has been recognized. Enumerate all the (primary)
3408  * partitions in the first disk, excluding the possible current active
3409  * partition, to find a new candidate.
3410  */
3411  for (ListEntry = DiskEntry->PrimaryPartListHead.Flink;
3412  ListEntry != &DiskEntry->PrimaryPartListHead;
3413  ListEntry = ListEntry->Flink)
3414  {
3415  /* Retrieve the partition */
3416  PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry);
3417 
3418  /* Skip the current active partition */
3419  if (/* ActivePartition != NULL && */ PartEntry == ActivePartition)
3420  continue;
3421 
3422  /* Check if the partition is partitioned and used */
3423  if (PartEntry->IsPartitioned &&
3424  !IsContainerPartition(PartEntry->PartitionType))
3425  {
3427 
3428  /* If we get a candidate active partition in the first disk, validate it */
3429  if (IsSupportedActivePartition(PartEntry))
3430  {
3431  CandidatePartition = PartEntry;
3432  goto FindAndUseAlternativeSystemPartition;
3433  }
3434  }
3435 
3436 #if 0
3437  /* Check if the partition is partitioned and used */
3438  if (!PartEntry->IsPartitioned)
3439  {
3441 
3442  // TODO: Check for minimal size!!
3443  CandidatePartition = PartEntry;
3444  goto FindAndUseAlternativeSystemPartition;
3445  }
3446 #endif
3447  }
3448 
3449  /*
3450  * Still nothing, look whether there is some free space that we can use
3451  * for the new system partition. We must be sure that the total number
3452  * of partition is less than the maximum allowed, and that the minimal
3453  * size is fine.
3454  */
3455 //
3456 // TODO: Fix the handling of system partition being created in unpartitioned space!!
3457 // --> When to partition it? etc...
3458 //
3459  if (GetPrimaryPartitionCount(DiskEntry) < 4)
3460  {
3461  for (ListEntry = DiskEntry->PrimaryPartListHead.Flink;
3462  ListEntry != &DiskEntry->PrimaryPartListHead;
3463  ListEntry = ListEntry->Flink)
3464  {
3465  /* Retrieve the partition */
3466  PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry);
3467 
3468  /* Skip the current active partition */
3469  if (/* ActivePartition != NULL && */ PartEntry == ActivePartition)
3470  continue;
3471 
3472  /* Check for unpartitioned space */
3473  if (!PartEntry->IsPartitioned)
3474  {
3476 
3477  // TODO: Check for minimal size!!
3478  CandidatePartition = PartEntry;
3479  goto FindAndUseAlternativeSystemPartition;
3480  }
3481  }
3482  }
3483  }
3484 
3485 
3486 //
3487 // Pass == 2 : No active partition found: Check the alternate disk if specified.
3488 //
3489 
3490 UseAlternateDisk:
3491  if (!AlternateDisk || (!ForceSelect && (DiskEntry != AlternateDisk)))
3492  goto NoSystemPartition;
3493 
3494  if (AlternateDisk->DiskStyle == PARTITION_STYLE_GPT)
3495  {
3496  DPRINT1("Alternate disk -- GPT-partitioned disk detected, not currently supported by SETUP!\n");
3497  goto NoSystemPartition;
3498  }
3499 
3500  if (DiskEntry != AlternateDisk)
3501  {
3502  /* Choose the alternate disk */
3503  DiskEntry = AlternateDisk;
3504 
3505  ActivePartition = GetActiveDiskPartition(DiskEntry);
3506  if (ActivePartition)
3507  {
3508  /* If we get a candidate active partition, validate it */
3509  if (IsSupportedActivePartition(ActivePartition))
3510  {
3511  CandidatePartition = ActivePartition;
3512  goto FindAndUseAlternativeSystemPartition;
3513  }
3514  }
3515  }
3516 
3517  /* We now may have an unsupported active partition, or none */
3518 
3519 /***
3520  *** TODO: Improve the selection:
3521  *** - If we want a really separate system partition from the partition where
3522  *** we install, do something similar to what's done below in the code.
3523  *** - Otherwise if we allow for the system partition to be also the partition
3524  *** where we install, just directly fall down to using AlternatePart.
3525  ***/
3526 
3527  /* Retrieve the first partition of the disk */
3528  PartEntry = CONTAINING_RECORD(DiskEntry->PrimaryPartListHead.Flink,
3529  PARTENTRY, ListEntry);
3530  ASSERT(DiskEntry == PartEntry->DiskEntry);
3531 
3532  CandidatePartition = PartEntry;
3533 
3534  //
3535  // See: https://svn.reactos.org/svn/reactos/trunk/reactos/base/setup/usetup/partlist.c?r1=63355&r2=63354&pathrev=63355#l2318
3536  //
3537 
3538  /* Check if the disk is new and if so, use its first partition as the active system partition */
3539  if (DiskEntry->NewDisk)
3540  {
3541  // !IsContainerPartition(PartEntry->PartitionType);
3542  if (!CandidatePartition->IsPartitioned || !CandidatePartition->BootIndicator) /* CandidatePartition != ActivePartition */
3543  {
3544  ASSERT(DiskEntry == CandidatePartition->DiskEntry);
3545 
3546  List->SystemPartition = CandidatePartition;
3547  List->OriginalSystemPartition = List->SystemPartition;
3548 
3549  DPRINT1("Use new first active system partition %lu in disk %lu, drive letter %C\n",
3550  List->SystemPartition->PartitionNumber,
3551  List->SystemPartition->DiskEntry->DiskNumber,
3552  (List->SystemPartition->DriveLetter == 0) ? L'-' : List->SystemPartition->DriveLetter);
3553 
3554  goto SetSystemPartition;
3555  }
3556 
3557  // FIXME: What to do??
3558  DPRINT1("NewDisk TRUE but first partition is used?\n");
3559  }
3560 
3561  /*
3562  * The disk is not new, check if any partition is initialized;
3563  * if not, the first one becomes the system partition.
3564  */
3565  for (ListEntry = DiskEntry->PrimaryPartListHead.Flink;
3566  ListEntry != &DiskEntry->PrimaryPartListHead;
3567  ListEntry = ListEntry->Flink)
3568  {
3569  /* Retrieve the partition */
3570  PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry);
3571 
3572  /* Check if the partition is partitioned and is used */
3573  // !IsContainerPartition(PartEntry->PartitionType);
3574  if (/* PartEntry->IsPartitioned && */
3575  PartEntry->PartitionType != PARTITION_ENTRY_UNUSED || PartEntry->BootIndicator)
3576  {
3577  break;
3578  }
3579  }
3580  if (ListEntry == &DiskEntry->PrimaryPartListHead)
3581  {
3582  /*
3583  * OK we haven't encountered any used and active partition,
3584  * so use the first one as the system partition.
3585  */
3586  ASSERT(DiskEntry == CandidatePartition->DiskEntry);
3587  List->SystemPartition = CandidatePartition; // The first PartEntry
3588  List->OriginalSystemPartition = List->SystemPartition;
3589 
3590  DPRINT1("Use first active system partition %lu in disk %lu, drive letter %C\n",
3591  List->SystemPartition->PartitionNumber,
3592  List->SystemPartition->DiskEntry->DiskNumber,
3593  (List->SystemPartition->DriveLetter == 0) ? L'-' : List->SystemPartition->DriveLetter);
3594 
3595  goto SetSystemPartition;
3596  }
3597 
3598  /*
3599  * The disk is not new, we did not find any actual active partition,
3600  * or the one we found was not supported, or any possible other canditate
3601  * is not supported. We then use the alternate partition if specified.
3602  */
3603  if (AlternatePart)
3604  {
3605  DPRINT1("No system partition found, use the alternative partition!\n");
3606  CandidatePartition = AlternatePart;
3607  goto UseAlternativeSystemPartition;
3608  }
3609  else
3610  {
3611 NoSystemPartition:
3612  DPRINT1("No valid or supported system partition has been found on this system!\n");
3613  return;
3614  }
3615 
3616 
3617 SystemPartitionFound:
3618  ASSERT(CandidatePartition);
3619  List->SystemPartition = CandidatePartition;
3620 
3621  DPRINT1("Use existing active system partition %lu in disk %lu, drive letter %C\n",
3622  List->SystemPartition->PartitionNumber,
3623  List->SystemPartition->DiskEntry->DiskNumber,
3624  (List->SystemPartition->DriveLetter == 0) ? L'-' : List->SystemPartition->DriveLetter);
3625 
3626  return;
3627 
3628 FindAndUseAlternativeSystemPartition:
3629  /*
3630  * We are here because we have not found any (active) candidate
3631  * system partition that we know how to support. What we are going
3632  * to do is to change the existing system partition and use the
3633  * partition on which we install ReactOS as the new system partition,
3634  * and then we will need to add in FreeLdr's entry a boot entry to boot
3635  * from the original system partition.
3636  */
3637 
3638  /* Unset the old system partition */
3639  if (List->OriginalSystemPartition)
3640  {
3641  List->OriginalSystemPartition->BootIndicator = FALSE;
3642  List->OriginalSystemPartition->DiskEntry->LayoutBuffer->PartitionEntry[List->OriginalSystemPartition->PartitionIndex].BootIndicator = FALSE;
3643  List->OriginalSystemPartition->DiskEntry->LayoutBuffer->PartitionEntry[List->OriginalSystemPartition->PartitionIndex].RewritePartition = TRUE;
3644  List->OriginalSystemPartition->DiskEntry->Dirty = TRUE;
3645  }
3646 
3647 UseAlternativeSystemPartition:
3648  ASSERT(CandidatePartition);
3649  List->SystemPartition = CandidatePartition;
3650 
3651  DPRINT1("Use alternative active system partition %lu in disk %lu, drive letter %C\n",
3652  List->SystemPartition->PartitionNumber,
3653  List->SystemPartition->DiskEntry->DiskNumber,
3654  (List->SystemPartition->DriveLetter == 0) ? L'-' : List->SystemPartition->DriveLetter);
3655 
3656 SetSystemPartition:
3657  /* Set the new active system partition */
3658  List->SystemPartition->BootIndicator = TRUE;
3659  List->SystemPartition->DiskEntry->LayoutBuffer->PartitionEntry[List->SystemPartition->PartitionIndex].BootIndicator = TRUE;
3660  List->SystemPartition->DiskEntry->LayoutBuffer->PartitionEntry[List->SystemPartition->PartitionIndex].RewritePartition = TRUE;
3661  List->SystemPartition->DiskEntry->Dirty = TRUE;
3662 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
#define TRUE
Definition: types.h:120
static PPARTENTRY GetActiveDiskPartition(IN PDISKENTRY DiskEntry)
Definition: partlist.c:3184
static BOOLEAN IsSupportedActivePartition(IN PPARTENTRY PartEntry)
Definition: partlist.c:3247
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static ULONG GetPrimaryPartitionCount(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2414
static const WCHAR L[]
Definition: oid.c:1250
Definition: typedefs.h:117
#define DPRINT1
Definition: precomp.h:8
BOOLEAN BootIndicator
Definition: partlist.h:45
BOOLEAN NewDisk
Definition: partlist.h:114
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by SelectFileSystemPage().

◆ CreateExtendedPartition()

BOOLEAN CreateExtendedPartition ( IN PPARTLIST  List,
IN PPARTENTRY  SelectedEntry,
IN ULONGLONG  SectorCount 
)

Definition at line 2837 of file partlist.c.

2841 {
2843  PPARTENTRY PartEntry;
2844 
2845  DPRINT1("CreateExtendedPartition(%I64u)\n", SectorCount);
2846 
2847  if (List == NULL ||
2848  SelectedEntry == NULL ||
2849  SelectedEntry->DiskEntry == NULL ||
2850  SelectedEntry->IsPartitioned)
2851  {
2852  return FALSE;
2853  }
2854 
2855  Error = ExtendedPartitionCreationChecks(SelectedEntry);
2856  if (Error != NOT_AN_ERROR)
2857  {
2858  DPRINT1("ExtendedPartitionCreationChecks() failed with error %lu\n", Error);
2859  return FALSE;
2860  }
2861 
2862  /* Convert the current entry, or insert and initialize a new partition entry */
2863  PartEntry = InitializePartitionEntry(SelectedEntry->DiskEntry, SelectedEntry, SectorCount, FALSE);
2864  if (PartEntry == NULL)
2865  return FALSE;
2866 
2867  if (PartEntry->StartSector.QuadPart < 1450560)
2868  {
2869  /* Partition starts below the 8.4GB boundary ==> CHS partition */
2870  PartEntry->PartitionType = PARTITION_EXTENDED;
2871  }
2872  else
2873  {
2874  /* Partition starts above the 8.4GB boundary ==> LBA partition */
2876  }
2877 
2878  // FIXME? Possibly to make GetNextUnformattedPartition work (i.e. skip the extended partition container)
2879  PartEntry->New = FALSE;
2880  PartEntry->FormatState = Formatted;
2881 
2882  PartEntry->DiskEntry->ExtendedPartition = PartEntry;
2883 
2884  AddLogicalDiskSpace(PartEntry->DiskEntry);
2885 
2886  UpdateDiskLayout(PartEntry->DiskEntry);
2887 
2889 
2890  return TRUE;
2891 }
ULARGE_INTEGER StartSector
Definition: partlist.h:42
ERROR_NUMBER ExtendedPartitionCreationChecks(IN PPARTENTRY PartEntry)
Definition: partlist.c:4023
#define TRUE
Definition: types.h:120
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
FORMATSTATE FormatState
Definition: partlist.h:55
smooth NULL
Definition: ftsmooth.c:416
static VOID UpdateDiskLayout(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2520
#define PARTITION_EXTENDED
Definition: disk.h:91
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
BOOL Error
Definition: chkdsk.c:66
enum _ERROR_NUMBER ERROR_NUMBER
ULONG SectorCount
Definition: part_xbox.c:32
#define PARTITION_XINT13_EXTENDED
Definition: disk.h:98
BOOLEAN New
Definition: partlist.h:65
#define DPRINT1
Definition: precomp.h:8
static PPARTENTRY InitializePartitionEntry(IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
Definition: partlist.c:855
static VOID AddLogicalDiskSpace(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2809
static VOID AssignDriveLetters(IN PPARTLIST List)
Definition: partlist.c:316

Referenced by CreateExtendedPartitionPage().

◆ CreateInsertBlankRegion()

static PPARTENTRY CreateInsertBlankRegion ( IN PDISKENTRY  DiskEntry,
IN OUT PLIST_ENTRY  ListHead,
IN ULONGLONG  StartSector,
IN ULONGLONG  SectorCount,
IN BOOLEAN  LogicalSpace 
)
static

Definition at line 817 of file partlist.c.

823 {
824  PPARTENTRY NewPartEntry;
825 
826  NewPartEntry = RtlAllocateHeap(ProcessHeap,
828  sizeof(PARTENTRY));
829  if (NewPartEntry == NULL)
830  return NULL;
831 
832  NewPartEntry->DiskEntry = DiskEntry;
833 
834  NewPartEntry->StartSector.QuadPart = StartSector;
835  NewPartEntry->SectorCount.QuadPart = SectorCount;
836 
837  NewPartEntry->IsPartitioned = FALSE;
838  NewPartEntry->PartitionType = PARTITION_ENTRY_UNUSED;
839  NewPartEntry->FormatState = Unformatted;
840  NewPartEntry->FileSystem[0] = L'\0';
841 
842  DPRINT1("First Sector : %I64u\n", NewPartEntry->StartSector.QuadPart);
843  DPRINT1("Last Sector : %I64u\n", NewPartEntry->StartSector.QuadPart + NewPartEntry->SectorCount.QuadPart - 1);
844  DPRINT1("Total Sectors: %I64u\n", NewPartEntry->SectorCount.QuadPart);
845 
846  /* Insert the new entry into the list */
847  InsertTailList(ListHead, &NewPartEntry->ListEntry);
848 
849  return NewPartEntry;
850 }
ULARGE_INTEGER StartSector
Definition: partlist.h:42
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
#define InsertTailList(ListHead, Entry)
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
LIST_ENTRY ListEntry
Definition: partlist.h:36
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
FORMATSTATE FormatState
Definition: partlist.h:55
smooth NULL
Definition: ftsmooth.c:416
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
WCHAR FileSystem[MAX_PATH+1]
Definition: partlist.h:54
static const WCHAR L[]
Definition: oid.c:1250
ULONG SectorCount
Definition: part_xbox.c:32
HANDLE ProcessHeap
Definition: servman.c:15
#define HEAP_ZERO_MEMORY
Definition: compat.h:123
#define DPRINT1
Definition: precomp.h:8
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by AddLogicalDiskSpace(), and ScanForUnpartitionedDiskSpace().

◆ CreateLogicalPartition()

BOOLEAN CreateLogicalPartition ( IN PPARTLIST  List,
IN PPARTENTRY  SelectedEntry,
IN ULONGLONG  SectorCount,
IN BOOLEAN  AutoCreate 
)

Definition at line 2894 of file partlist.c.

2899 {
2901  PPARTENTRY PartEntry;
2902 
2903  DPRINT1("CreateLogicalPartition(%I64u)\n", SectorCount);
2904 
2905  if (List == NULL ||
2906  SelectedEntry == NULL ||
2907  SelectedEntry->DiskEntry == NULL ||
2908  SelectedEntry->IsPartitioned)
2909  {
2910  return FALSE;
2911  }
2912 
2913  Error = LogicalPartitionCreationChecks(SelectedEntry);
2914  if (Error != NOT_AN_ERROR)
2915  {
2916  DPRINT1("LogicalPartitionCreationChecks() failed with error %lu\n", Error);
2917  return FALSE;
2918  }
2919 
2920  /* Convert the current entry, or insert and initialize a new partition entry */
2921  PartEntry = InitializePartitionEntry(SelectedEntry->DiskEntry, SelectedEntry, SectorCount, AutoCreate);
2922  if (PartEntry == NULL)
2923  return FALSE;
2924 
2925  PartEntry->LogicalPartition = TRUE;
2926 
2927  UpdateDiskLayout(PartEntry->DiskEntry);
2928 
2930 
2931  return TRUE;
2932 }
#define TRUE
Definition: types.h:120
ERROR_NUMBER LogicalPartitionCreationChecks(IN PPARTENTRY PartEntry)
Definition: partlist.c:4054
BOOLEAN LogicalPartition
Definition: partlist.h:57
smooth NULL
Definition: ftsmooth.c:416
static VOID UpdateDiskLayout(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2520
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
BOOL Error
Definition: chkdsk.c:66
enum _ERROR_NUMBER ERROR_NUMBER
ULONG SectorCount
Definition: part_xbox.c:32
#define DPRINT1
Definition: precomp.h:8
static PPARTENTRY InitializePartitionEntry(IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
Definition: partlist.c:855
static VOID AssignDriveLetters(IN PPARTLIST List)
Definition: partlist.c:316

Referenced by CreateLogicalPartitionPage(), and SelectPartitionPage().

◆ CreatePartitionList()

PPARTLIST CreatePartitionList ( VOID  )

Definition at line 1840 of file partlist.c.

1841 {
1842  PPARTLIST List;
1846  ULONG ReturnSize;
1847  NTSTATUS Status;
1848  ULONG DiskNumber;
1852 
1854  0,
1855  sizeof(PARTLIST));
1856  if (List == NULL)
1857  return NULL;
1858 
1859  List->SystemPartition = NULL;
1860  List->OriginalSystemPartition = NULL;
1861 
1862  InitializeListHead(&List->DiskListHead);
1863  InitializeListHead(&List->BiosDiskListHead);
1864 
1865  /*
1866  * Enumerate the disks seen by the BIOS; this will be used later
1867  * to map drives seen by NTOS with their corresponding BIOS names.
1868  */
1870 
1871  /* Enumerate disks seen by NTOS */
1873  &Sdi,
1874  sizeof(Sdi),
1875  &ReturnSize);
1876  if (!NT_SUCCESS(Status))
1877  {
1878  DPRINT1("NtQuerySystemInformation() failed, Status 0x%08lx", Status);
1880  return NULL;
1881  }
1882 
1883  for (DiskNumber = 0; DiskNumber < Sdi.NumberOfDisks; DiskNumber++)
1884  {
1886  L"\\Device\\Harddisk%lu\\Partition0",
1887  DiskNumber);
1889 
1891  &Name,
1893  NULL,
1894  NULL);
1895 
1899  &Iosb,
1902  if (NT_SUCCESS(Status))
1903  {
1904  AddDiskToList(FileHandle, DiskNumber, List);
1906  }
1907  }
1908 
1912 
1913  return List;
1914 }
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:35
NTSYSAPI NTSTATUS NTAPI NtQuerySystemInformation(IN SYSTEM_INFORMATION_CLASS SystemInfoClass, OUT PVOID SystemInfoBuffer, IN ULONG SystemInfoBufferSize, OUT PULONG BytesReturned OPTIONAL)
struct _PARTLIST * PPARTLIST
LONG NTSTATUS
Definition: precomp.h:26
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:603
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define FILE_SHARE_WRITE
Definition: nt_native.h:681
static VOID UpdateDiskSignatures(IN PPARTLIST List)
Definition: partlist.c:1344
#define FILE_SHARE_READ
Definition: compat.h:125
HANDLE FileHandle
Definition: stats.c:38
#define FILE_READ_DATA
Definition: nt_native.h:628
struct NameRec_ * Name
Definition: cdprocs.h:464
smooth NULL
Definition: ftsmooth.c:416
Definition: bufpool.h:45
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
NTSYSAPI NTSTATUS NTAPI NtOpenFile(OUT PHANDLE phFile, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes, OUT PIO_STATUS_BLOCK pIoStatusBlock, IN ULONG ShareMode, IN ULONG OpenMode)
Definition: file.c:3951
LIST_ENTRY List
Definition: psmgr.c:57
__wchar_t WCHAR
Definition: xmlstorage.h:180
return Iosb
Definition: create.c:4426
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
static VOID UpdateHwDiskNumbers(IN PPARTLIST List)
Definition: partlist.c:1374
#define MAX_PATH
Definition: compat.h:26
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3399
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
#define FILE_READ_ATTRIBUTES
Definition: nt_native.h:647
static const WCHAR L[]
Definition: oid.c:1250
#define SYNCHRONIZE
Definition: nt_native.h:61
HANDLE ProcessHeap
Definition: servman.c:15
Status
Definition: gdiplustypes.h:24
static VOID EnumerateBiosDiskEntries(IN PPARTLIST PartList)
Definition: partlist.c:515
static VOID AddDiskToList(IN HANDLE FileHandle, IN ULONG DiskNumber, IN PPARTLIST List)
Definition: partlist.c:1435
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define DPRINT1
Definition: precomp.h:8
#define FILE_SYNCHRONOUS_IO_NONALERT
Definition: from_kernel.h:31
unsigned int ULONG
Definition: retypes.h:1
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
static VOID AssignDriveLetters(IN PPARTLIST List)
Definition: partlist.c:316

Referenced by LoadSetupData(), rescan_main(), SelectPartitionPage(), UpgradeRepairPage(), and wmain().

◆ CreatePrimaryPartition()

BOOLEAN CreatePrimaryPartition ( IN PPARTLIST  List,
IN PPARTENTRY  SelectedEntry,
IN ULONGLONG  SectorCount,
IN BOOLEAN  AutoCreate 
)

Definition at line 2769 of file partlist.c.

2774 {
2776  PPARTENTRY PartEntry;
2777 
2778  DPRINT1("CreatePrimaryPartition(%I64u)\n", SectorCount);
2779 
2780  if (List == NULL ||
2781  SelectedEntry == NULL ||
2782  SelectedEntry->DiskEntry == NULL ||
2783  SelectedEntry->IsPartitioned)
2784  {
2785  return FALSE;
2786  }
2787 
2788  Error = PrimaryPartitionCreationChecks(SelectedEntry);
2789  if (Error != NOT_AN_ERROR)
2790  {
2791  DPRINT1("PrimaryPartitionCreationChecks() failed with error %lu\n", Error);
2792  return FALSE;
2793  }
2794 
2795  /* Convert the current entry, or insert and initialize a new partition entry */
2796  PartEntry = InitializePartitionEntry(SelectedEntry->DiskEntry, SelectedEntry, SectorCount, AutoCreate);
2797  if (PartEntry == NULL)
2798  return FALSE;
2799 
2800  UpdateDiskLayout(PartEntry->DiskEntry);
2801 
2803 
2804  return TRUE;
2805 }
#define TRUE
Definition: types.h:120
smooth NULL
Definition: ftsmooth.c:416
static VOID UpdateDiskLayout(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2520
ERROR_NUMBER PrimaryPartitionCreationChecks(IN PPARTENTRY PartEntry)
Definition: partlist.c:3996
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
BOOL Error
Definition: chkdsk.c:66
enum _ERROR_NUMBER ERROR_NUMBER
ULONG SectorCount
Definition: part_xbox.c:32
#define DPRINT1
Definition: precomp.h:8
static PPARTENTRY InitializePartitionEntry(IN PDISKENTRY DiskEntry, IN PPARTENTRY PartEntry, IN ULONGLONG SectorCount, IN BOOLEAN AutoCreate)
Definition: partlist.c:855
static VOID AssignDriveLetters(IN PPARTLIST List)
Definition: partlist.c:316

Referenced by CreatePrimaryPartitionPage(), SelectFileSystemPage(), and SelectPartitionPage().

◆ DeletePartition()

BOOLEAN DeletePartition ( IN PPARTLIST  List,
IN PPARTENTRY  PartEntry,
OUT PPARTENTRY *FreeRegion  OPTIONAL 
)

Definition at line 3041 of file partlist.c.

3045 {
3046  PDISKENTRY DiskEntry;
3047  PPARTENTRY PrevPartEntry;
3048  PPARTENTRY NextPartEntry;
3049  PPARTENTRY LogicalPartEntry;
3051 
3052  if (List == NULL ||
3053  PartEntry == NULL ||
3054  PartEntry->DiskEntry == NULL ||
3055  PartEntry->IsPartitioned == FALSE)
3056  {
3057  return FALSE;
3058  }
3059 
3060  ASSERT(PartEntry->PartitionType != PARTITION_ENTRY_UNUSED);
3061 
3062  /* Clear the system partition pointers if it is being deleted */
3063  if (List->SystemPartition == PartEntry)
3064  {
3065  ASSERT(List->SystemPartition);
3066  ASSERT(List->SystemPartition->DiskEntry->MediaType != RemovableMedia);
3067 
3068  if (List->SystemPartition == List->OriginalSystemPartition)
3069  List->OriginalSystemPartition = NULL;
3070  List->SystemPartition = NULL;
3071  }
3072 
3073  DiskEntry = PartEntry->DiskEntry;
3074 
3075  /* Check which type of partition (primary/logical or extended) is being deleted */
3076  if (DiskEntry->ExtendedPartition == PartEntry)
3077  {
3078  /* An extended partition is being deleted: delete all logical partition entries */
3079  while (!IsListEmpty(&DiskEntry->LogicalPartListHead))
3080  {
3081  Entry = RemoveHeadList(&DiskEntry->LogicalPartListHead);
3082  LogicalPartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
3083 
3084  /* Dismount the logical partition */
3085  DismountVolume(LogicalPartEntry);
3086 
3087  /* Delete it */
3088  RtlFreeHeap(ProcessHeap, 0, LogicalPartEntry);
3089  }
3090 
3091  DiskEntry->ExtendedPartition = NULL;
3092  }
3093  else
3094  {
3095  /* A primary partition is being deleted: dismount it */
3096  DismountVolume(PartEntry);
3097  }
3098 
3099  /* Adjust the unpartitioned disk space entries */
3100 
3101  /* Get pointer to previous and next unpartitioned entries */
3102  PrevPartEntry = GetPrevUnpartitionedEntry(PartEntry);
3103  NextPartEntry = GetNextUnpartitionedEntry(PartEntry);
3104 
3105  if (PrevPartEntry != NULL && NextPartEntry != NULL)
3106  {
3107  /* Merge the previous, current and next unpartitioned entries */
3108 
3109  /* Adjust the previous entry length */
3110  PrevPartEntry->SectorCount.QuadPart += (PartEntry->SectorCount.QuadPart + NextPartEntry->SectorCount.QuadPart);
3111 
3112  /* Remove the current and next entries */
3113  RemoveEntryList(&PartEntry->ListEntry);
3114  RtlFreeHeap(ProcessHeap, 0, PartEntry);
3115  RemoveEntryList(&NextPartEntry->ListEntry);
3116  RtlFreeHeap(ProcessHeap, 0, NextPartEntry);
3117 
3118  /* Optionally return the freed region */
3119  if (FreeRegion)
3120  *FreeRegion = PrevPartEntry;
3121  }
3122  else if (PrevPartEntry != NULL && NextPartEntry == NULL)
3123  {
3124  /* Merge the current and the previous unpartitioned entries */
3125 
3126  /* Adjust the previous entry length */
3127  PrevPartEntry->SectorCount.QuadPart += PartEntry->SectorCount.QuadPart;
3128 
3129  /* Remove the current entry */
3130  RemoveEntryList(&PartEntry->ListEntry);
3131  RtlFreeHeap(ProcessHeap, 0, PartEntry);
3132 
3133  /* Optionally return the freed region */
3134  if (FreeRegion)
3135  *FreeRegion = PrevPartEntry;
3136  }
3137  else if (PrevPartEntry == NULL && NextPartEntry != NULL)
3138  {
3139  /* Merge the current and the next unpartitioned entries */
3140 
3141  /* Adjust the next entry offset and length */
3142  NextPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart;
3143  NextPartEntry->SectorCount.QuadPart += PartEntry->SectorCount.QuadPart;
3144 
3145  /* Remove the current entry */
3146  RemoveEntryList(&PartEntry->ListEntry);
3147  RtlFreeHeap(ProcessHeap, 0, PartEntry);
3148 
3149  /* Optionally return the freed region */
3150  if (FreeRegion)
3151  *FreeRegion = NextPartEntry;
3152  }
3153  else
3154  {
3155  /* Nothing to merge but change the current entry */
3156  PartEntry->IsPartitioned = FALSE;
3157  PartEntry->PartitionType = PARTITION_ENTRY_UNUSED;
3158  PartEntry->FormatState = Unformatted;
3159  PartEntry->FileSystem[0] = L'\0';
3160  PartEntry->DriveLetter = 0;
3161  PartEntry->OnDiskPartitionNumber = 0;
3162  PartEntry->PartitionNumber = 0;
3163  // PartEntry->PartitionIndex = 0;
3164 
3165  /* Optionally return the freed region */
3166  if (FreeRegion)
3167  *FreeRegion = PartEntry;
3168  }
3169 
3170  UpdateDiskLayout(DiskEntry);
3171 
3173 
3174  return TRUE;
3175 }
ULARGE_INTEGER StartSector
Definition: partlist.h:42
#define TRUE
Definition: types.h:120
struct _Entry Entry
Definition: kefuncs.h:640
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:603
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
PPARTENTRY ExtendedPartition
Definition: partlist.h:129
FORCEINLINE BOOLEAN RemoveEntryList(_In_ PLIST_ENTRY Entry)
Definition: rtlfuncs.h:105
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
LIST_ENTRY ListEntry
Definition: partlist.h:36
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
smooth NULL
Definition: ftsmooth.c:416
FORCEINLINE PLIST_ENTRY RemoveHeadList(_Inout_ PLIST_ENTRY ListHead)
Definition: rtlfuncs.h:128
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
static VOID UpdateDiskLayout(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2520
LIST_ENTRY List
Definition: psmgr.c:57
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
Definition: typedefs.h:117
static NTSTATUS DismountVolume(IN PPARTENTRY PartEntry)
Definition: partlist.c:2936
HANDLE ProcessHeap
Definition: servman.c:15
static PPARTENTRY GetPrevUnpartitionedEntry(IN PPARTENTRY PartEntry)
Definition: partlist.c:2700
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
static PPARTENTRY GetNextUnpartitionedEntry(IN PPARTENTRY PartEntry)
Definition: partlist.c:2735
base of all file and directory entries
Definition: entries.h:82
static VOID AssignDriveLetters(IN PPARTLIST List)
Definition: partlist.c:316
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by DeletePartitionPage().

◆ DestroyPartitionList()

VOID DestroyPartitionList ( IN PPARTLIST  List)

Definition at line 1917 of file partlist.c.

1919 {
1920  PDISKENTRY DiskEntry;
1921  PBIOSDISKENTRY BiosDiskEntry;
1922  PPARTENTRY PartEntry;
1924 
1925  /* Release disk and partition info */
1926  while (!IsListEmpty(&List->DiskListHead))
1927  {
1928  Entry = RemoveHeadList(&List->DiskListHead);
1929  DiskEntry = CONTAINING_RECORD(Entry, DISKENTRY, ListEntry);
1930 
1931  /* Release driver name */
1932  RtlFreeUnicodeString(&DiskEntry->DriverName);
1933 
1934  /* Release primary partition list */
1935  while (!IsListEmpty(&DiskEntry->PrimaryPartListHead))
1936  {
1937  Entry = RemoveHeadList(&DiskEntry->PrimaryPartListHead);
1938  PartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
1939 
1940  RtlFreeHeap(ProcessHeap, 0, PartEntry);
1941  }
1942 
1943  /* Release logical partition list */
1944  while (!IsListEmpty(&DiskEntry->LogicalPartListHead))
1945  {
1946  Entry = RemoveHeadList(&DiskEntry->LogicalPartListHead);
1947  PartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
1948 
1949  RtlFreeHeap(ProcessHeap, 0, PartEntry);
1950  }
1951 
1952  /* Release layout buffer */
1953  if (DiskEntry->LayoutBuffer != NULL)
1954  RtlFreeHeap(ProcessHeap, 0, DiskEntry->LayoutBuffer);
1955 
1956  /* Release disk entry */
1957  RtlFreeHeap(ProcessHeap, 0, DiskEntry);
1958  }
1959 
1960  /* Release the bios disk info */
1961  while (!IsListEmpty(&List->BiosDiskListHead))
1962  {
1963  Entry = RemoveHeadList(&List->BiosDiskListHead);
1964  BiosDiskEntry = CONTAINING_RECORD(Entry, BIOSDISKENTRY, ListEntry);
1965 
1966  RtlFreeHeap(ProcessHeap, 0, BiosDiskEntry);
1967  }
1968 
1969  /* Release list head */
1971 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
struct _Entry Entry
Definition: kefuncs.h:640
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:603
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
smooth NULL
Definition: ftsmooth.c:416
FORCEINLINE PLIST_ENTRY RemoveHeadList(_Inout_ PLIST_ENTRY ListHead)
Definition: rtlfuncs.h:128
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
LIST_ENTRY List
Definition: psmgr.c:57
UNICODE_STRING DriverName
Definition: partlist.h:117
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
Definition: typedefs.h:117
HANDLE ProcessHeap
Definition: servman.c:15
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
PDRIVE_LAYOUT_INFORMATION LayoutBuffer
Definition: partlist.h:119
base of all file and directory entries
Definition: entries.h:82

Referenced by QuitPage(), rescan_main(), SelectPartitionPage(), and wmain().

◆ DiskConfigurationDataQueryRoutine()

static NTSTATUS NTAPI DiskConfigurationDataQueryRoutine ( PWSTR  ValueName,
ULONG  ValueType,
PVOID  ValueData,
ULONG  ValueLength,
PVOID  Context,
PVOID  EntryContext 
)
static

Definition at line 425 of file partlist.c.

432 {
433  PBIOSDISKENTRY BiosDiskEntry = (PBIOSDISKENTRY)Context;
434  PCM_FULL_RESOURCE_DESCRIPTOR FullResourceDescriptor;
435  PCM_DISK_GEOMETRY_DEVICE_DATA DiskGeometry;
436  ULONG i;
437 
440  return STATUS_UNSUCCESSFUL;
441 
442  FullResourceDescriptor = (PCM_FULL_RESOURCE_DESCRIPTOR)ValueData;
443 
444  /* Hm. Version and Revision are not set on Microsoft Windows XP... */
445 #if 0
446  if (FullResourceDescriptor->PartialResourceList.Version != 1 ||
447  FullResourceDescriptor->PartialResourceList.Revision != 1)
448  return STATUS_UNSUCCESSFUL;
449 #endif
450 
451  for (i = 0; i < FullResourceDescriptor->PartialResourceList.Count; i++)
452  {
454  FullResourceDescriptor->PartialResourceList.PartialDescriptors[i].u.DeviceSpecificData.DataSize != sizeof(CM_DISK_GEOMETRY_DEVICE_DATA))
455  continue;
456 
457  DiskGeometry = (PCM_DISK_GEOMETRY_DEVICE_DATA)&FullResourceDescriptor->PartialResourceList.PartialDescriptors[i + 1];
458  BiosDiskEntry->DiskGeometry = *DiskGeometry;
459 
460  return STATUS_SUCCESS;
461  }
462 
463  return STATUS_UNSUCCESSFUL;
464 }
#define CmResourceTypeDeviceSpecific
Definition: hwresource.cpp:127
_In_ PCWSTR _In_z_ PCWSTR _In_ ULONG ValueType
Definition: rtlfuncs.h:4000
union _CM_PARTIAL_RESOURCE_DESCRIPTOR::@369 u
struct _CM_DISK_GEOMETRY_DEVICE_DATA * PCM_DISK_GEOMETRY_DEVICE_DATA
struct _BIOSDISKENTRY * PBIOSDISKENTRY
CM_PARTIAL_RESOURCE_LIST PartialResourceList
Definition: hwresource.cpp:160
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
struct _CM_FULL_RESOURCE_DESCRIPTOR * PCM_FULL_RESOURCE_DESCRIPTOR
struct _CM_PARTIAL_RESOURCE_DESCRIPTOR::@369::@378 DeviceSpecificData
#define REG_FULL_RESOURCE_DESCRIPTOR
Definition: nt_native.h:1503
CM_DISK_GEOMETRY_DEVICE_DATA DiskGeometry
Definition: partlist.h:142
_In_ GUID _In_ PVOID ValueData
Definition: hubbusif.h:311
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
CM_PARTIAL_RESOURCE_DESCRIPTOR PartialDescriptors[1]
Definition: hwresource.cpp:119
_In_ GUID _In_ PVOID _In_ ULONG ValueLength
Definition: hubbusif.h:311
unsigned int ULONG
Definition: retypes.h:1
return STATUS_SUCCESS
Definition: btrfs.c:2745

Referenced by EnumerateBiosDiskEntries().

◆ DiskIdentifierQueryRoutine()

static NTSTATUS NTAPI DiskIdentifierQueryRoutine ( PWSTR  ValueName,
ULONG  ValueType,
PVOID  ValueData,
ULONG  ValueLength,
PVOID  Context,
PVOID  EntryContext 
)
static

Definition at line 395 of file partlist.c.

402 {
403  PBIOSDISKENTRY BiosDiskEntry = (PBIOSDISKENTRY)Context;
404  UNICODE_STRING NameU;
405 
406  if (ValueType == REG_SZ &&
407  ValueLength == 20 * sizeof(WCHAR) &&
408  ((PWCHAR)ValueData)[8] == L'-')
409  {
410  NameU.Buffer = (PWCHAR)ValueData;
411  NameU.Length = NameU.MaximumLength = 8 * sizeof(WCHAR);
412  RtlUnicodeStringToInteger(&NameU, 16, &BiosDiskEntry->Checksum);
413 
414  NameU.Buffer = (PWCHAR)ValueData + 9;
415  RtlUnicodeStringToInteger(&NameU, 16, &BiosDiskEntry->Signature);
416 
417  return STATUS_SUCCESS;
418  }
419 
420  return STATUS_UNSUCCESSFUL;
421 }
USHORT MaximumLength
Definition: env_spec_w32.h:370
ULONG Checksum
Definition: partlist.h:140
_In_ PCWSTR _In_z_ PCWSTR _In_ ULONG ValueType
Definition: rtlfuncs.h:4000
ULONG Signature
Definition: partlist.h:139
uint16_t * PWCHAR
Definition: typedefs.h:54
struct _BIOSDISKENTRY * PBIOSDISKENTRY
__wchar_t WCHAR
Definition: xmlstorage.h:180
_In_ GUID _In_ PVOID ValueData
Definition: hubbusif.h:311
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
static const WCHAR L[]
Definition: oid.c:1250
_In_ GUID _In_ PVOID _In_ ULONG ValueLength
Definition: hubbusif.h:311
NTSYSAPI NTSTATUS NTAPI RtlUnicodeStringToInteger(PUNICODE_STRING String, ULONG Base, PULONG Value)
return STATUS_SUCCESS
Definition: btrfs.c:2745
#define REG_SZ
Definition: layer.c:22

Referenced by EnumerateBiosDiskEntries().

◆ DismountVolume()

static NTSTATUS DismountVolume ( IN PPARTENTRY  PartEntry)
static

Definition at line 2936 of file partlist.c.

2938 {
2939  NTSTATUS Status;
2940  NTSTATUS LockStatus;
2944  HANDLE PartitionHandle;
2946 
2947  /* Check whether the partition is valid and was mounted by the system */
2948  if (!PartEntry->IsPartitioned ||
2949  IsContainerPartition(PartEntry->PartitionType) ||
2950  !IsRecognizedPartition(PartEntry->PartitionType) ||
2951  PartEntry->FormatState == Unformatted /* || PartEntry->FormatState == UnknownFormat */ ||
2952  !*PartEntry->FileSystem ||
2953  PartEntry->PartitionNumber == 0)
2954  {
2955  /* The partition is not mounted, so just return success */
2956  return STATUS_SUCCESS;
2957  }
2958 
2959  ASSERT(PartEntry->PartitionType != PARTITION_ENTRY_UNUSED);
2960 
2961  /* Open the volume */
2963  L"\\Device\\Harddisk%lu\\Partition%lu",
2964  PartEntry->DiskEntry->DiskNumber,
2965  PartEntry->PartitionNumber);
2967 
2969  &Name,
2971  NULL,
2972  NULL);
2973 
2974  Status = NtOpenFile(&PartitionHandle,
2977  &IoStatusBlock,
2980  if (!NT_SUCCESS(Status))
2981  {
2982  DPRINT1("ERROR: Cannot open volume %wZ for dismounting! (Status 0x%lx)\n", &Name, Status);
2983  return Status;
2984  }
2985 
2986  /* Lock the volume */
2987  LockStatus = NtFsControlFile(PartitionHandle,
2988  NULL,
2989  NULL,
2990  NULL,
2991  &IoStatusBlock,
2993  NULL,
2994  0,
2995  NULL,
2996  0);
2997  if (!NT_SUCCESS(LockStatus))
2998  {
2999  DPRINT1("WARNING: Failed to lock volume! Operations may fail! (Status 0x%lx)\n", LockStatus);
3000  }
3001 
3002  /* Dismount the volume */
3003  Status = NtFsControlFile(PartitionHandle,
3004  NULL,
3005  NULL,
3006  NULL,
3007  &IoStatusBlock,
3009  NULL,
3010  0,
3011  NULL,
3012  0);
3013  if (!NT_SUCCESS(Status))
3014  {
3015  DPRINT1("Failed to unmount volume (Status 0x%lx)\n", Status);
3016  }
3017 
3018  /* Unlock the volume */
3019  LockStatus = NtFsControlFile(PartitionHandle,
3020  NULL,
3021  NULL,
3022  NULL,
3023  &IoStatusBlock,
3025  NULL,
3026  0,
3027  NULL,
3028  0);
3029  if (!NT_SUCCESS(LockStatus))
3030  {
3031  DPRINT1("Failed to unlock volume (Status 0x%lx)\n", LockStatus);
3032  }
3033 
3034  /* Close the volume */
3035  NtClose(PartitionHandle);
3036 
3037  return Status;
3038 }
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:35
#define FSCTL_UNLOCK_VOLUME
Definition: nt_native.h:833
LONG NTSTATUS
Definition: precomp.h:26
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
NTSYSCALLAPI NTSTATUS NTAPI NtFsControlFile(HANDLE FileHandle, HANDLE Event, PIO_APC_ROUTINE ApcRoutine, PVOID ApcContext, PIO_STATUS_BLOCK IoStatusBlock, ULONG FsControlCode, PVOID InputBuffer, ULONG InputBufferLength, PVOID OutputBuffer, ULONG OutputBufferLength)
#define FILE_SHARE_WRITE
Definition: nt_native.h:681
#define FILE_SHARE_READ
Definition: compat.h:125
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
#define GENERIC_WRITE
Definition: nt_native.h:90
struct NameRec_ * Name
Definition: cdprocs.h:464
smooth NULL
Definition: ftsmooth.c:416
Definition: bufpool.h:45
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
#define FSCTL_DISMOUNT_VOLUME
Definition: nt_native.h:834
NTSYSAPI NTSTATUS NTAPI NtOpenFile(OUT PHANDLE phFile, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes, OUT PIO_STATUS_BLOCK pIoStatusBlock, IN ULONG ShareMode, IN ULONG OpenMode)
Definition: file.c:3951
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define IsRecognizedPartition(PartitionType)
Definition: ntdddisk.h:271
#define MAX_PATH
Definition: compat.h:26
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3399
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
#define GENERIC_READ
Definition: compat.h:124
#define SYNCHRONIZE
Definition: nt_native.h:61
Status
Definition: gdiplustypes.h:24
static OUT PIO_STATUS_BLOCK IoStatusBlock
Definition: pipe.c:75
#define DPRINT1
Definition: precomp.h:8
#define FILE_SYNCHRONOUS_IO_NONALERT
Definition: from_kernel.h:31
#define FSCTL_LOCK_VOLUME
Definition: nt_native.h:832
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
return STATUS_SUCCESS
Definition: btrfs.c:2745

Referenced by DeletePartition().

◆ EnumerateBiosDiskEntries()

static VOID EnumerateBiosDiskEntries ( IN PPARTLIST  PartList)
static

Definition at line 515 of file partlist.c.

517 {
519  WCHAR Name[120];
520  ULONG AdapterCount;
522  ULONG DiskCount;
524  PCM_INT13_DRIVE_PARAMETER Int13Drives;
525  PBIOSDISKENTRY BiosDiskEntry;
526 
527 #define ROOT_NAME L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION\\System\\MultifunctionAdapter"
528 
529  memset(QueryTable, 0, sizeof(QueryTable));
530 
531  QueryTable[1].Name = L"Configuration Data";
533  Int13Drives = NULL;
535  L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION\\System",
536  &QueryTable[1],
537  (PVOID)&Int13Drives,
538  NULL);
539  if (!NT_SUCCESS(Status))
540  {
541  DPRINT1("Unable to query the 'Configuration Data' key in '\\Registry\\Machine\\HARDWARE\\DESCRIPTION\\System', status=%lx\n", Status);
542  return;
543  }
544 
545  for (AdapterCount = 0; ; ++AdapterCount)
546  {
548  L"%s\\%lu",
549  ROOT_NAME, AdapterCount);
551  Name,
552  &QueryTable[2],
553  NULL,
554  NULL);
555  if (!NT_SUCCESS(Status))
556  {
557  break;
558  }
559 
561  L"%s\\%lu\\DiskController",
562  ROOT_NAME, AdapterCount);
564  Name,
565  &QueryTable[2],
566  NULL,
567  NULL);
568  if (NT_SUCCESS(Status))
569  {
570  for (ControllerCount = 0; ; ++ControllerCount)
571  {
573  L"%s\\%lu\\DiskController\\%lu",
574  ROOT_NAME, AdapterCount, ControllerCount);
576  Name,
577  &QueryTable[2],
578  NULL,
579  NULL);
580  if (!NT_SUCCESS(Status))
581  {
582  RtlFreeHeap(ProcessHeap, 0, Int13Drives);
583  return;
584  }
585 
587  L"%s\\%lu\\DiskController\\%lu\\DiskPeripheral",
588  ROOT_NAME, AdapterCount, ControllerCount);
590  Name,
591  &QueryTable[2],
592  NULL,
593  NULL);
594  if (NT_SUCCESS(Status))
595  {
596  QueryTable[0].Name = L"Identifier";
598  QueryTable[1].Name = L"Configuration Data";
600 
601  for (DiskCount = 0; ; ++DiskCount)
602  {
604  if (BiosDiskEntry == NULL)
605  {
606  RtlFreeHeap(ProcessHeap, 0, Int13Drives);
607  return;
608  }
609 
611  L"%s\\%lu\\DiskController\\%lu\\DiskPeripheral\\%lu",
612  ROOT_NAME, AdapterCount, ControllerCount, DiskCount);
614  Name,
615  QueryTable,
616  (PVOID)BiosDiskEntry,
617  NULL);
618  if (!NT_SUCCESS(Status))
619  {
620  RtlFreeHeap(ProcessHeap, 0, BiosDiskEntry);
621  RtlFreeHeap(ProcessHeap, 0, Int13Drives);
622  return;
623  }
624 
625  BiosDiskEntry->AdapterNumber = 0; // And NOT "AdapterCount" as it needs to be hardcoded for BIOS!
626  BiosDiskEntry->ControllerNumber = ControllerCount;
627  BiosDiskEntry->DiskNumber = DiskCount;
628  BiosDiskEntry->DiskEntry = NULL;
629 
630  if (DiskCount < Int13Drives[0].NumberDrives)
631  {
632  BiosDiskEntry->Int13DiskData = Int13Drives[DiskCount];
633  }
634  else
635  {
636  DPRINT1("Didn't find Int13 drive data for disk %u\n", DiskCount);
637  }
638 
639  InsertTailList(&PartList->BiosDiskListHead, &BiosDiskEntry->ListEntry);
640 
641  DPRINT("--->\n");
642  DPRINT("AdapterNumber: %lu\n", BiosDiskEntry->AdapterNumber);
643  DPRINT("ControllerNumber: %lu\n", BiosDiskEntry->ControllerNumber);
644  DPRINT("DiskNumber: %lu\n", BiosDiskEntry->DiskNumber);
645  DPRINT("Signature: %08lx\n", BiosDiskEntry->Signature);
646  DPRINT("Checksum: %08lx\n", BiosDiskEntry->Checksum);
647  DPRINT("BytesPerSector: %lu\n", BiosDiskEntry->DiskGeometry.BytesPerSector);
648  DPRINT("NumberOfCylinders: %lu\n", BiosDiskEntry->DiskGeometry.NumberOfCylinders);
649  DPRINT("NumberOfHeads: %lu\n", BiosDiskEntry->DiskGeometry.NumberOfHeads);
650  DPRINT("DriveSelect: %02x\n", BiosDiskEntry->Int13DiskData.DriveSelect);
651  DPRINT("MaxCylinders: %lu\n", BiosDiskEntry->Int13DiskData.MaxCylinders);
652  DPRINT("SectorsPerTrack: %d\n", BiosDiskEntry->Int13DiskData.SectorsPerTrack);
653  DPRINT("MaxHeads: %d\n", BiosDiskEntry->Int13DiskData.MaxHeads);
654  DPRINT("NumberDrives: %d\n", BiosDiskEntry->Int13DiskData.NumberDrives);
655  DPRINT("<---\n");
656  }
657  }
658  }
659  }
660  }
661 
662  RtlFreeHeap(ProcessHeap, 0, Int13Drives);
663 
664 #undef ROOT_NAME
665 }
_In_ PCWSTR _Inout_ _At_ QueryTable _Pre_unknown_ PRTL_QUERY_REGISTRY_TABLE QueryTable
Definition: rtlfuncs.h:3988
ULONG Checksum
Definition: partlist.h:140
ULONG Signature
Definition: partlist.h:139
LONG NTSTATUS
Definition: precomp.h:26
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:603
ULONG ControllerNumber
Definition: partlist.h:137
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define InsertTailList(ListHead, Entry)
ULONG ControllerCount
Definition: fdc.c:18
PRTL_QUERY_REGISTRY_ROUTINE QueryRoutine
Definition: nt_native.h:109
static NTSTATUS NTAPI SystemConfigurationDataQueryRoutine(PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
Definition: partlist.c:468
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
ULONG AdapterNumber
Definition: partlist.h:136
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
CM_DISK_GEOMETRY_DEVICE_DATA DiskGeometry
Definition: partlist.h:142
NTSYSAPI NTSTATUS WINAPI RtlQueryRegistryValues(ULONG, PCWSTR, PRTL_QUERY_REGISTRY_TABLE, PVOID, PVOID)
PDISKENTRY DiskEntry
Definition: partlist.h:141
static const WCHAR L[]
Definition: oid.c:1250
#define RTL_REGISTRY_ABSOLUTE
Definition: nt_native.h:161
HANDLE ProcessHeap
Definition: servman.c:15
Status
Definition: gdiplustypes.h:24
LIST_ENTRY ListEntry
Definition: partlist.h:135
ULONG DiskNumber
Definition: partlist.h:138
#define HEAP_ZERO_MEMORY
Definition: compat.h:123
#define DPRINT1
Definition: precomp.h:8
#define ROOT_NAME
static NTSTATUS NTAPI DiskConfigurationDataQueryRoutine(PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
Definition: partlist.c:425
unsigned int ULONG
Definition: retypes.h:1
static NTSTATUS NTAPI DiskIdentifierQueryRoutine(PWSTR ValueName, ULONG ValueType, PVOID ValueData, ULONG ValueLength, PVOID Context, PVOID EntryContext)
Definition: partlist.c:395
CM_INT13_DRIVE_PARAMETER Int13DiskData
Definition: partlist.h:143
#define memset(x, y, z)
Definition: compat.h:39

Referenced by CreatePartitionList().

◆ ExtendedPartitionCreationChecks()

ERROR_NUMBER ExtendedPartitionCreationChecks ( IN PPARTENTRY  PartEntry)

Definition at line 4023 of file partlist.c.

4025 {
4026  PDISKENTRY DiskEntry = PartEntry->DiskEntry;
4027 
4028  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
4029  {
4030  DPRINT1("GPT-partitioned disk detected, not currently supported by SETUP!\n");
4031  return ERROR_WARN_PARTITION;
4032  }
4033 
4034  /* Fail if the partition is already in use */
4035  if (PartEntry->IsPartitioned)
4036  return ERROR_NEW_PARTITION;
4037 
4038  /* Only one primary partition is allowed on super-floppy */
4039  if (IsSuperFloppy(DiskEntry))
4041 
4042  /* Fail if there are already 4 primary partitions in the list */
4043  if (GetPrimaryPartitionCount(DiskEntry) >= 4)
4045 
4046  /* Fail if there is another extended partition in the list */
4047  if (DiskEntry->ExtendedPartition != NULL)
4048  return ERROR_ONLY_ONE_EXTENDED;
4049 
4050  return ERROR_SUCCESS;
4051 }
#define ERROR_SUCCESS
Definition: deptool.c:10
PPARTENTRY ExtendedPartition
Definition: partlist.h:129
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
static ULONG GetPrimaryPartitionCount(IN PDISKENTRY DiskEntry)
Definition: partlist.c:2414
BOOLEAN IsSuperFloppy(IN PDISKENTRY DiskEntry)
Definition: partlist.c:679
#define DPRINT1
Definition: precomp.h:8

Referenced by CreateExtendedPartition(), and SelectPartitionPage().

◆ GetActiveDiskPartition()

static PPARTENTRY GetActiveDiskPartition ( IN PDISKENTRY  DiskEntry)
static

Definition at line 3184 of file partlist.c.

3186 {
3187  PLIST_ENTRY ListEntry;
3188  PPARTENTRY PartEntry;
3189  PPARTENTRY ActivePartition = NULL;
3190 
3191  /* Check for empty disk list */
3192  // ASSERT(DiskEntry);
3193  if (!DiskEntry)
3194  return NULL;
3195 
3196  /* Check for empty partition list */
3197  if (IsListEmpty(&DiskEntry->PrimaryPartListHead))
3198  return NULL;
3199 
3200  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
3201  {
3202  DPRINT1("GPT-partitioned disk detected, not currently supported by SETUP!\n");
3203  return NULL;
3204  }
3205 
3206  /* Scan all (primary) partitions to find the active disk partition */
3207  for (ListEntry = DiskEntry->PrimaryPartListHead.Flink;
3208  ListEntry != &DiskEntry->PrimaryPartListHead;
3209  ListEntry = ListEntry->Flink)
3210  {
3211  /* Retrieve the partition */
3212  PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry);
3213 
3214  // TODO: Support for GPT disks!
3215 
3216  /* Check if the partition is partitioned, used and active */
3217  if (PartEntry->IsPartitioned &&
3218  // !IsContainerPartition(PartEntry->PartitionType) &&
3219  PartEntry->BootIndicator)
3220  {
3221  /* Yes, we found it */
3222  ASSERT(DiskEntry == PartEntry->DiskEntry);
3224 
3225  ActivePartition = PartEntry;
3226 
3227  DPRINT1("Found active system partition %lu in disk %lu, drive letter %C\n",
3228  PartEntry->PartitionNumber, DiskEntry->DiskNumber,
3229  (PartEntry->DriveLetter == 0) ? L'-' : PartEntry->DriveLetter);
3230  break;
3231  }
3232  }
3233 
3234  /* Check if the disk is new and if so, use its first partition as the active system partition */
3235  if (DiskEntry->NewDisk && ActivePartition != NULL)
3236  {
3237  // FIXME: What to do??
3238  DPRINT1("NewDisk TRUE but already existing active partition?\n");
3239  }
3240 
3241  /* Return the active partition found (or none) */
3242  return ActivePartition;
3243 }
WCHAR DriveLetter
Definition: partlist.h:52
ULONG PartitionNumber
Definition: partlist.h:49
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
Definition: typedefs.h:117
#define DPRINT1
Definition: precomp.h:8
BOOLEAN BootIndicator
Definition: partlist.h:45
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by CheckActiveSystemPartition().

◆ GetDiskByBiosNumber()

PDISKENTRY GetDiskByBiosNumber ( IN PPARTLIST  List,
IN ULONG  HwDiskNumber 
)

Definition at line 1974 of file partlist.c.

1977 {
1978  PDISKENTRY DiskEntry;
1980 
1981  /* Loop over the disks and find the correct one */
1982  for (Entry = List->DiskListHead.Flink;
1983  Entry != &List->DiskListHead;
1984  Entry = Entry->Flink)
1985  {
1986  DiskEntry = CONTAINING_RECORD(Entry, DISKENTRY, ListEntry);
1987 
1988  if (DiskEntry->HwDiskNumber == HwDiskNumber)
1989  {
1990  /* Disk found */
1991  return DiskEntry;
1992  }
1993  }
1994 
1995  /* Disk not found, stop there */
1996  return NULL;
1997 }
struct _Entry Entry
Definition: kefuncs.h:640
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
LIST_ENTRY List
Definition: psmgr.c:57
ULONG HwDiskNumber
Definition: partlist.h:99
Definition: typedefs.h:117
base of all file and directory entries
Definition: entries.h:82

◆ GetDiskByNumber()

PDISKENTRY GetDiskByNumber ( IN PPARTLIST  List,
IN ULONG  DiskNumber 
)

Definition at line 2000 of file partlist.c.

2003 {
2004  PDISKENTRY DiskEntry;
2006 
2007  /* Loop over the disks and find the correct one */
2008  for (Entry = List->DiskListHead.Flink;
2009  Entry != &List->DiskListHead;
2010  Entry = Entry->Flink)
2011  {
2012  DiskEntry = CONTAINING_RECORD(Entry, DISKENTRY, ListEntry);
2013 
2014  if (DiskEntry->DiskNumber == DiskNumber)
2015  {
2016  /* Disk found */
2017  return DiskEntry;
2018  }
2019  }
2020 
2021  /* Disk not found, stop there */
2022  return NULL;
2023 }
struct _Entry Entry
Definition: kefuncs.h:640
ULONG DiskNumber
Definition: partlist.h:105
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
LIST_ENTRY List
Definition: psmgr.c:57
Definition: typedefs.h:117
base of all file and directory entries
Definition: entries.h:82

Referenced by GetDiskOrPartition(), and SelectPartition().

◆ GetDiskBySCSI()

PDISKENTRY GetDiskBySCSI ( IN PPARTLIST  List,
IN USHORT  Port,
IN USHORT  Bus,
IN USHORT  Id 
)

Definition at line 2026 of file partlist.c.

2031 {
2032  PDISKENTRY DiskEntry;
2034 
2035  /* Loop over the disks and find the correct one */
2036  for (Entry = List->DiskListHead.Flink;
2037  Entry != &List->DiskListHead;
2038  Entry = Entry->Flink)
2039  {
2040  DiskEntry = CONTAINING_RECORD(Entry, DISKENTRY, ListEntry);
2041 
2042  if (DiskEntry->Port == Port &&
2043  DiskEntry->Bus == Bus &&
2044  DiskEntry->Id == Id)
2045  {
2046  /* Disk found */
2047  return DiskEntry;
2048  }
2049  }
2050 
2051  /* Disk not found, stop there */
2052  return NULL;
2053 }
CPPORT Port[4]
Definition: headless.c:34
USHORT Id
Definition: partlist.h:109
struct _Entry Entry
Definition: kefuncs.h:640
USHORT Bus
Definition: partlist.h:108
DWORD Id
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
LIST_ENTRY List
Definition: psmgr.c:57
Definition: typedefs.h:117
USHORT Port
Definition: partlist.h:107
base of all file and directory entries
Definition: entries.h:82

Referenced by ResolveArcNameManually().

◆ GetDiskBySignature()

PDISKENTRY GetDiskBySignature ( IN PPARTLIST  List,
IN ULONG  Signature 
)

Definition at line 2056 of file partlist.c.

2059 {
2060  PDISKENTRY DiskEntry;
2062 
2063  /* Loop over the disks and find the correct one */
2064  for (Entry = List->DiskListHead.Flink;
2065  Entry != &List->DiskListHead;
2066  Entry = Entry->Flink)
2067  {
2068  DiskEntry = CONTAINING_RECORD(Entry, DISKENTRY, ListEntry);
2069 
2070  if (DiskEntry->LayoutBuffer->Signature == Signature)
2071  {
2072  /* Disk found */
2073  return DiskEntry;
2074  }
2075  }
2076 
2077  /* Disk not found, stop there */
2078  return NULL;
2079 }
struct _Entry Entry
Definition: kefuncs.h:640
smooth NULL
Definition: ftsmooth.c:416
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
LIST_ENTRY List
Definition: psmgr.c:57
Definition: typedefs.h:117
static const WCHAR Signature[]
Definition: parser.c:141
PDRIVE_LAYOUT_INFORMATION LayoutBuffer
Definition: partlist.h:119
base of all file and directory entries
Definition: entries.h:82

Referenced by ResolveArcNameManually().

◆ GetDiskOrPartition()

BOOLEAN GetDiskOrPartition ( IN PPARTLIST  List,
IN ULONG  DiskNumber,
IN ULONG PartitionNumber  OPTIONAL,
OUT PDISKENTRY pDiskEntry,
OUT PPARTENTRY *pPartEntry  OPTIONAL 
)

Definition at line 2129 of file partlist.c.

2135 {
2136  PDISKENTRY DiskEntry;
2137  PPARTENTRY PartEntry = NULL;
2138 
2139  /* Find the disk */
2140  DiskEntry = GetDiskByNumber(List, DiskNumber);
2141  if (!DiskEntry)
2142  return FALSE;
2143 
2144  /* If we have a partition (PartitionNumber != 0), find it */
2145  if (PartitionNumber != 0)
2146  {
2147  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2148  {
2149  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2150  return FALSE;
2151  }
2152 
2153  PartEntry = GetPartition(/*List,*/ DiskEntry, PartitionNumber);
2154  if (!PartEntry)
2155  return FALSE;
2156  ASSERT(PartEntry->DiskEntry == DiskEntry);
2157  }
2158 
2159  /* Return the disk (and optionally the partition) */
2160  *pDiskEntry = DiskEntry;
2161  if (pPartEntry) *pPartEntry = PartEntry;
2162  return TRUE;
2163 }
#define TRUE
Definition: types.h:120
_In_ ULONG _In_ ULONG PartitionNumber
Definition: iofuncs.h:2056
PPARTENTRY GetPartition(IN PDISKENTRY DiskEntry, IN ULONG PartitionNumber)
Definition: partlist.c:2082
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PDISKENTRY GetDiskByNumber(IN PPARTLIST List, IN ULONG DiskNumber)
Definition: partlist.c:2000
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)

Referenced by EnumerateInstallations().

◆ GetDriverName()

static VOID GetDriverName ( IN PDISKENTRY  DiskEntry)
static

Definition at line 283 of file partlist.c.

285 {
287  WCHAR KeyName[32];
289 
290  RtlInitUnicodeString(&DiskEntry->DriverName, NULL);
291 
293  L"\\Scsi\\Scsi Port %hu",
294  DiskEntry->Port);
295 
297 
298  QueryTable[0].Name = L"Driver";
300  QueryTable[0].EntryContext = &DiskEntry->DriverName;
301 
302  /* This will allocate DiskEntry->DriverName if needed */
304  KeyName,
305  QueryTable,
306  NULL,
307  NULL);
308  if (!NT_SUCCESS(Status))
309  {
310  DPRINT1("RtlQueryRegistryValues() failed (Status %lx)\n", Status);
311  }
312 }
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ ULONG _Out_ PNDIS_STRING KeyName
Definition: ndis.h:4711
_In_ PCWSTR _Inout_ _At_ QueryTable _Pre_unknown_ PRTL_QUERY_REGISTRY_TABLE QueryTable
Definition: rtlfuncs.h:3988
LONG NTSTATUS
Definition: precomp.h:26
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
smooth NULL
Definition: ftsmooth.c:416
static __inline NTSTATUS RtlStringCchPrintfW(_Out_writes_(cchDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cchDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1064
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
NTSYSAPI NTSTATUS WINAPI RtlQueryRegistryValues(ULONG, PCWSTR, PRTL_QUERY_REGISTRY_TABLE, PVOID, PVOID)
static const WCHAR L[]
Definition: oid.c:1250
Status
Definition: gdiplustypes.h:24
#define DPRINT1
Definition: precomp.h:8
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:261
#define RTL_REGISTRY_DEVICEMAP
Definition: nt_native.h:165
#define RTL_QUERY_REGISTRY_DIRECT
Definition: nt_native.h:144

Referenced by AddDiskToList().

◆ GetLogicalPartitionCount()

static ULONG GetLogicalPartitionCount ( IN PDISKENTRY  DiskEntry)
static

Definition at line 2441 of file partlist.c.

2443 {
2444  PLIST_ENTRY ListEntry;
2445  PPARTENTRY PartEntry;
2446  ULONG Count = 0;
2447 
2448  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2449  {
2450  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2451  return 0;
2452  }
2453 
2454  for (ListEntry = DiskEntry->LogicalPartListHead.Flink;
2455  ListEntry != &DiskEntry->LogicalPartListHead;
2456  ListEntry = ListEntry->Flink)
2457  {
2458  PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry);
2459  if (PartEntry->IsPartitioned)
2460  Count++;
2461  }
2462 
2463  return Count;
2464 }
_Inout_ __drv_aliasesMem PSLIST_ENTRY _Inout_ PSLIST_ENTRY _In_ ULONG Count
Definition: exfuncs.h:1015
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
Definition: typedefs.h:117
unsigned int ULONG
Definition: retypes.h:1
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by ReAllocateLayoutBuffer().

◆ GetNextPartition()

PPARTENTRY GetNextPartition ( IN PPARTLIST  List,
IN PPARTENTRY CurrentPart  OPTIONAL 
)

Definition at line 2193 of file partlist.c.

2196 {
2197  PLIST_ENTRY DiskListEntry;
2198  PLIST_ENTRY PartListEntry;
2200 
2201  /* Fail if no disks are available */
2202  if (IsListEmpty(&List->DiskListHead))
2203  return NULL;
2204 
2205  /* Check for the next usable entry on the current partition's disk */
2206  if (CurrentPart != NULL)
2207  {
2208  CurrentDisk = CurrentPart->DiskEntry;
2209 
2210  if (CurrentPart->LogicalPartition)
2211  {
2212  /* Logical partition */
2213 
2214  PartListEntry = CurrentPart->ListEntry.Flink;
2215  if (PartListEntry != &CurrentDisk->LogicalPartListHead)
2216  {
2217  /* Next logical partition */
2218  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2219  return CurrentPart;
2220  }
2221  else
2222  {
2223  PartListEntry = CurrentDisk->ExtendedPartition->ListEntry.Flink;
2224  if (PartListEntry != &CurrentDisk->PrimaryPartListHead)
2225  {
2226  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2227  return CurrentPart;
2228  }
2229  }
2230  }
2231  else
2232  {
2233  /* Primary or extended partition */
2234 
2235  if (CurrentPart->IsPartitioned &&
2236  IsContainerPartition(CurrentPart->PartitionType))
2237  {
2238  /* First logical partition */
2239  PartListEntry = CurrentDisk->LogicalPartListHead.Flink;
2240  if (PartListEntry != &CurrentDisk->LogicalPartListHead)
2241  {
2242  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2243  return CurrentPart;
2244  }
2245  }
2246  else
2247  {
2248  /* Next primary partition */
2249  PartListEntry = CurrentPart->ListEntry.Flink;
2250  if (PartListEntry != &CurrentDisk->PrimaryPartListHead)
2251  {
2252  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2253  return CurrentPart;
2254  }
2255  }
2256  }
2257  }
2258 
2259  /* Search for the first partition entry on the next disk */
2260  for (DiskListEntry = (CurrentPart ? CurrentDisk->ListEntry.Flink
2261  : List->DiskListHead.Flink);
2262  DiskListEntry != &List->DiskListHead;
2263  DiskListEntry = DiskListEntry->Flink)
2264  {
2265  CurrentDisk = CONTAINING_RECORD(DiskListEntry, DISKENTRY, ListEntry);
2266 
2268  {
2269  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2270  continue;
2271  }
2272 
2273  PartListEntry = CurrentDisk->PrimaryPartListHead.Flink;
2274  if (PartListEntry != &CurrentDisk->PrimaryPartListHead)
2275  {
2276  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2277  return CurrentPart;
2278  }
2279  }
2280 
2281  return NULL;
2282 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
PDISKENTRY CurrentDisk
Definition: partlist.c:73
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
PPARTENTRY ExtendedPartition
Definition: partlist.h:129
LIST_ENTRY ListEntry
Definition: partlist.h:36
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
LIST_ENTRY List
Definition: psmgr.c:57
LIST_ENTRY ListEntry
Definition: partlist.h:77
Definition: typedefs.h:117
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126

Referenced by ScrollDownPartitionList().

◆ GetNextUncheckedPartition()

BOOLEAN GetNextUncheckedPartition ( IN PPARTLIST  List,
OUT PDISKENTRY *pDiskEntry  OPTIONAL,
OUT PPARTENTRY pPartEntry 
)

Definition at line 4136 of file partlist.c.

4140 {
4141  PLIST_ENTRY Entry1, Entry2;
4142  PDISKENTRY DiskEntry;
4143  PPARTENTRY PartEntry;
4144 
4145  for (Entry1 = List->DiskListHead.Flink;
4146  Entry1 != &List->DiskListHead;
4147  Entry1 = Entry1->Flink)
4148  {
4149  DiskEntry = CONTAINING_RECORD(Entry1,
4150  DISKENTRY,
4151  ListEntry);
4152 
4153  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
4154  {
4155  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
4156  continue;
4157  }
4158 
4159  for (Entry2 = DiskEntry->PrimaryPartListHead.Flink;
4160  Entry2 != &DiskEntry->PrimaryPartListHead;
4161  Entry2 = Entry2->Flink)
4162  {
4163  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
4164  if (PartEntry->IsPartitioned && PartEntry->NeedsCheck)
4165  {
4166  ASSERT(DiskEntry == PartEntry->DiskEntry);
4167  if (pDiskEntry) *pDiskEntry = DiskEntry;
4168  *pPartEntry = PartEntry;
4169  return TRUE;
4170  }
4171  }
4172 
4173  for (Entry2 = DiskEntry->LogicalPartListHead.Flink;
4174  Entry2 != &DiskEntry->LogicalPartListHead;
4175  Entry2 = Entry2->Flink)
4176  {
4177  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
4178  if (PartEntry->IsPartitioned && PartEntry->NeedsCheck)
4179  {
4180  ASSERT(DiskEntry == PartEntry->DiskEntry);
4181  if (pDiskEntry) *pDiskEntry = DiskEntry;
4182  *pPartEntry = PartEntry;
4183  return TRUE;
4184  }
4185  }
4186  }
4187 
4188  if (pDiskEntry) *pDiskEntry = NULL;
4189  *pPartEntry = NULL;
4190 
4191  return FALSE;
4192 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
#define TRUE
Definition: types.h:120
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
Definition: typedefs.h:117
BOOLEAN NeedsCheck
Definition: partlist.h:71
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by CheckFileSystemPage().

◆ GetNextUnformattedPartition()

BOOLEAN GetNextUnformattedPartition ( IN PPARTLIST  List,
OUT PDISKENTRY *pDiskEntry  OPTIONAL,
OUT PPARTENTRY pPartEntry 
)

Definition at line 4077 of file partlist.c.

4081 {
4082  PLIST_ENTRY Entry1, Entry2;
4083  PDISKENTRY DiskEntry;
4084  PPARTENTRY PartEntry;
4085 
4086  for (Entry1 = List->DiskListHead.Flink;
4087  Entry1 != &List->DiskListHead;
4088  Entry1 = Entry1->Flink)
4089  {
4090  DiskEntry = CONTAINING_RECORD(Entry1,
4091  DISKENTRY,
4092  ListEntry);
4093 
4094  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
4095  {
4096  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
4097  continue;
4098  }
4099 
4100  for (Entry2 = DiskEntry->PrimaryPartListHead.Flink;
4101  Entry2 != &DiskEntry->PrimaryPartListHead;
4102  Entry2 = Entry2->Flink)
4103  {
4104  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
4105  if (PartEntry->IsPartitioned && PartEntry->New)
4106  {
4107  ASSERT(DiskEntry == PartEntry->DiskEntry);
4108  if (pDiskEntry) *pDiskEntry = DiskEntry;
4109  *pPartEntry = PartEntry;
4110  return TRUE;
4111  }
4112  }
4113 
4114  for (Entry2 = DiskEntry->LogicalPartListHead.Flink;
4115  Entry2 != &DiskEntry->LogicalPartListHead;
4116  Entry2 = Entry2->Flink)
4117  {
4118  PartEntry = CONTAINING_RECORD(Entry2, PARTENTRY, ListEntry);
4119  if (PartEntry->IsPartitioned && PartEntry->New)
4120  {
4121  ASSERT(DiskEntry == PartEntry->DiskEntry);
4122  if (pDiskEntry) *pDiskEntry = DiskEntry;
4123  *pPartEntry = PartEntry;
4124  return TRUE;
4125  }
4126  }
4127  }
4128 
4129  if (pDiskEntry) *pDiskEntry = NULL;
4130  *pPartEntry = NULL;
4131 
4132  return FALSE;
4133 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
#define TRUE
Definition: types.h:120
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
LIST_ENTRY List
Definition: psmgr.c:57
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
Definition: typedefs.h:117
BOOLEAN New
Definition: partlist.h:65
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by SelectFileSystemPage().

◆ GetNextUnpartitionedEntry()

static PPARTENTRY GetNextUnpartitionedEntry ( IN PPARTENTRY  PartEntry)
static

Definition at line 2735 of file partlist.c.

2737 {
2738  PDISKENTRY DiskEntry = PartEntry->DiskEntry;
2739  PPARTENTRY NextPartEntry;
2740  PLIST_ENTRY ListHead;
2741 
2742  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2743  {
2744  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2745  return NULL;
2746  }
2747 
2748  if (PartEntry->LogicalPartition)
2749  ListHead = &DiskEntry->LogicalPartListHead;
2750  else
2751  ListHead = &DiskEntry->PrimaryPartListHead;
2752 
2753  if (PartEntry->ListEntry.Flink != ListHead)
2754  {
2755  NextPartEntry = CONTAINING_RECORD(PartEntry->ListEntry.Flink,
2756  PARTENTRY,
2757  ListEntry);
2758  if (!NextPartEntry->IsPartitioned)
2759  {
2760  ASSERT(NextPartEntry->PartitionType == PARTITION_ENTRY_UNUSED);
2761  return NextPartEntry;
2762  }
2763  }
2764 
2765  return NULL;
2766 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
UCHAR PartitionType
Definition: partlist.h:46
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
Definition: typedefs.h:117
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by DeletePartition().

◆ GetPartition()

PPARTENTRY GetPartition ( IN PDISKENTRY  DiskEntry,
IN ULONG  PartitionNumber 
)

Definition at line 2082 of file partlist.c.

2086 {
2087  PPARTENTRY PartEntry;
2089 
2090  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2091  {
2092  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2093  return NULL;
2094  }
2095 
2096  /* Disk found, loop over the primary partitions first... */
2097  for (Entry = DiskEntry->PrimaryPartListHead.Flink;
2098  Entry != &DiskEntry->PrimaryPartListHead;
2099  Entry = Entry->Flink)
2100  {
2101  PartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
2102 
2103  if (PartEntry->PartitionNumber == PartitionNumber)
2104  {
2105  /* Partition found */
2106  return PartEntry;
2107  }
2108  }
2109 
2110  /* ... then over the logical partitions if needed */
2111  for (Entry = DiskEntry->LogicalPartListHead.Flink;
2112  Entry != &DiskEntry->LogicalPartListHead;
2113  Entry = Entry->Flink)
2114  {
2115  PartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
2116 
2117  if (PartEntry->PartitionNumber == PartitionNumber)
2118  {
2119  /* Partition found */
2120  return PartEntry;
2121  }
2122  }
2123 
2124  /* The partition was not found on the disk, stop there */
2125  return NULL;
2126 }
ULONG PartitionNumber
Definition: partlist.h:49
struct _Entry Entry
Definition: kefuncs.h:640
_In_ ULONG _In_ ULONG PartitionNumber
Definition: iofuncs.h:2056
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
Definition: typedefs.h:117
base of all file and directory entries
Definition: entries.h:82

Referenced by GetDiskOrPartition(), ResolveArcNameManually(), and SelectPartition().

◆ GetPrevPartition()

PPARTENTRY GetPrevPartition ( IN PPARTLIST  List,
IN PPARTENTRY CurrentPart  OPTIONAL 
)

Definition at line 2285 of file partlist.c.

2288 {
2289  PLIST_ENTRY DiskListEntry;
2290  PLIST_ENTRY PartListEntry;
2292 
2293  /* Fail if no disks are available */
2294  if (IsListEmpty(&List->DiskListHead))
2295  return NULL;
2296 
2297  /* Check for the previous usable entry on the current partition's disk */
2298  if (CurrentPart != NULL)
2299  {
2300  CurrentDisk = CurrentPart->DiskEntry;
2301 
2302  if (CurrentPart->LogicalPartition)
2303  {
2304  /* Logical partition */
2305 
2306  PartListEntry = CurrentPart->ListEntry.Blink;
2307  if (PartListEntry != &CurrentDisk->LogicalPartListHead)
2308  {
2309  /* Previous logical partition */
2310  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2311  }
2312  else
2313  {
2314  /* Extended partition */
2315  CurrentPart = CurrentDisk->ExtendedPartition;
2316  }
2317  return CurrentPart;
2318  }
2319  else
2320  {
2321  /* Primary or extended partition */
2322 
2323  PartListEntry = CurrentPart->ListEntry.Blink;
2324  if (PartListEntry != &CurrentDisk->PrimaryPartListHead)
2325  {
2326  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2327 
2328  if (CurrentPart->IsPartitioned &&
2329  IsContainerPartition(CurrentPart->PartitionType))
2330  {
2331  PartListEntry = CurrentDisk->LogicalPartListHead.Blink;
2332  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2333  }
2334 
2335  return CurrentPart;
2336  }
2337  }
2338  }
2339 
2340  /* Search for the last partition entry on the previous disk */
2341  for (DiskListEntry = (CurrentPart ? CurrentDisk->ListEntry.Blink
2342  : List->DiskListHead.Blink);
2343  DiskListEntry != &List->DiskListHead;
2344  DiskListEntry = DiskListEntry->Blink)
2345  {
2346  CurrentDisk = CONTAINING_RECORD(DiskListEntry, DISKENTRY, ListEntry);
2347 
2349  {
2350  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2351  continue;
2352  }
2353 
2354  PartListEntry = CurrentDisk->PrimaryPartListHead.Blink;
2355  if (PartListEntry != &CurrentDisk->PrimaryPartListHead)
2356  {
2357  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2358 
2359  if (CurrentPart->IsPartitioned &&
2360  IsContainerPartition(CurrentPart->PartitionType))
2361  {
2362  PartListEntry = CurrentDisk->LogicalPartListHead.Blink;
2363  if (PartListEntry != &CurrentDisk->LogicalPartListHead)
2364  {
2365  CurrentPart = CONTAINING_RECORD(PartListEntry, PARTENTRY, ListEntry);
2366  return CurrentPart;
2367  }
2368  }
2369  else
2370  {
2371  return CurrentPart;
2372  }
2373  }
2374  }
2375 
2376  return NULL;
2377 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
PDISKENTRY CurrentDisk
Definition: partlist.c:73
struct _LIST_ENTRY * Blink
Definition: typedefs.h:120
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
_Must_inspect_result_ FORCEINLINE BOOLEAN IsListEmpty(_In_ const LIST_ENTRY *ListHead)
Definition: rtlfuncs.h:57
PPARTENTRY ExtendedPartition
Definition: partlist.h:129
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
LIST_ENTRY List
Definition: psmgr.c:57
LIST_ENTRY ListEntry
Definition: partlist.h:77
Definition: typedefs.h:117
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126

Referenced by ScrollUpPartitionList().

◆ GetPrevUnpartitionedEntry()

static PPARTENTRY GetPrevUnpartitionedEntry ( IN PPARTENTRY  PartEntry)
static

Definition at line 2700 of file partlist.c.

2702 {
2703  PDISKENTRY DiskEntry = PartEntry->DiskEntry;
2704  PPARTENTRY PrevPartEntry;
2705  PLIST_ENTRY ListHead;
2706 
2707  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2708  {
2709  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2710  return NULL;
2711  }
2712 
2713  if (PartEntry->LogicalPartition)
2714  ListHead = &DiskEntry->LogicalPartListHead;
2715  else
2716  ListHead = &DiskEntry->PrimaryPartListHead;
2717 
2718  if (PartEntry->ListEntry.Blink != ListHead)
2719  {
2720  PrevPartEntry = CONTAINING_RECORD(PartEntry->ListEntry.Blink,
2721  PARTENTRY,
2722  ListEntry);
2723  if (!PrevPartEntry->IsPartitioned)
2724  {
2725  ASSERT(PrevPartEntry->PartitionType == PARTITION_ENTRY_UNUSED);
2726  return PrevPartEntry;
2727  }
2728  }
2729 
2730  return NULL;
2731 }
LIST_ENTRY PrimaryPartListHead
Definition: partlist.h:125
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
smooth NULL
Definition: ftsmooth.c:416
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
UCHAR PartitionType
Definition: partlist.h:46
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
Definition: typedefs.h:117
LIST_ENTRY LogicalPartListHead
Definition: partlist.h:126
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by DeletePartition().

◆ GetPrimaryPartitionCount()

static ULONG GetPrimaryPartitionCount ( IN PDISKENTRY  DiskEntry)
static

Definition at line 2414 of file partlist.c.

2416 {
2418  PPARTENTRY PartEntry;
2419  ULONG Count = 0;
2420 
2421  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
2422  {
2423  DPRINT("GPT-partitioned disk detected, not currently supported by SETUP!\n");
2424  return 0;
2425  }
2426 
2427  for (Entry = DiskEntry->PrimaryPartListHead.Flink;
2428  Entry != &DiskEntry->PrimaryPartListHead;
2429  Entry = Entry->Flink)
2430  {
2431  PartEntry = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
2432  if (PartEntry->IsPartitioned)
2433  Count++;
2434  }
2435 
2436  return Count;
2437 }
struct _Entry Entry
Definition: kefuncs.h:640
_Inout_ __drv_aliasesMem PSLIST_ENTRY _Inout_ PSLIST_ENTRY _In_ ULONG Count
Definition: exfuncs.h:1015
void DPRINT(...)
Definition: polytest.cpp:61
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
Definition: typedefs.h:117
unsigned int ULONG
Definition: retypes.h:1
base of all file and directory entries
Definition: entries.h:82
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by CheckActiveSystemPartition(), ExtendedPartitionCreationChecks(), PrimaryPartitionCreationChecks(), and UpdateDiskLayout().

◆ InitializePartitionEntry()

static PPARTENTRY InitializePartitionEntry ( IN PDISKENTRY  DiskEntry,
IN PPARTENTRY  PartEntry,
IN ULONGLONG  SectorCount,
IN BOOLEAN  AutoCreate 
)
static

Definition at line 855 of file partlist.c.

860 {
861  PPARTENTRY NewPartEntry;
862 
863  DPRINT1("Current partition sector count: %I64u\n", PartEntry->SectorCount.QuadPart);
864 
865  if ((AutoCreate != FALSE) ||
866  (AlignDown(PartEntry->StartSector.QuadPart + SectorCount, DiskEntry->SectorAlignment) -
867  PartEntry->StartSector.QuadPart == PartEntry->SectorCount.QuadPart))
868  {
869  DPRINT1("Convert existing partition entry\n");
870 
871  NewPartEntry = PartEntry;
872  NewPartEntry->AutoCreate = AutoCreate;
873  }
874  else
875  {
876  DPRINT1("Add new partition entry\n");
877 
878  /* Insert and initialize a new partition entry */
879  NewPartEntry = RtlAllocateHeap(ProcessHeap,
881  sizeof(PARTENTRY));
882  if (NewPartEntry == NULL)
883  return NULL;
884 
885  NewPartEntry->DiskEntry = DiskEntry;
886 
887  NewPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart;
888  NewPartEntry->SectorCount.QuadPart = AlignDown(NewPartEntry->StartSector.QuadPart + SectorCount, DiskEntry->SectorAlignment) -
889  NewPartEntry->StartSector.QuadPart;
890 
891  PartEntry->StartSector.QuadPart = NewPartEntry->StartSector.QuadPart + NewPartEntry->SectorCount.QuadPart;
892  PartEntry->SectorCount.QuadPart -= (PartEntry->StartSector.QuadPart - NewPartEntry->StartSector.QuadPart);
893 
894  /* Insert the new entry into the list */
895  InsertTailList(&PartEntry->ListEntry, &NewPartEntry->ListEntry);
896  }
897 
898  /* Create entry as 'New (Unformatted)' */
899  NewPartEntry->New = TRUE;
900  NewPartEntry->IsPartitioned = TRUE;
901 
902  NewPartEntry->PartitionType = FileSystemToPartitionType(L"RAW", &NewPartEntry->StartSector, &NewPartEntry->SectorCount);
903  ASSERT(NewPartEntry->PartitionType != PARTITION_ENTRY_UNUSED);
904 
905  NewPartEntry->FormatState = Unformatted;
906  NewPartEntry->FileSystem[0] = L'\0';
907  // NewPartEntry->AutoCreate = AutoCreate;
908  NewPartEntry->BootIndicator = FALSE;
909  NewPartEntry->LogicalPartition = FALSE;
910 
911  DPRINT1("First Sector : %I64u\n", NewPartEntry->StartSector.QuadPart);
912  DPRINT1("Last Sector : %I64u\n", NewPartEntry->StartSector.QuadPart + NewPartEntry->SectorCount.QuadPart - 1);
913  DPRINT1("Total Sectors: %I64u\n", NewPartEntry->SectorCount.QuadPart);
914 
915  return NewPartEntry;
916 }
ULARGE_INTEGER StartSector
Definition: partlist.h:42
#define TRUE
Definition: types.h:120
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
#define InsertTailList(ListHead, Entry)
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
LIST_ENTRY ListEntry
Definition: partlist.h:36
BOOLEAN LogicalPartition
Definition: partlist.h:57
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
FORMATSTATE FormatState
Definition: partlist.h:55
smooth NULL
Definition: ftsmooth.c:416
BOOLEAN AutoCreate
Definition: partlist.h:68
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:585
UCHAR PartitionType
Definition: partlist.h:46
struct _DISKENTRY * DiskEntry
Definition: partlist.h:39
WCHAR FileSystem[MAX_PATH+1]
Definition: partlist.h:54
ULONGLONG AlignDown(IN ULONGLONG Value, IN ULONG Alignment)
Definition: partlist.c:245
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
ULONG SectorCount
Definition: part_xbox.c:32
HANDLE ProcessHeap
Definition: servman.c:15
BOOLEAN New
Definition: partlist.h:65
#define HEAP_ZERO_MEMORY
Definition: compat.h:123
#define DPRINT1
Definition: precomp.h:8
BOOLEAN BootIndicator
Definition: partlist.h:45
UCHAR FileSystemToPartitionType(IN PCWSTR FileSystem, IN PULARGE_INTEGER StartSector, IN PULARGE_INTEGER SectorCount)
Definition: fsutil.c:457
BOOLEAN IsPartitioned
Definition: partlist.h:60

Referenced by CreateExtendedPartition(), CreateLogicalPartition(), and CreatePrimaryPartition().

◆ InsertDiskRegion()

static VOID InsertDiskRegion ( IN PDISKENTRY  DiskEntry,
IN PPARTENTRY  PartEntry,
IN BOOLEAN  LogicalPartition 
)
static

Definition at line 752 of file partlist.c.

756 {
759  PPARTENTRY PartEntry2;
760 
761  /* Use the correct partition list */
762  if (LogicalPartition)
763  List = &DiskEntry->LogicalPartListHead;
764  else
765  List = &DiskEntry->PrimaryPartListHead;
766 
767  /* Find the first disk region before which we need to insert the new one */
768  for (Entry = List->Flink; Entry != List; Entry = Entry->Flink)
769  {
770  PartEntry2 = CONTAINING_RECORD(Entry, PARTENTRY, ListEntry);
771 
772  /* Ignore any unused empty region */
773  if ((PartEntry2->PartitionType == PARTITION_ENTRY_UNUSED &&
774  PartEntry2->StartSector.QuadPart == 0) || PartEntry2->SectorCount.QuadPart == 0)
775  {
776  continue;
777  }
778 
779  /* If the current region ends before the one to be inserted, try again */
780  if (PartEntry2->StartSector.QuadPart + PartEntry2->SectorCount.QuadPart - 1 < PartEntry->StartSector.QuadPart)
781  continue;
782 
783  /*
784  * One of the disk region boundaries crosses the desired region
785  * (it starts after the desired region, or ends before the end
786  * of the desired region): this is an impossible situation because
787  * disk regions (partitions) cannot overlap!
788  * Throw an error and bail out.
789  */
790  if (max(PartEntry->StartSector.QuadPart, PartEntry2->StartSector.QuadPart)
791  <=
792  min( PartEntry->StartSector.QuadPart + PartEntry->SectorCount.QuadPart - 1,
793  PartEntry2->StartSector.QuadPart + PartEntry2->SectorCount.QuadPart - 1))
794  {
795  DPRINT1("Disk region overlap problem, stopping there!\n"
796  "Partition to be inserted:\n"
797  " StartSector = %I64u ; EndSector = %I64u\n"
798  "Existing disk region:\n"
799  " StartSector = %I64u ; EndSector = %I64u\n",
800  PartEntry->StartSector.QuadPart,
801  PartEntry->StartSector.QuadPart + PartEntry->SectorCount.QuadPart - 1,
802  PartEntry2->StartSector.QuadPart,
803  PartEntry2->StartSector.QuadPart + PartEntry2->SectorCount.QuadPart - 1);
804  return;
805  }
806 
807  /* We have found the first region before which the new one has to be inserted */
808  break;
809  }
810 
811  /* Insert the disk region */
812  InsertTailList(Entry, &PartEntry->ListEntry);
813 }
#define max(a, b)
Definition: svc.c:63
ULARGE_INTEGER StartSector
Definition: partlist.h:42
struct _Entry Entry
Definition: kefuncs.h:640
ULARGE_INTEGER SectorCount
Definition: partlist.h:43
#define InsertTailList(ListHead, Entry)
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
struct _LIST_ENTRY * Flink
Definition: typedefs.h:119
UCHAR PartitionType
Definition: partlist.h:46
LIST_ENTRY List
Definition: psmgr.c:57
Definition: typedefs.h:117
#define min(a, b)
Definition: monoChain.cc:55
#define DPRINT1
Definition: precomp.h:8
base of all file and directory entries
Definition: entries.h:82

Referenced by AddPartitionToDisk().

◆ IsEmptyLayoutEntry()

FORCEINLINE BOOLEAN IsEmptyLayoutEntry ( IN PPARTITION_INFORMATION  PartitionInfo)

Definition at line 2382 of file partlist.c.

2384 {
2385  if (PartitionInfo->StartingOffset.QuadPart == 0 &&
2386  PartitionInfo->PartitionLength.QuadPart == 0)
2387  {
2388  return TRUE;
2389  }
2390 
2391  return FALSE;
2392 }
#define TRUE
Definition: types.h:120
_In_ ULONG _In_ struct _SET_PARTITION_INFORMATION_EX * PartitionInfo
Definition: iofuncs.h:2101

Referenced by UpdateDiskLayout().

◆ IsSamePrimaryLayoutEntry()

FORCEINLINE BOOLEAN IsSamePrimaryLayoutEntry ( IN PPARTITION_INFORMATION  PartitionInfo,
IN PDISKENTRY  DiskEntry,
IN PPARTENTRY  PartEntry 
)

Definition at line 2397 of file partlist.c.

2401 {
2402  if (PartitionInfo->StartingOffset.QuadPart == PartEntry->StartSector.QuadPart * DiskEntry->BytesPerSector &&
2403  PartitionInfo->PartitionLength.QuadPart == PartEntry->SectorCount.QuadPart * DiskEntry->BytesPerSector)
2404 // PartitionInfo->PartitionType == PartEntry->PartitionType
2405  {
2406  return TRUE;
2407  }
2408 
2409  return FALSE;
2410 }
#define TRUE
Definition: types.h:120
_In_ ULONG _In_ struct _SET_PARTITION_INFORMATION_EX * PartitionInfo
Definition: iofuncs.h:2101

Referenced by UpdateDiskLayout().

◆ IsSuperFloppy()

BOOLEAN IsSuperFloppy ( IN PDISKENTRY  DiskEntry)

Definition at line 679 of file partlist.c.

681 {
683  ULONGLONG PartitionLengthEstimate;
684 
685  /* No layout buffer: we cannot say anything yet */
686  if (DiskEntry->LayoutBuffer == NULL)
687  return FALSE;
688 
689  /* We must have only one partition */
690  if (DiskEntry->LayoutBuffer->PartitionCount != 1)
691  return FALSE;
692 
693  /* Get the single partition entry */
694  PartitionInfo = DiskEntry->LayoutBuffer->PartitionEntry;
695 
696  /* The single partition must start at the beginning of the disk */
697  if (!(PartitionInfo->StartingOffset.QuadPart == 0 &&
698  PartitionInfo->HiddenSectors == 0))
699  {
700  return FALSE;
701  }
702 
703  /* The disk signature is usually set to one; warn in case it's not */
704  if (DiskEntry->LayoutBuffer->Signature != 1)
705  {
706  DPRINT1("Super-Floppy disk %lu signature %08x != 1!\n",
707  DiskEntry->DiskNumber, DiskEntry->LayoutBuffer->Signature);
708  }
709 
710  /*
711  * The partition number must be zero or one, be recognized,
712  * have FAT16 type and report as non-bootable.
713  */
714  if ((PartitionInfo->PartitionNumber != 0 &&
715  PartitionInfo->PartitionNumber != 1) ||
716  PartitionInfo->RecognizedPartition != TRUE ||
717  PartitionInfo->PartitionType != PARTITION_FAT_16 ||
718  PartitionInfo->BootIndicator != FALSE)
719  {
720  DPRINT1("Super-Floppy disk %lu does not return default settings!\n"
721  " PartitionNumber = %lu, expected 0\n"
722  " RecognizedPartition = %s, expected TRUE\n"
723  " PartitionType = 0x%02x, expected 0x04 (PARTITION_FAT_16)\n"
724  " BootIndicator = %s, expected FALSE\n",
725  DiskEntry->DiskNumber,
726  PartitionInfo->PartitionNumber,
727  PartitionInfo->RecognizedPartition ? "TRUE" : "FALSE",
728  PartitionInfo->PartitionType,
729  PartitionInfo->BootIndicator ? "TRUE" : "FALSE");
730  }
731 
732  /* The partition lengths should agree */
733  PartitionLengthEstimate = DiskEntry->SectorCount.QuadPart * DiskEntry->BytesPerSector;
734  if (PartitionInfo->PartitionLength.QuadPart != PartitionLengthEstimate)
735  {
736  DPRINT1("PartitionLength = %I64u is different from PartitionLengthEstimate = %I64u\n",
737  PartitionInfo->PartitionLength.QuadPart, PartitionLengthEstimate);
738  }
739 
740  return TRUE;
741 }
#define TRUE
Definition: types.h:120
smooth NULL
Definition: ftsmooth.c:416
uint64_t ULONGLONG
Definition: typedefs.h:65
_In_ ULONG _In_ struct _SET_PARTITION_INFORMATION_EX * PartitionInfo
Definition: iofuncs.h:2101
#define PARTITION_FAT_16
Definition: disk.h:90
#define DPRINT1
Definition: precomp.h:8

Referenced by AddDiskToList(), BootLoaderHarddiskMbrPage(), ExtendedPartitionCreationChecks(), LogicalPartitionCreationChecks(), PrimaryPartitionCreationChecks(), and xHalIoWritePartitionTable().

◆ IsSupportedActivePartition()

static BOOLEAN IsSupportedActivePartition ( IN PPARTENTRY  PartEntry)
static

Definition at line 3247 of file partlist.c.

3249 {
3250  /* Check the type and the filesystem of this partition */
3251 
3252  /*
3253  * We do not support extended partition containers (on MBR disks) marked
3254  * as active, and containing code inside their extended boot records.
3255  */
3256  if (IsContainerPartition(PartEntry->PartitionType))
3257  {
3258  DPRINT1("System partition %lu in disk %lu is an extended partition container?!\n",
3259  PartEntry->PartitionNumber, PartEntry->DiskEntry->DiskNumber);
3260  return FALSE;
3261  }
3262 
3263  /*
3264  * ADDITIONAL CHECKS / BIG HACK:
3265  *
3266  * Retrieve its file system and check whether we have
3267  * write support for it. If that is the case we are fine
3268  * and we can use it directly. However if we don't have
3269  * write support we will need to change the active system
3270  * partition.
3271  *
3272  * NOTE that this is completely useless on architectures
3273  * where a real system partition is required, as on these
3274  * architectures the partition uses the FAT FS, for which
3275  * we do have write support.
3276  * NOTE also that for those architectures looking for a
3277  * partition boot indicator is insufficient.
3278  */
3279  if ((PartEntry->FormatState == Unformatted ) ||
3280  (PartEntry->FormatState == Preformatted) ||
3281  (PartEntry->FormatState == Formatted ))
3282  {
3283  ASSERT(*PartEntry->FileSystem);
3284 
3285  /* NOTE: Please keep in sync with the RegisteredFileSystems list! */
3286  if (wcsicmp(PartEntry->FileSystem, L"FAT") == 0 ||
3287  wcsicmp(PartEntry->FileSystem, L"FAT32") == 0 ||
3288  // wcsicmp(PartEntry->FileSystem, L"NTFS") == 0 ||
3289  wcsicmp(PartEntry->FileSystem, L"BTRFS") == 0 ||
3290  wcsicmp(PartEntry->FileSystem, L"RAW") == 0)
3291  {
3292  return TRUE;
3293  }
3294  else
3295  {
3296  // WARNING: We cannot write on this FS yet!
3297  DPRINT1("Recognized file system '%S' that doesn't have write support yet!\n",
3298  PartEntry->FileSystem);
3299  return FALSE;
3300  }
3301  }
3302  else // if (PartEntry->FormatState == UnknownFormat)
3303  {
3304  ASSERT(!*PartEntry->FileSystem);
3305 
3306  DPRINT1("System partition %lu in disk %lu with no or unknown FS?!\n",
3307  PartEntry->PartitionNumber, PartEntry->DiskEntry->DiskNumber);
3308  return FALSE;
3309  }
3310 
3311  // HACK: WARNING: We cannot write on this FS yet!
3312  // See fsutil.c:InferFileSystem()
3313  if (PartEntry->PartitionType == PARTITION_IFS)
3314  {
3315  DPRINT1("Recognized file system '%S' that doesn't have write support yet!\n",
3316  PartEntry->FileSystem);
3317  return FALSE;
3318  }
3319 
3320  return TRUE;
3321 }
#define TRUE
Definition: types.h:120
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:245
#define PARTITION_IFS
Definition: disk.h:93
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
#define wcsicmp
Definition: string.h:1152
#define DPRINT1
Definition: precomp.h:8

Referenced by CheckActiveSystemPartition().

◆ LogicalPartitionCreationChecks()

ERROR_NUMBER LogicalPartitionCreationChecks ( IN PPARTENTRY  PartEntry)

Definition at line 4054 of file partlist.c.

4056 {
4057  PDISKENTRY DiskEntry = PartEntry->DiskEntry;
4058 
4059  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
4060  {
4061  DPRINT1("GPT-partitioned disk detected, not currently supported by SETUP!\n");
4062  return ERROR_WARN_PARTITION;
4063  }
4064 
4065  /* Fail if the partition is already in use */
4066  if (PartEntry->IsPartitioned)
4067  return ERROR_NEW_PARTITION;
4068 
4069  /* Only one primary partition is allowed on super-floppy */
4070  if (IsSuperFloppy(DiskEntry))
4072 
4073  return ERROR_SUCCESS;
4074 }
#define ERROR_SUCCESS
Definition: deptool.c:10
PARTITION_STYLE DiskStyle
Definition: partlist.h:115
BOOLEAN IsSuperFloppy(IN PDISKENTRY DiskEntry)
Definition: partlist.c:679
#define DPRINT1
Definition: precomp.h:8

Referenced by CreateLogicalPartition(), and SelectPartitionPage().

◆ PrimaryPartitionCreationChecks()

ERROR_NUMBER PrimaryPartitionCreationChecks ( IN PPARTENTRY  PartEntry)

Definition at line 3996 of file partlist.c.

3998 {
3999  PDISKENTRY DiskEntry = PartEntry->DiskEntry;
4000 
4001  if (DiskEntry->DiskStyle == PARTITION_STYLE_GPT)
4002  {
4003  DPRINT1("GPT-partitioned disk detected, not currently supported by SETUP!\n");
4004  return ERROR_WARN_PARTITION;
4005  }
4006 
4007  /* Fail if the partition is already in use */
4008  if (PartEntry->IsPartitioned)
4009  return ERROR_NEW_PARTITION;
4010 
4011  /* Only one primary partition is allowed on super-floppy */
4012  if (IsSuperFloppy(DiskEntry))