Changeset 38
- Timestamp:
- Nov 5, 2010, 7:13:11 PM (15 years ago)
- Location:
- trunk/src/os2ahci
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/os2ahci/ata.c
r36 r38 431 431 u16 *id_buf = add_workspace(iorb)->buf; 432 432 433 /* Fill-in geometry information; os2ahci has been designed for devices434 * adhering to the ATA spec v8 or later, thus the real geometry doesn't435 * really matter (it's actually marked "obsolete" in the ATA 8 specs).436 * In order to maintain compatibitily to the BIOS and partition tables,437 * we'll use the same algorithm as used by typical PC BIOS versions:433 /* Fill-in geometry information; the ATA-8 spec declares the geometry 434 * fields in the ATA ID buffer as obsolete but it's still the best 435 * guess in most cases. If the information stored in the geometry 436 * fields is apparently incorrect, we'll use the algorithm typically 437 * used by SCSI adapters and modern PC BIOS releases: 438 438 * 439 439 * - 512 bytes per sector … … 459 459 */ 460 460 memset(geometry, 0x00, geometry_len); 461 geometry->BytesPerSector = 512; 461 462 462 463 /* extract total number of sectors */ 463 464 if (id_buf[ATA_ID_CFS_ENABLE_2] & 0x40) { 464 465 /* 48-bit LBA supported */ 465 if ( id_buf[ATA_ID_LBA_CAPACITY_2 + 2]!= 0) {466 if (ATA_CAPACITY48_H(id_buf) != 0) { 466 467 /* more than 32 bits for number of sectors */ 467 468 dprintf("warning: limiting disk %d.%d.%d to 2TB\n", … … 470 471 geometry->TotalSectors = 0xffffffffUL; 471 472 } else { 472 geometry->TotalSectors = *((u32 *) (id_buf + ATA_ID_LBA_CAPACITY_2));473 geometry->TotalSectors = ATA_CAPACITY48_L(id_buf); 473 474 } 474 475 } else { 475 476 /* 28-bit LBA */ 476 geometry->TotalSectors = *((u32 *) (id_buf + ATA_ID_LBA_CAPACITY)) & 477 0x0fffffffUL; 478 } 479 480 geometry->BytesPerSector = 512; 481 geometry->NumHeads = 255; 482 geometry->SectorsPerTrack = 63; 483 geometry->TotalCylinders = geometry->TotalSectors / 484 ((u32) geometry->NumHeads * 485 (u32) geometry->SectorsPerTrack); 477 geometry->TotalSectors = ATA_CAPACITY(id_buf) & 0x0fffffffUL; 478 } 479 480 /* see whether the "current" (read: BIOS-supplied) geometry looks OK */ 481 if (CUR_HEADS(id_buf) > 0 && CUR_CYLS(id_buf) > 0 && 482 CUR_SECTORS(id_buf) > 0 && 483 CUR_CAPACITY(id_buf) == CUR_HEADS(id_buf) * 484 CUR_CYLS(id_buf) * 485 CUR_SECTORS(id_buf)) { 486 /* use BIOS-supplied values for geometry */ 487 geometry->NumHeads = CUR_HEADS(id_buf); 488 geometry->SectorsPerTrack = CUR_SECTORS(id_buf); 489 geometry->TotalCylinders = CUR_CYLS(id_buf); 490 491 } else if (ATA_HEADS(id_buf) > 0 && ATA_CYLS(id_buf) > 0 && 492 ATA_SECTORS(id_buf) > 0) { 493 /* use ATA-supplied values for geometry */ 494 geometry->NumHeads = ATA_HEADS(id_buf); 495 geometry->SectorsPerTrack = ATA_SECTORS(id_buf); 496 geometry->TotalCylinders = ATA_CYLS(id_buf); 497 498 } else { 499 /* construct values based on typical [SCSI] BIOS algorithms */ 500 geometry->NumHeads = 255; 501 geometry->SectorsPerTrack = 63; 502 geometry->TotalCylinders = geometry->TotalSectors / 503 ((u32) geometry->NumHeads * 504 (u32) geometry->SectorsPerTrack); 505 } 506 507 if (debug > 1) { 508 printf("geometry information:\n"); 509 printf(" heads: %d\n", (u16) geometry->NumHeads); 510 printf(" sectors: %d\n", (u16) geometry->SectorsPerTrack); 511 printf(" cylinders: %d\n", (u16) geometry->TotalCylinders); 512 printf(" capacity: %ldMB\n", (u32) (geometry->TotalSectors / 2048)); 513 } 486 514 487 515 /* tell interrupt handler that this IORB is complete */ -
trunk/src/os2ahci/ata.h
r13 r38 21 21 22 22 /* -------------------------- macros and constants ------------------------- */ 23 24 /****************************************************************************** 25 * Macros to access geometry values in the ATA ID buffer 26 */ 27 #define ATA_CYLS(id_buf) *((u32 *) (id_buf + ATA_ID_CYLS)) 28 #define ATA_HEADS(id_buf) *((u32 *) (id_buf + ATA_ID_HEADS)) 29 #define ATA_SECTORS(id_buf) *((u32 *) (id_buf + ATA_ID_SECTORS)) 30 #define ATA_CAPACITY(id_buf) *((u32 *) (id_buf + ATA_ID_LBA_CAPACITY)) 31 32 #define ATA_CAPACITY48_L(id_buf) *((u32 *) (id_buf + ATA_ID_LBA_CAPACITY_2)) 33 #define ATA_CAPACITY48_H(id_buf) *((u32 *) (id_buf + ATA_ID_LBA_CAPACITY_2 + 2)) 34 35 #define CUR_CYLS(id_buf) *((u32 *) (id_buf + ATA_ID_CUR_CYLS)) 36 #define CUR_HEADS(id_buf) *((u32 *) (id_buf + ATA_ID_CUR_HEADS)) 37 #define CUR_SECTORS(id_buf) *((u32 *) (id_buf + ATA_ID_CUR_SECTORS)) 38 #define CUR_CAPACITY(id_buf) *((u32 *) (id_buf + ATA_ID_CUR_CAPACITY)) 39 23 40 24 41 /****************************************************************************** … … 50 67 #define ATA_ID_CUR_HEADS 55 51 68 #define ATA_ID_CUR_SECTORS 56 69 #define ATA_ID_CUR_CAPACITY 57 52 70 #define ATA_ID_MULTSECT 59 53 71 #define ATA_ID_LBA_CAPACITY 60
Note:
See TracChangeset
for help on using the changeset viewer.