This commit is contained in:
Baptiste Wicht 2016-07-02 16:09:00 +02:00
parent 1a0586d7b6
commit 1f1b319bb4

View File

@ -118,11 +118,20 @@ void ata_wait_irq_secondary(){
} }
} }
inline void ata_400ns_delay(uint16_t /*controller*/){
timer::sleep_ms(1);
//TODO Ideally, we should have a real 400ns delay by simply reading the controller status 4 times
}
static uint8_t wait_for_controller(uint16_t controller, uint8_t mask, uint8_t value, uint16_t timeout){ static uint8_t wait_for_controller(uint16_t controller, uint8_t mask, uint8_t value, uint16_t timeout){
uint8_t status; uint8_t status;
do { do {
// Sleep at least 400ns before reading the status register
ata_400ns_delay(controller);
// Final read of the controller status
status = in_byte(controller + ATA_STATUS); status = in_byte(controller + ATA_STATUS);
timer::sleep_ms(1);
} while ((status & mask) != value && --timeout); } while ((status & mask) != value && --timeout);
return timeout; return timeout;
@ -140,9 +149,6 @@ bool select_device(ata::drive_descriptor& drive){
//Indicate the selected device //Indicate the selected device
out_byte(controller + ATA_DRV_HEAD, 0xA0 | (drive.slave << 4)); out_byte(controller + ATA_DRV_HEAD, 0xA0 | (drive.slave << 4));
//Sleep at least 400ns before reading the status register
timer::sleep_ms(1);
if(!wait_for_controller(controller, wait_mask, 0, 10000)){ if(!wait_for_controller(controller, wait_mask, 0, 10000)){
return false; return false;
} }
@ -175,9 +181,6 @@ bool read_write_sector(ata::drive_descriptor& drive, uint64_t start, void* data,
out_byte(controller + ATA_DRV_HEAD, (1 << 6) | (drive.slave << 4) | hd); out_byte(controller + ATA_DRV_HEAD, (1 << 6) | (drive.slave << 4) | hd);
out_byte(controller + ATA_COMMAND, command); out_byte(controller + ATA_COMMAND, command);
//Wait at least 400ns before reading status register
timer::sleep_ms(1);
//Wait at most 30 seconds for BSY flag to be cleared //Wait at most 30 seconds for BSY flag to be cleared
if(!wait_for_controller(controller, ATA_STATUS_BSY, 0, 30000)){ if(!wait_for_controller(controller, ATA_STATUS_BSY, 0, 30000)){
return false; return false;