aboutsummaryrefslogtreecommitdiff
path: root/hw/ide
diff options
context:
space:
mode:
Diffstat (limited to 'hw/ide')
-rw-r--r--hw/ide/core.c35
-rw-r--r--hw/ide/piix.c17
2 files changed, 41 insertions, 11 deletions
diff --git a/hw/ide/core.c b/hw/ide/core.c
index 7cbc0a54a7..39afdc0006 100644
--- a/hw/ide/core.c
+++ b/hw/ide/core.c
@@ -1340,6 +1340,11 @@ static void ide_reset(IDEState *s)
s->pio_aiocb = NULL;
}
+ if (s->reset_reverts) {
+ s->reset_reverts = false;
+ s->heads = s->drive_heads;
+ s->sectors = s->drive_sectors;
+ }
if (s->drive_kind == IDE_CFATA)
s->mult_sectors = 0;
else
@@ -1618,6 +1623,20 @@ static bool cmd_check_power_mode(IDEState *s, uint8_t cmd)
return true;
}
+/* INITIALIZE DEVICE PARAMETERS */
+static bool cmd_specify(IDEState *s, uint8_t cmd)
+{
+ if (s->blk && s->drive_kind != IDE_CD) {
+ s->heads = (s->select & (ATA_DEV_HS)) + 1;
+ s->sectors = s->nsector;
+ ide_set_irq(s->bus);
+ } else {
+ ide_abort_command(s);
+ }
+
+ return true;
+}
+
static bool cmd_set_features(IDEState *s, uint8_t cmd)
{
uint16_t *identify_data;
@@ -1641,7 +1660,11 @@ static bool cmd_set_features(IDEState *s, uint8_t cmd)
ide_flush_cache(s);
return false;
case 0xcc: /* reverting to power-on defaults enable */
+ s->reset_reverts = true;
+ return true;
case 0x66: /* reverting to power-on defaults disable */
+ s->reset_reverts = false;
+ return true;
case 0xaa: /* read look-ahead enable */
case 0x55: /* read look-ahead disable */
case 0x05: /* set advanced power management mode */
@@ -1704,8 +1727,14 @@ static bool cmd_identify_packet(IDEState *s, uint8_t cmd)
return false;
}
+/* EXECUTE DEVICE DIAGNOSTIC */
static bool cmd_exec_dev_diagnostic(IDEState *s, uint8_t cmd)
{
+ /*
+ * Clear the device register per the ATA (v6) specification,
+ * because ide_set_signature does not clear LBA or drive bits.
+ */
+ s->select = (ATA_DEV_ALWAYS_ON);
ide_set_signature(s);
if (s->drive_kind == IDE_CD) {
@@ -2045,7 +2074,7 @@ static const struct {
[WIN_SEEK] = { cmd_seek, HD_CFA_OK | SET_DSC },
[CFA_TRANSLATE_SECTOR] = { cmd_cfa_translate_sector, CFA_OK },
[WIN_DIAGNOSE] = { cmd_exec_dev_diagnostic, ALL_OK },
- [WIN_SPECIFY] = { cmd_nop, HD_CFA_OK | SET_DSC },
+ [WIN_SPECIFY] = { cmd_specify, HD_CFA_OK | SET_DSC },
[WIN_STANDBYNOW2] = { cmd_nop, HD_CFA_OK },
[WIN_IDLEIMMEDIATE2] = { cmd_nop, HD_CFA_OK },
[WIN_STANDBY2] = { cmd_nop, HD_CFA_OK },
@@ -2535,8 +2564,8 @@ int ide_init_drive(IDEState *s, BlockBackend *blk, IDEDriveKind kind,
blk_get_geometry(blk, &nb_sectors);
s->cylinders = cylinders;
- s->heads = heads;
- s->sectors = secs;
+ s->heads = s->drive_heads = heads;
+ s->sectors = s->drive_sectors = secs;
s->chs_trans = chs_trans;
s->nb_sectors = nb_sectors;
s->wwn = wwn;
diff --git a/hw/ide/piix.c b/hw/ide/piix.c
index 9a9b28078e..de1f4f0efb 100644
--- a/hw/ide/piix.c
+++ b/hw/ide/piix.c
@@ -21,6 +21,10 @@
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
+ *
+ * References:
+ * [1] 82371FB (PIIX) AND 82371SB (PIIX3) PCI ISA IDE XCELERATOR,
+ * 290550-002, Intel Corporation, April 1997.
*/
#include "qemu/osdep.h"
@@ -114,14 +118,11 @@ static void piix_ide_reset(DeviceState *dev)
ide_bus_reset(&d->bus[i]);
}
- /* TODO: this is the default. do not override. */
- pci_conf[PCI_COMMAND] = 0x00;
- /* TODO: this is the default. do not override. */
- pci_conf[PCI_COMMAND + 1] = 0x00;
- /* TODO: use pci_set_word */
- pci_conf[PCI_STATUS] = PCI_STATUS_FAST_BACK;
- pci_conf[PCI_STATUS + 1] = PCI_STATUS_DEVSEL_MEDIUM >> 8;
- pci_conf[0x20] = 0x01; /* BMIBA: 20-23h */
+ /* PCI command register default value (0000h) per [1, p.48]. */
+ pci_set_word(pci_conf + PCI_COMMAND, 0x0000);
+ pci_set_word(pci_conf + PCI_STATUS,
+ PCI_STATUS_DEVSEL_MEDIUM | PCI_STATUS_FAST_BACK);
+ pci_set_byte(pci_conf + 0x20, 0x01); /* BMIBA: 20-23h */
}
static int pci_piix_init_ports(PCIIDEState *d)