I've been working on a basic ATA driver, but I'm running into a strange problem when I try to issue the command IDENTIFY (ECh) to a drive:
Code: Select all
cli
mov dx, 0x3f6 ;clear both control registers
xor al, al
out dx, al
mov dx, 0x376
out dx, al
mov dx, 0x177 ;now we need to check if there even are any drives
in al, dx
cmp al, 0xff ;if status is all ones, there is no drive at all
je ata_err
;now we need to check that we at least /have/ a responsive drive
mov dx, 0x172
mov al, 0x72
out dx, al
inc dx
mov al, 0x73
out dx, al
inc dx
mov al, 0xfa ;just a random value
out dx, al
mov dx, 0x172
in al, dx
cmp al, 0x72
jne stop_it ;this means we have no responsive drives
mov dx, 0x176 ;drive select register
mov al, 0xa0 ;master drive
out dx, al
mov dx, 0x177 ;now send IDENTIFY (0xec) to command reg
mov al, 0xec
out dx, al
in al, dx ;immediately read status after command
call fnc_print_hex ;print human-readable contents of al
cmp al, 0x00 ;if status is zero after IDENTIFY command, drive doesn't exist
je ata_err
If I'm not mistaken, this means the busy and error bits are both set after issuing the command. Is this a problem with QEMU (v 0.9.0 under Windows (I know)), or am I doing something wrong with my code?
I'm booting off of an CD-ROM ISO, and I'm zero-ing both bus's control registers before attempting anything. I also check that the secondary returns old CHS values written to its registers.
My Sources
ATA PIO Mode
http://lateblt.tripod.com/atapi.htm
http://forum.osdev.org/viewtopic.php?t=15087