Hello everyone, A little background if I may.
I have been doing OS development for some time and even started with QEMU way back when. Shortly after I started, though, I found Bochs and found it to be more to my liking. I went on to submit many improvements to Bochs including the initial USB code. Recently, I have had a few questions about QEMU and decided to take a look at it again. I run WinXP and so went to https://qemu.weilnetz.de/ and installed the latest package there. BTW, I am the reason for the recent patch request from Stefan for the truncation of the para file :-) I then started to run a few images and found that I could not get QEMU to emulate the IDE READ_DMA command (0xC8). Therefore, I went testing my code, after all, it probably is my code, though it works fine in Bochs and Oracle VirtualBox. After some testing, I still couldn't get it to work, so I went investigating and found http://comments.gmane.org/gmane.comp.emulators.qemu/15307 though currently the page is down, it suggests a patch to make FreeBSD work with the Bus Master. This suggested to me that maybe, as far as QEMU was concerned, I am not setting up the BusMaster in the correct sequence...No improvement. After many different sequences, including exactly following page 99 of the Piix3 specs, I still don't have the command working. Debug messages... Here is a list of message to show what I am doing and exactly what the values are: (Please ignore the initial xx-xxxxxxxxx number, and I will try to help with word-wrap) 00-543274621: ATA: Detect ATA drive: cntlr base = 0x01F0 drive = 0 00-543274621: ATA: Drive reset: 0x01F0 (0) 00-543274619: ATA: Setting SRST bit 00-543274619: ATA: Clearing SRST bit 00-543274617: ATA: Error Register returned: 0x01 00-543274617: ATA: Detect controller bytes: (0) 0x00 0x00 00-543274617: ATA: Type_id returned 0x0000 atapi = 0 atapi_type = 0 00-543274616: ATA: Sending Identify Command 00-543274616: ATA: ata_tx_rx_data: cmn = EC, lba = 0, len = 512 bytes, buf address = 0x0039C2B0 00-543274610: ATA: 32-bit PIO is allowed...(0x0001) 00-543274610: ATA: atapi = 0, removable = 0 00-543274609: ATA: Highest ATA version = 7 00-543274609: ATA: Is 48-bit capable = 1 00-543274609: ATA: Returned capacity: 201600 sectors 00-543274306: ATA: Words per sector: 256 At this point I have detected an ATA compatible device. So, skipping a lot of other things, I want to just read a sector from the disk, say sector 35... (Note, it is not an ATAPI device. If it was, 0xC8 wouldn't work anyway) 00-543272416: ATA: ata_read_sectors: lba = 35, count = 1, buf address = 0x03F10000 00-543272415: ATA: ata_tx_rx_data: cmn = C8, lba = 35, len = 512 bytes, buf address = 0x03F10000 00-543272415: ATA: ata_create_dma_table: table at 0x03C10000, first entry: 0x03F10000, total transfer size = 512 00-543272414: ATA: BusMaster Base Address: 0xC041 (Obviously I am masking off the lower bits and using PIO) 00-543272413: ATA: Command Reg: 0x0107 (IO, Mem, and BusMaster is enabled, though I don't know why QEMU has bit 8 set...) 00-543272413: ATA: Status Reg: 0x0280 (Status register says fast back-to-back and medium device select timing) 00-543272413: ATA: Channel = 0 (we are using the first channel (0x1F0), and we set up the PRD Table) 00-543272413: ATA: Channel 0: 00-543272413: ATA: BusMaster Command: 0x00 00-543272412: ATA: Status: 0x00 00-543272412: ATA: Address: 0x03C10000 00-543272411: ATA: PRD Entry 0: [03C10000]: 0x03F10000 0x80000200 (The address of the PRDT is 0x3C10000, doesn't cross a 64k boundary) (The address of the first transfer doesn't either, nor does the table use more than 4k) (I'm transfering 0x200 bytes, and have the EOT set) (Note that I have not set the direction bit yet...) 00-543272410: ATA: ATA Data: 0xFF 00-543272410: ATA: Error: 0x01 (ATA_FEATURE should be 0x00) 00-543272410: ATA: Count: 0x01 00-543272410: ATA: Low: 0x23 (35 dec) 00-543272409: ATA: Mid: 0x00 00-543272409: ATA: High: 0x00 00-543272409: ATA: Dev/Head: 0x60 (Side Note: even though bits 7 and 5 are obsolete, I set them in code before this, yet QEMU cleared bit 7. Any reason for this?) 00-543272409: ATA: altStatus: 0x50 (Status says Drive is Ready) Here is were I send the 0xC8 command by writing to the COMMAND Register. 00-543271956: ATA: ata_wait returned FALSE (D8) (00) Then, in the above debug line, I wait for the busy bit to clear so that I can check the Data Request (DRQ) bit. However, the busy bit never clears, even though the DRQ bit is set. The (alt)status register shows 0xD8 (ALT_Error = 0x00): BSY = 1 DRDY = 1 Command Spec (bit 4) DRQ = 1 Even after waiting quite some time, the BSY bit never clears. I decided to ignore the BSY bit and just wait for the DRQ bit to become set (even though any other bit in the status register is invalid while the BSY bit is set). It still never sent any data. *If* the BSY bit becomes clear and the DRQ bit becomes set, this is when I would set the direction bit and the start bit in the BusMaster's Command register. One thing I tried was setting the direction bit as I was initializing the BusMaster above. This had no effect. I am using the Windows port at https://qemu.weilnetz.de/ (Thanks Stefan for your work) and have not tried any Linux port. At this point, I really have to say that it is something wrong with QEMU, since I cannot see anything wrong with my code, *and* it works with Bochs, VirtualBox, and on real hardware. However, I have been wrong before, once or twice... I know that WinXP uses this command (0xC8) and ran a version of that in QEMU. It worked, though I am not sure if 0xC8 actually worked or if WinXP switched to PIO reading after 0xC8 failed. If anyone has any comments, I would greatly appreciate them. Thanks, Ben