mirror of
https://github.com/FDOS/kernel.git
synced 2025-07-26 15:24:15 +02:00
initdisk: actually restrict disk size to 2TB, fix ExtLBAForce usage
This commit is contained in:
parent
569337a7ef
commit
c20a97e844
@ -630,13 +630,23 @@ void DosDefinePartition(struct DriveParamS *driveParam,
|
|||||||
nUnits++;
|
nUnits++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
STATIC UWORD BIOS_assisted_LBA_heads(ULONG sectors)
|
||||||
|
{
|
||||||
|
if (sectors > 63ul * 128ul * 1024ul) return 255;
|
||||||
|
else if (sectors > 63ul * 64ul * 1024ul) return 128;
|
||||||
|
else if (sectors > 63ul * 32ul * 1024ul) return 64;
|
||||||
|
else if (sectors > 63ul * 16ul * 1024ul) return 32;
|
||||||
|
else return 16;
|
||||||
|
}
|
||||||
|
|
||||||
/* Get the parameters of the hard disk */
|
/* Get the parameters of the hard disk */
|
||||||
STATIC int LBA_Get_Drive_Parameters(int drive, struct DriveParamS *driveParam, int firstPass)
|
STATIC int LBA_Get_Drive_Parameters(int drive, struct DriveParamS *driveParam, int firstPass)
|
||||||
{
|
{
|
||||||
iregs regs;
|
iregs regs;
|
||||||
struct _bios_LBA_disk_parameterS lba_bios_parameters;
|
struct _bios_LBA_disk_parameterS lba_bios_parameters;
|
||||||
|
|
||||||
ExtLBAForce = InitKernelConfig.ForceLBA;
|
if (firstPass && (InitKernelConfig.Verbose >= 1))
|
||||||
|
printf("Checking for LBA support in BIOS for drive %02x\n", drive);
|
||||||
|
|
||||||
memset(driveParam, 0, sizeof *driveParam);
|
memset(driveParam, 0, sizeof *driveParam);
|
||||||
drive |= 0x80;
|
drive |= 0x80;
|
||||||
@ -654,27 +664,18 @@ STATIC int LBA_Get_Drive_Parameters(int drive, struct DriveParamS *driveParam, i
|
|||||||
|
|
||||||
init_call_intr(0x13, ®s);
|
init_call_intr(0x13, ®s);
|
||||||
|
|
||||||
if (regs.b.x != 0xaa55 || (regs.flags & 0x01))
|
/* LBA not supported at all, or read, write, verify not supported */
|
||||||
|
if (regs.b.x != 0xaa55 || (regs.flags & 0x01) || (regs.c.x & 1) == 0)
|
||||||
{
|
{
|
||||||
goto StandardBios;
|
goto StandardBios;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* by ralph :
|
|
||||||
if DAP cannot be used, don't use
|
|
||||||
LBA
|
|
||||||
*/
|
|
||||||
if (((regs.c.x & 1) == 0) && !ExtLBAForce)
|
|
||||||
{
|
|
||||||
goto StandardBios;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* drive supports LBA addressing */
|
|
||||||
if (firstPass && (InitKernelConfig.Verbose >= 1)) printf("Checking for LBA support in BIOS\n");
|
|
||||||
|
|
||||||
/* version 1.0, 2.0 have different verify */
|
/* version 1.0, 2.0 have different verify */
|
||||||
if (regs.a.x < 0x2100)
|
if (regs.a.x < 0x2100)
|
||||||
LBA_WRITE_VERIFY = 0x4301;
|
LBA_WRITE_VERIFY = 0x4301; /* problematic if INT13 is hooked by
|
||||||
|
different controllers / drivers */
|
||||||
|
|
||||||
|
/* query disk size and DMA handling, geometry is queried later by INT13,08 */
|
||||||
memset(&lba_bios_parameters, 0, sizeof(lba_bios_parameters));
|
memset(&lba_bios_parameters, 0, sizeof(lba_bios_parameters));
|
||||||
lba_bios_parameters.size = sizeof(lba_bios_parameters);
|
lba_bios_parameters.size = sizeof(lba_bios_parameters);
|
||||||
|
|
||||||
@ -690,20 +691,15 @@ STATIC int LBA_Get_Drive_Parameters(int drive, struct DriveParamS *driveParam, i
|
|||||||
goto StandardBios;
|
goto StandardBios;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* verify maximum settings, we can't handle more */
|
|
||||||
|
|
||||||
if (lba_bios_parameters.heads > 0xffff ||
|
if (lba_bios_parameters.heads > 0xffff ||
|
||||||
lba_bios_parameters.sectors > 0xffff ||
|
lba_bios_parameters.sectors > 0xffff ||
|
||||||
lba_bios_parameters.totalSectHigh != 0)
|
(lba_bios_parameters.totalSect == 0 &&
|
||||||
|
lba_bios_parameters.totalSectHigh == 0))
|
||||||
{
|
{
|
||||||
if (firstPass)
|
if (firstPass)
|
||||||
{
|
{
|
||||||
printf("Drive is too large to handle, ");
|
printf("Suspicious LBA disk parameters, reverting to CHS access:\n");
|
||||||
if (ExtLBAForce)
|
printf(" drive %02x, heads=%lu, sectors=%lu, total=0x%lx-%08lx\n",
|
||||||
printf("limited to 2TB");
|
|
||||||
else
|
|
||||||
printf("using CHS, limited to 8GB");
|
|
||||||
printf("\nDrive %02x, heads=%lu, sectors=%lu, total=0x%lx-%08lx\n",
|
|
||||||
drive,
|
drive,
|
||||||
(ULONG) lba_bios_parameters.heads,
|
(ULONG) lba_bios_parameters.heads,
|
||||||
(ULONG) lba_bios_parameters.sectors,
|
(ULONG) lba_bios_parameters.sectors,
|
||||||
@ -711,12 +707,21 @@ STATIC int LBA_Get_Drive_Parameters(int drive, struct DriveParamS *driveParam, i
|
|||||||
(ULONG) lba_bios_parameters.totalSectHigh);
|
(ULONG) lba_bios_parameters.totalSectHigh);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!ExtLBAForce) goto StandardBios;
|
goto StandardBios;
|
||||||
}
|
}
|
||||||
|
|
||||||
driveParam->total_sectors = lba_bios_parameters.totalSect;
|
/* restrict disk size to 2TB, because we can not handle more */
|
||||||
|
if (lba_bios_parameters.totalSectHigh == 0)
|
||||||
|
{
|
||||||
|
driveParam->total_sectors = lba_bios_parameters.totalSect;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (firstPass) printf("Drive %02x is too large to handle, restricted to 2TB\n", drive);
|
||||||
|
driveParam->total_sectors = 0xffffffffu;
|
||||||
|
}
|
||||||
|
|
||||||
/* if we arrive here, success */
|
/* if we arrive here, mark drive as LBA capable */
|
||||||
driveParam->descflags = DF_LBA;
|
driveParam->descflags = DF_LBA;
|
||||||
if (lba_bios_parameters.information & 8)
|
if (lba_bios_parameters.information & 8)
|
||||||
driveParam->descflags |= DF_WRTVERIFY;
|
driveParam->descflags |= DF_WRTVERIFY;
|
||||||
@ -736,9 +741,6 @@ StandardBios: /* old way to get parameters */
|
|||||||
|
|
||||||
if (regs.flags & 0x01)
|
if (regs.flags & 0x01)
|
||||||
{
|
{
|
||||||
/* to avoid division by zero later, use some sane defaults */
|
|
||||||
driveParam->chs.Head = 16;
|
|
||||||
driveParam->chs.Sector = 63;
|
|
||||||
goto ErrorReturn;
|
goto ErrorReturn;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -751,7 +753,18 @@ StandardBios: /* old way to get parameters */
|
|||||||
if (driveParam->chs.Sector == 0) {
|
if (driveParam->chs.Sector == 0) {
|
||||||
/* happens e.g. with Bochs 1.x if no harddisk defined */
|
/* happens e.g. with Bochs 1.x if no harddisk defined */
|
||||||
driveParam->chs.Sector = 63; /* avoid division by zero...! */
|
driveParam->chs.Sector = 63; /* avoid division by zero...! */
|
||||||
if (firstPass && (InitKernelConfig.Verbose >= 0)) printf("BIOS reported 0 sectors/track, assuming 63!\n");
|
if (firstPass && (InitKernelConfig.Verbose >= 0))
|
||||||
|
printf("BIOS reported 0 sectors/track, assuming 63!\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
/* if heads==0, determine from disk size like LBA assisted BIOS translation
|
||||||
|
does, or default to 16 if LBA is not used */
|
||||||
|
if (driveParam->chs.Head == 0) {
|
||||||
|
driveParam->chs.Head = (driveParam->descflags & DF_LBA)
|
||||||
|
? BIOS_assisted_LBA_heads(driveParam->total_sectors)
|
||||||
|
: 16;
|
||||||
|
if (firstPass && (InitKernelConfig.Verbose >= 0))
|
||||||
|
printf("BIOS reported 0 heads, assuming %u!\n", driveParam->chs.Head);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!(driveParam->descflags & DF_LBA))
|
if (!(driveParam->descflags & DF_LBA))
|
||||||
@ -769,9 +782,15 @@ StandardBios: /* old way to get parameters */
|
|||||||
driveParam->chs.Head, driveParam->chs.Sector));
|
driveParam->chs.Head, driveParam->chs.Sector));
|
||||||
DebugPrintf((" total size %luMB\n\n", driveParam->total_sectors / 2048));
|
DebugPrintf((" total size %luMB\n\n", driveParam->total_sectors / 2048));
|
||||||
|
|
||||||
ErrorReturn:
|
|
||||||
|
|
||||||
return driveParam->driveno;
|
return driveParam->driveno;
|
||||||
|
|
||||||
|
|
||||||
|
ErrorReturn:
|
||||||
|
/* to avoid division by zero later, use some sane defaults */
|
||||||
|
driveParam->total_sectors = 0;
|
||||||
|
driveParam->chs.Head = 16;
|
||||||
|
driveParam->chs.Sector = 63;
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -997,7 +1016,11 @@ int Read1LBASector(struct DriveParamS *driveParam, unsigned drive,
|
|||||||
|
|
||||||
for (num_retries = 0; num_retries < N_RETRY; num_retries++)
|
for (num_retries = 0; num_retries < N_RETRY; num_retries++)
|
||||||
{
|
{
|
||||||
if (InitKernelConfig.Verbose >= 1) printf("retry# %i\n", num_retries);
|
if (InitKernelConfig.Verbose >= 1)
|
||||||
|
{
|
||||||
|
printf("retry# %i sector %lu\n", num_retries, LBA_address);
|
||||||
|
}
|
||||||
|
|
||||||
regs.d.b.l = drive | 0x80;
|
regs.d.b.l = drive | 0x80;
|
||||||
LBA_to_CHS(&chs, LBA_address, driveParam);
|
LBA_to_CHS(&chs, LBA_address, driveParam);
|
||||||
/* Some old "security" software (PROT) traps int13 and assumes non
|
/* Some old "security" software (PROT) traps int13 and assumes non
|
||||||
@ -1074,6 +1097,9 @@ int ProcessDisk(int scanType, unsigned drive, int PartitionsToIgnore)
|
|||||||
|
|
||||||
RelSectorOffset = 0; /* boot sector */
|
RelSectorOffset = 0; /* boot sector */
|
||||||
ExtendedPartitionOffset = 0; /* not found yet */
|
ExtendedPartitionOffset = 0; /* not found yet */
|
||||||
|
ExtLBAForce = 0; /* initially we are not dealing with partitions
|
||||||
|
within a type 0x0E LBA extended partition,
|
||||||
|
so we do not enforce LBA access by now */
|
||||||
|
|
||||||
/* Read the Primary Partition Table. */
|
/* Read the Primary Partition Table. */
|
||||||
|
|
||||||
@ -1130,7 +1156,7 @@ strange_restart:
|
|||||||
{
|
{
|
||||||
RelSectorOffset = ExtendedPartitionOffset + PTable[iPart].RelSect;
|
RelSectorOffset = ExtendedPartitionOffset + PTable[iPart].RelSect;
|
||||||
|
|
||||||
if (ExtendedPartitionOffset == 0)
|
if (ExtendedPartitionOffset == 0) /* first extended in chain? */
|
||||||
{
|
{
|
||||||
ExtendedPartitionOffset = PTable[iPart].RelSect;
|
ExtendedPartitionOffset = PTable[iPart].RelSect;
|
||||||
/* grand parent LBA -> all children and grandchildren LBA */
|
/* grand parent LBA -> all children and grandchildren LBA */
|
||||||
@ -1407,14 +1433,14 @@ void ReadAllPartitionTables(void)
|
|||||||
|
|
||||||
if (InitKernelConfig.Verbose >= 0)
|
if (InitKernelConfig.Verbose >= 0)
|
||||||
{
|
{
|
||||||
unsigned foundPartitionsCount = 0;
|
unsigned foundPartitionsCount = 0;
|
||||||
/* Tell user if no valid partitions found on any hard drive */
|
/* Tell user if no valid partitions found on any hard drive */
|
||||||
for (HardDrive = 0; HardDrive < nHardDisk; HardDrive++)
|
for (HardDrive = 0; HardDrive < nHardDisk; HardDrive++)
|
||||||
{
|
{
|
||||||
foundPartitionsCount += foundPartitions[HardDrive];
|
foundPartitionsCount += foundPartitions[HardDrive];
|
||||||
}
|
}
|
||||||
/* printf("Found %i partitions\n", foundPartitionsCount); */
|
/* printf("Found %i partitions\n", foundPartitionsCount); */
|
||||||
if (!foundPartitionsCount) printf("No supported partitions found.\n");
|
if (!foundPartitionsCount) printf("No supported partitions found.\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user