94#ifdef CACHE_MULTI_DRIVES
104#ifdef CACHE_MULTI_DRIVES
132 case 0x00:
return "no error";
133 case 0x01:
return "bad command passed to driver";
134 case 0x02:
return "address mark not found or bad sector";
135 case 0x03:
return "diskette write protect error";
136 case 0x04:
return "sector not found";
137 case 0x05:
return "fixed disk reset failed";
138 case 0x06:
return "diskette changed or removed";
139 case 0x07:
return "bad fixed disk parameter table";
140 case 0x08:
return "DMA overrun";
141 case 0x09:
return "DMA access across 64k boundary";
142 case 0x0A:
return "bad fixed disk sector flag";
143 case 0x0B:
return "bad fixed disk cylinder";
144 case 0x0C:
return "unsupported track/invalid media";
145 case 0x0D:
return "invalid number of sectors on fixed disk format";
146 case 0x0E:
return "fixed disk controlled data address mark detected";
147 case 0x0F:
return "fixed disk DMA arbitration level out of range";
148 case 0x10:
return "ECC/CRC error on disk read";
149 case 0x11:
return "recoverable fixed disk data error, data fixed by ECC";
150 case 0x20:
return "controller error (NEC for floppies)";
151 case 0x40:
return "seek failure";
152 case 0x80:
return "time out, drive not ready";
153 case 0xAA:
return "fixed disk drive not ready";
154 case 0xBB:
return "fixed disk undefined error";
155 case 0xCC:
return "fixed disk write fault on selected drive";
156 case 0xE0:
return "fixed disk status error/Error reg = 0";
157 case 0xFF:
return "sense operation failed";
159 default:
return "unknown error code";
165 CHAR ErrorCodeString[200];
170 sprintf(ErrorCodeString,
"%s\n\nError Code: 0x%lx\nError: %s",
173 ERR(
"%s\n", ErrorCodeString);
182 REGS RegsIn, RegsOut;
184 WARN(
"DiskResetController(0x%x) DISK OPERATION FAILED -- RESETTING CONTROLLER\n", DriveNumber);
196 RegsIn.
b.
dl = DriveNumber;
199 Int386(0x13, &RegsIn, &RegsOut);
212 if ((DriveNumber >= 0x80) || (DriveNumber == 0x49))
222 REGS RegsIn, RegsOut;
232 if (DriveNumber >= 0x8A)
262 RegsIn.
w.
bx = 0x55AA;
263 RegsIn.
b.
dl = DriveNumber;
266 Int386(0x13, &RegsIn, &RegsOut);
273 if (RegsOut.
w.
bx != 0xAA55)
279 if (!(RegsOut.
w.
cx & 0x0001))
285 WARN(
"Suspicious API subset support bitmap 0x%x on device 0x%lx\n",
286 RegsOut.
w.
cx, DriveNumber);
300 REGS RegsIn, RegsOut;
303 TRACE(
"DiskGetExtendedDriveParameters(0x%x)\n", DriveNumber);
305 if (!DiskDrive->Int13ExtensionsSupported)
324 RegsIn.
b.
dl = DriveNumber;
329 Int386(0x13, &RegsIn, &RegsOut);
336 TRACE(
"size of buffer: %x\n",
Ptr[0]);
337 TRACE(
"information flags: %x\n",
Ptr[1]);
338 TRACE(
"number of physical cylinders on drive: %u\n", *(
PULONG)&
Ptr[2]);
339 TRACE(
"number of physical heads on drive: %u\n", *(
PULONG)&
Ptr[4]);
340 TRACE(
"number of physical sectors per track: %u\n", *(
PULONG)&
Ptr[6]);
342 TRACE(
"bytes per sector: %u\n",
Ptr[12]);
346 TRACE(
"EDD configuration parameters: %x:%x\n",
Ptr[14],
Ptr[13]);
347 if (
Ptr[13] != 0xffff &&
Ptr[14] != 0xffff)
350 TRACE(
"SpecPtr: %x\n", SpecPtr);
351 TRACE(
"physical I/O port base address: %x\n", *(
PUSHORT)&SpecPtr[0]);
352 TRACE(
"disk-drive control port address: %x\n", *(
PUSHORT)&SpecPtr[2]);
353 TRACE(
"drive flags: %x\n", SpecPtr[4]);
354 TRACE(
"proprietary information: %x\n", SpecPtr[5]);
355 TRACE(
"IRQ for drive: %u\n", SpecPtr[6]);
356 TRACE(
"sector count for multi-sector transfers: %u\n", SpecPtr[7]);
357 TRACE(
"DMA control: %x\n", SpecPtr[8]);
358 TRACE(
"programmed I/O control: %x\n", SpecPtr[9]);
377 REGS RegsIn, RegsOut;
381 DiskDrive->ExtGeometry.Size =
sizeof(DiskDrive->ExtGeometry);
383 &DiskDrive->ExtGeometry,
384 DiskDrive->ExtGeometry.Size);
388 RtlZeroMemory(&DiskDrive->ExtGeometry,
sizeof(DiskDrive->ExtGeometry));
392 TRACE(
"DiskGetExtendedDriveParameters(0x%x) returned:\n"
395 "Sects/Track: 0x%x\n"
396 "Bytes/Sect : 0x%x\n",
398 DiskDrive->ExtGeometry.Cylinders,
399 DiskDrive->ExtGeometry.Heads,
400 DiskDrive->ExtGeometry.SectorsPerTrack,
401 DiskDrive->ExtGeometry.BytesPerSector);
405 RtlZeroMemory(&DiskDrive->Geometry,
sizeof(DiskDrive->Geometry));
427 RegsIn.
b.
dl = DriveNumber;
428 RegsIn.
w.
es = 0x0000;
429 RegsIn.
w.
di = 0x0000;
432 Int386(0x13, &RegsIn, &RegsOut);
441 Cylinders = (RegsOut.
b.
cl & 0xC0) << 2;
442 Cylinders += RegsOut.
b.
ch;
444 DiskDrive->Geometry.Cylinders = Cylinders;
445 DiskDrive->Geometry.Heads = RegsOut.
b.
dh + 1;
446 DiskDrive->Geometry.SectorsPerTrack = RegsOut.
b.
cl & 0x3F;
447 DiskDrive->Geometry.BytesPerSector = 512;
449 DiskDrive->Geometry.Sectors = (
ULONGLONG)DiskDrive->Geometry.Cylinders *
450 DiskDrive->Geometry.Heads *
451 DiskDrive->Geometry.SectorsPerTrack;
453 TRACE(
"Regular Int13h(0x%x) returned:\n"
456 "Sects/Track: 0x%x (original 0x%x)\n"
457 "Bytes/Sect : 0x%x\n",
459 DiskDrive->Geometry.Cylinders,
460 DiskDrive->Geometry.Heads,
461 DiskDrive->Geometry.SectorsPerTrack, RegsOut.
b.
cl,
462 DiskDrive->Geometry.BytesPerSector);
485 "DriveNumber: 0x%x\n"
487 "Int13ExtensionsSupported = %s\n",
489 DiskDrive->IsRemovable ?
"TRUE" :
"FALSE",
490 DiskDrive->Int13ExtensionsSupported ?
"TRUE" :
"FALSE");
499#ifdef CACHE_MULTI_DRIVES
508 if (!DiskDrive->Initialized)
517 DiskDrive->Initialized |= 0x80;
520 DiskDrive->Initialized =
TRUE;
522 else if (DiskDrive->Initialized & 0x80)
528 DiskDrive->Initialized =
FALSE;
536 ASSERT((0 <= DriveNumber) && (DriveNumber <= 0xFF));
569 REGS RegsIn, RegsOut;
575 Packet->PacketSize =
sizeof(*Packet);
580 Packet->LBAStartBlock = SectorNumber;
593 RegsIn.
b.
dl = DriveNumber;
598 for (RetryCount = 0; RetryCount < 3; ++RetryCount)
606 Int386(0x13, &RegsIn, &RegsOut);
618 DiskError(
"Disk Read Failed in LBA mode", RegsOut.
b.
ah);
619 ERR(
"Disk Read Failed in LBA mode: %x (%s) (DriveNumber: 0x%x SectorNumber: %I64d SectorCount: %d)\n",
634 UCHAR PhysicalSector;
638 ULONG NumberOfSectorsToRead;
639 REGS RegsIn, RegsOut;
642 DriveGeometry = DiskDrive->Geometry;
657 if (PhysicalSector > 1)
668 if ((PhysicalHead >= DriveGeometry.
Heads) ||
669 (PhysicalTrack >= DriveGeometry.
Cylinders) ||
670 ((NumberOfSectorsToRead + PhysicalSector) > (DriveGeometry.
SectorsPerTrack + 1)) ||
673 DiskError(
"Disk read exceeds drive geometry limits.", 0);
696 RegsIn.
b.
al = (
UCHAR)NumberOfSectorsToRead;
697 RegsIn.
b.
ch = (PhysicalTrack & 0xFF);
698 RegsIn.
b.
cl = (
UCHAR)(PhysicalSector + ((PhysicalTrack & 0x300) >> 2));
699 RegsIn.
b.
dh = PhysicalHead;
700 RegsIn.
b.
dl = DriveNumber;
705 for (RetryCount = 0; RetryCount < 3; ++RetryCount)
707 Int386(0x13, &RegsIn, &RegsOut);
721 DiskError(
"Disk Read Failed in CHS mode, after retrying 3 times", RegsOut.
b.
ah);
722 ERR(
"Disk Read Failed in CHS mode, after retrying 3 times: %x (%s) (DriveNumber: 0x%x SectorNumber: %I64d SectorCount: %d)\n",
738 SectorNumber += NumberOfSectorsToRead;
753 TRACE(
"PcDiskReadLogicalSectors() DriveNumber: 0x%x SectorNumber: %I64d SectorCount: %d Buffer: 0x%x\n",
766 TRACE(
"--> Using LBA\n");
772 TRACE(
"--> Using CHS\n");
777#if defined(__i386__) || defined(_M_AMD64)
789 TRACE(
"PcDiskGetDriveGeometry(0x%x)\n", DriveNumber);
#define DBG_DEFAULT_CHANNEL(ch)
VOID UiMessageBox(_In_ PCSTR Format,...)
_Must_inspect_result_ _In_ PFSRTL_PER_STREAM_CONTEXT Ptr
#define sprintf(buf, format,...)
_In_ NDIS_HANDLE _In_ PNDIS_PACKET Packet
_In_ NDIS_ERROR_CODE ErrorCode
__GNU_EXTENSION typedef unsigned __int64 * PULONGLONG
VOID __cdecl DiskStopFloppyMotor(VOID)
#define WRITE_PORT_UCHAR(p, d)
#define INT386_SUCCESS(regs)
int __cdecl Int386(int ivec, REGS *in, REGS *out)
static BOOLEAN DiskInt13ExtensionsSupported(IN UCHAR DriveNumber)
BOOLEAN DiskResetController(UCHAR DriveNumber)
static PCSTR DiskGetErrorCodeString(ULONG ErrorCode)
static BOOLEAN PcDiskReadLogicalSectorsLBA(IN UCHAR DriveNumber, IN ULONGLONG SectorNumber, IN ULONG SectorCount, OUT PVOID Buffer)
static BOOLEAN DiskIsDriveRemovable(UCHAR DriveNumber)
struct _PC_DISK_DRIVE PC_DISK_DRIVE
LONG DiskReportError(BOOLEAN bShowError)
static USHORT LastDriveNumber
static BOOLEAN PcDiskReadLogicalSectorsCHS(IN UCHAR DriveNumber, IN PPC_DISK_DRIVE DiskDrive, IN ULONGLONG SectorNumber, IN ULONG SectorCount, OUT PVOID Buffer)
static PC_DISK_DRIVE PcDiskDrive
struct I386_DISK_ADDRESS_PACKET * PI386_DISK_ADDRESS_PACKET
BOOLEAN PcDiskReadLogicalSectors(IN UCHAR DriveNumber, IN ULONGLONG SectorNumber, IN ULONG SectorCount, OUT PVOID Buffer)
struct I386_CDROM_SPEC_PACKET * PI386_CDROM_SPEC_PACKET
struct _PC_DISK_DRIVE * PPC_DISK_DRIVE
static BOOLEAN InitDriveGeometry(IN UCHAR DriveNumber, IN PPC_DISK_DRIVE DiskDrive)
static BOOLEAN DiskGetExtendedDriveParameters(IN UCHAR DriveNumber, IN PPC_DISK_DRIVE DiskDrive, OUT PVOID Buffer, IN USHORT BufferSize)
static PPC_DISK_DRIVE PcDiskDriveNumberToDrive(IN UCHAR DriveNumber)
static BOOLEAN PcDiskDriveInit(IN UCHAR DriveNumber, IN OUT PPC_DISK_DRIVE DiskDrive)
ULONG PcDiskGetCacheableBlockCount(UCHAR DriveNumber)
static VOID DiskError(PCSTR ErrorString, ULONG ErrorCode)
BOOLEAN PcDiskGetDriveGeometry(UCHAR DriveNumber, PGEOMETRY Geometry)
USHORT TransferBufferSegment
USHORT TransferBufferOffset
ULONG BytesPerSector
Number of bytes per sector.
ULONG Cylinders
Number of cylinders on the disk.
ULONGLONG Sectors
Total number of disk sectors/LBA blocks.
ULONG SectorsPerTrack
Number of sectors per track.
ULONG Heads
Number of heads on the disk.
EXTENDED_GEOMETRY ExtGeometry
BOOLEAN Int13ExtensionsSupported
#define RtlCopyMemory(Destination, Source, Length)
#define RtlZeroMemory(Destination, Length)
_In_ WDFMEMORY _Out_opt_ size_t * BufferSize
#define BIOSCALLBUFSEGMENT
#define BIOSCALLBUFOFFSET