X-Git-Url: https://git.reactos.org/?p=reactos.git;a=blobdiff_plain;f=ntoskrnl%2Ffstub%2Fdisksup.c;h=c4a67c3413fb637f12ff950c277bdd4bb7978e05;hp=29c3dc9ea911ff15b5a80c45b922167d12ecd80a;hb=b726d7355f0aa394852fa8c56e59cfc9bbc4293c;hpb=63b50165b246c58f1663017ba6c01ab57ccc1e01 diff --git a/ntoskrnl/fstub/disksup.c b/ntoskrnl/fstub/disksup.c index 29c3dc9ea91..c4a67c3413f 100644 --- a/ntoskrnl/fstub/disksup.c +++ b/ntoskrnl/fstub/disksup.c @@ -24,6 +24,8 @@ const WCHAR DiskMountString[] = L"\\DosDevices\\%C:"; #define PARTITION_MAGIC 0xaa55 +#define EFI_PMBR_OSTYPE_EFI 0xEE + #include typedef struct _REG_DISK_MOUNT_INFO @@ -62,17 +64,20 @@ HalpAssignDrive(IN PUNICODE_STRING PartitionName, if ((DriveNumber != AUTO_DRIVE) && (DriveNumber < 26)) { /* Force assignment */ + KeAcquireGuardedMutex(&ObpDeviceMapLock); if ((ObSystemDeviceMap->DriveMap & (1 << DriveNumber)) != 0) { DbgPrint("Drive letter already used!\n"); + KeReleaseGuardedMutex(&ObpDeviceMapLock); return FALSE; } + KeReleaseGuardedMutex(&ObpDeviceMapLock); } else { /* Automatic assignment */ DriveNumber = AUTO_DRIVE; - + KeAcquireGuardedMutex(&ObpDeviceMapLock); for (i = 2; i < 26; i++) { if ((ObSystemDeviceMap->DriveMap & (1 << i)) == 0) @@ -81,6 +86,7 @@ HalpAssignDrive(IN PUNICODE_STRING PartitionName, break; } } + KeReleaseGuardedMutex(&ObpDeviceMapLock); if (DriveNumber == AUTO_DRIVE) { @@ -91,10 +97,6 @@ HalpAssignDrive(IN PUNICODE_STRING PartitionName, DPRINT("DriveNumber %d\n", DriveNumber); - /* Update the System Device Map */ - ObSystemDeviceMap->DriveMap |= (1 << DriveNumber); - ObSystemDeviceMap->DriveType[DriveNumber] = DriveType; - /* Build drive name */ swprintf(DriveNameBuffer, L"\\??\\%C:", @@ -1358,6 +1360,24 @@ xHalExamineMBR(IN PDEVICE_OBJECT DeviceObject, } } +VOID +NTAPI +FstubFixupEfiPartition(IN PPARTITION_DESCRIPTOR PartitionDescriptor, + IN ULONGLONG MaxOffset) +{ + ULONG PartitionLength; + PAGED_CODE(); + + /* Compute partition length (according to MBR entry) */ + PartitionLength = PartitionDescriptor->StartingSectorLsb0 + PartitionDescriptor->PartitionLengthLsb0; + /* In case the partition length goes beyond disk size... */ + if (PartitionLength > MaxOffset) + { + /* Resize partition to its maximum real length */ + PartitionDescriptor->PartitionLengthLsb0 = MaxOffset - PartitionDescriptor->StartingSectorLsb0; + } +} + NTSTATUS FASTCALL xHalIoReadPartitionTable(IN PDEVICE_OBJECT DeviceObject, @@ -1425,7 +1445,7 @@ xHalIoReadPartitionTable(IN PDEVICE_OBJECT DeviceObject, MaxOffset, MaxSector); /* Allocate our buffer */ - Buffer = ExAllocatePoolWithTag(NonPagedPool, PAGE_SIZE, TAG_FILE_SYSTEM); + Buffer = ExAllocatePoolWithTag(NonPagedPool, InputSize, TAG_FILE_SYSTEM); if (!Buffer) { /* Fail, free the input buffer */ @@ -1503,9 +1523,6 @@ xHalIoReadPartitionTable(IN PDEVICE_OBJECT DeviceObject, PartitionDescriptor = (PPARTITION_DESCRIPTOR) &(((PUSHORT)Buffer)[PARTITION_TABLE_OFFSET]); - /* Get the partition type */ - PartitionType = PartitionDescriptor->PartitionType; - /* Start looping partitions */ j++; DPRINT("FSTUB: Partition Table %d:\n", j); @@ -1524,6 +1541,14 @@ xHalIoReadPartitionTable(IN PDEVICE_OBJECT DeviceObject, GET_STARTING_SECTOR(PartitionDescriptor), GET_PARTITION_LENGTH(PartitionDescriptor)); + /* Check whether we're facing a protective MBR */ + if (PartitionType == EFI_PMBR_OSTYPE_EFI) + { + /* Partition length might be bigger than disk size */ + FstubFixupEfiPartition(PartitionDescriptor, + MaxOffset); + } + /* Make sure that the partition is valid, unless it's the first */ if (!(HalpIsValidPartitionEntry(PartitionDescriptor, MaxOffset, @@ -1686,7 +1711,7 @@ xHalIoReadPartitionTable(IN PDEVICE_OBJECT DeviceObject, for (Entry = 1; Entry <= 4; Entry++, PartitionDescriptor++) { /* Check if this is a container partition, since we skipped them */ - if (IsContainerPartition(PartitionType)) + if (IsContainerPartition(PartitionDescriptor->PartitionType)) { /* Get its offset */ Offset.QuadPart = VolumeOffset.QuadPart +