VirtualBox

source: vbox/trunk/src/VBox/Devices/Storage/DevATA.cpp@ 25985

Last change on this file since 25985 was 25985, checked in by vboxsync, 15 years ago

pdmifs.h: the final batch of refactored interface ID code.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 267.5 KB
Line 
1/* $Id: DevATA.cpp 25985 2010-01-23 00:51:04Z vboxsync $ */
2/** @file
3 * VBox storage devices: ATA/ATAPI controller device (disk and cdrom).
4 */
5
6/*
7 * Copyright (C) 2006-2008 Sun Microsystems, Inc.
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.215389.xyz. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 *
17 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
18 * Clara, CA 95054 USA or visit http://www.sun.com if you need
19 * additional information or have any questions.
20 */
21
22/*******************************************************************************
23* Defined Constants And Macros *
24*******************************************************************************/
25/** Temporary instrumentation for tracking down potential virtual disk
26 * write performance issues. */
27#undef VBOX_INSTRUMENT_DMA_WRITES
28
29/** @name The SSM saved state versions.
30 * @{
31 */
32/** The current saved state version. */
33#define ATA_SAVED_STATE_VERSION 20
34/** The saved state version used by VirtualBox 3.0.
35 * This lacks the config part and has the type at the and. */
36#define ATA_SAVED_STATE_VERSION_VBOX_30 19
37#define ATA_SAVED_STATE_VERSION_WITH_BOOL_TYPE 18
38#define ATA_SAVED_STATE_VERSION_WITHOUT_FULL_SENSE 16
39#define ATA_SAVED_STATE_VERSION_WITHOUT_EVENT_STATUS 17
40/** @} */
41
42/*******************************************************************************
43* Header Files *
44*******************************************************************************/
45#define LOG_GROUP LOG_GROUP_DEV_IDE
46#include <VBox/pdmdev.h>
47#include <iprt/assert.h>
48#include <iprt/string.h>
49#ifdef IN_RING3
50# include <iprt/uuid.h>
51# include <iprt/semaphore.h>
52# include <iprt/thread.h>
53# include <iprt/time.h>
54# include <iprt/alloc.h>
55#endif /* IN_RING3 */
56#include <iprt/critsect.h>
57#include <iprt/asm.h>
58#include <VBox/stam.h>
59#include <VBox/mm.h>
60#include <VBox/pgm.h>
61
62#include <VBox/scsi.h>
63
64#include "PIIX3ATABmDma.h"
65#include "ide.h"
66#include "../Builtins.h"
67
68/*******************************************************************************
69* Defined Constants And Macros *
70*******************************************************************************/
71/**
72 * Maximum number of sectors to transfer in a READ/WRITE MULTIPLE request.
73 * Set to 1 to disable multi-sector read support. According to the ATA
74 * specification this must be a power of 2 and it must fit in an 8 bit
75 * value. Thus the only valid values are 1, 2, 4, 8, 16, 32, 64 and 128.
76 */
77#define ATA_MAX_MULT_SECTORS 128
78
79/**
80 * Fastest PIO mode supported by the drive.
81 */
82#define ATA_PIO_MODE_MAX 4
83/**
84 * Fastest MDMA mode supported by the drive.
85 */
86#define ATA_MDMA_MODE_MAX 2
87/**
88 * Fastest UDMA mode supported by the drive.
89 */
90#define ATA_UDMA_MODE_MAX 6
91
92/** ATAPI sense info size. */
93#define ATAPI_SENSE_SIZE 64
94
95/** The maximum number of release log entries per device. */
96#define MAX_LOG_REL_ERRORS 1024
97
98/* MediaEventStatus */
99#define ATA_EVENT_STATUS_UNCHANGED 0 /**< medium event status not changed */
100#define ATA_EVENT_STATUS_MEDIA_NEW 1 /**< new medium inserted */
101#define ATA_EVENT_STATUS_MEDIA_REMOVED 2 /**< medium removed */
102#define ATA_EVENT_STATUS_MEDIA_CHANGED 3 /**< medium was removed + new medium was inserted */
103
104/**
105 * Length of the configurable VPD data (without termination)
106 */
107#define ATA_SERIAL_NUMBER_LENGTH 20
108#define ATA_FIRMWARE_REVISION_LENGTH 8
109#define ATA_MODEL_NUMBER_LENGTH 40
110#define ATAPI_INQUIRY_VENDOR_ID_LENGTH 8
111#define ATAPI_INQUIRY_PRODUCT_ID_LENGTH 16
112#define ATAPI_INQUIRY_REVISION_LENGTH 4
113
114/*******************************************************************************
115* Structures and Typedefs *
116*******************************************************************************/
117/**
118 * The state of an ATA device.
119 *
120 * @implements PDMIBASE
121 * @implements PDMIBLOCKPORT
122 * @implements PDMIMOUNTNOTIFY
123 */
124typedef struct ATADevState
125{
126 /** Flag indicating whether the current command uses LBA48 mode. */
127 bool fLBA48;
128 /** Flag indicating whether this drive implements the ATAPI command set. */
129 bool fATAPI;
130 /** Set if this interface has asserted the IRQ. */
131 bool fIrqPending;
132 /** Currently configured number of sectors in a multi-sector transfer. */
133 uint8_t cMultSectors;
134 /** PCHS disk geometry. */
135 PDMMEDIAGEOMETRY PCHSGeometry;
136 /** Total number of sectors on this disk. */
137 uint64_t cTotalSectors;
138 /** Number of sectors to transfer per IRQ. */
139 uint32_t cSectorsPerIRQ;
140
141 /** ATA/ATAPI register 1: feature (write-only). */
142 uint8_t uATARegFeature;
143 /** ATA/ATAPI register 1: feature, high order byte. */
144 uint8_t uATARegFeatureHOB;
145 /** ATA/ATAPI register 1: error (read-only). */
146 uint8_t uATARegError;
147 /** ATA/ATAPI register 2: sector count (read/write). */
148 uint8_t uATARegNSector;
149 /** ATA/ATAPI register 2: sector count, high order byte. */
150 uint8_t uATARegNSectorHOB;
151 /** ATA/ATAPI register 3: sector (read/write). */
152 uint8_t uATARegSector;
153 /** ATA/ATAPI register 3: sector, high order byte. */
154 uint8_t uATARegSectorHOB;
155 /** ATA/ATAPI register 4: cylinder low (read/write). */
156 uint8_t uATARegLCyl;
157 /** ATA/ATAPI register 4: cylinder low, high order byte. */
158 uint8_t uATARegLCylHOB;
159 /** ATA/ATAPI register 5: cylinder high (read/write). */
160 uint8_t uATARegHCyl;
161 /** ATA/ATAPI register 5: cylinder high, high order byte. */
162 uint8_t uATARegHCylHOB;
163 /** ATA/ATAPI register 6: select drive/head (read/write). */
164 uint8_t uATARegSelect;
165 /** ATA/ATAPI register 7: status (read-only). */
166 uint8_t uATARegStatus;
167 /** ATA/ATAPI register 7: command (write-only). */
168 uint8_t uATARegCommand;
169 /** ATA/ATAPI drive control register (write-only). */
170 uint8_t uATARegDevCtl;
171
172 /** Currently active transfer mode (MDMA/UDMA) and speed. */
173 uint8_t uATATransferMode;
174 /** Current transfer direction. */
175 uint8_t uTxDir;
176 /** Index of callback for begin transfer. */
177 uint8_t iBeginTransfer;
178 /** Index of callback for source/sink of data. */
179 uint8_t iSourceSink;
180 /** Flag indicating whether the current command transfers data in DMA mode. */
181 bool fDMA;
182 /** Set to indicate that ATAPI transfer semantics must be used. */
183 bool fATAPITransfer;
184
185 /** Total ATA/ATAPI transfer size, shared PIO/DMA. */
186 uint32_t cbTotalTransfer;
187 /** Elementary ATA/ATAPI transfer size, shared PIO/DMA. */
188 uint32_t cbElementaryTransfer;
189 /** Current read/write buffer position, shared PIO/DMA. */
190 uint32_t iIOBufferCur;
191 /** First element beyond end of valid buffer content, shared PIO/DMA. */
192 uint32_t iIOBufferEnd;
193
194 /** ATA/ATAPI current PIO read/write transfer position. Not shared with DMA for safety reasons. */
195 uint32_t iIOBufferPIODataStart;
196 /** ATA/ATAPI current PIO read/write transfer end. Not shared with DMA for safety reasons. */
197 uint32_t iIOBufferPIODataEnd;
198
199 /** ATAPI current LBA position. */
200 uint32_t iATAPILBA;
201 /** ATAPI current sector size. */
202 uint32_t cbATAPISector;
203 /** ATAPI current command. */
204 uint8_t aATAPICmd[ATAPI_PACKET_SIZE];
205 /** ATAPI sense data. */
206 uint8_t abATAPISense[ATAPI_SENSE_SIZE];
207 /** HACK: Countdown till we report a newly unmounted drive as mounted. */
208 uint8_t cNotifiedMediaChange;
209 /** The same for GET_EVENT_STATUS for mechanism */
210 volatile uint32_t MediaEventStatus;
211
212 uint32_t Alignment0;
213
214 /** The status LED state for this drive. */
215 PDMLED Led;
216
217 /** Size of I/O buffer. */
218 uint32_t cbIOBuffer;
219 /** Pointer to the I/O buffer. */
220 R3PTRTYPE(uint8_t *) pbIOBufferR3;
221 /** Pointer to the I/O buffer. */
222 R0PTRTYPE(uint8_t *) pbIOBufferR0;
223 /** Pointer to the I/O buffer. */
224 RCPTRTYPE(uint8_t *) pbIOBufferRC;
225
226 RTRCPTR Aligmnent1; /**< Align the statistics at an 8-byte boundrary. */
227
228 /*
229 * No data that is part of the saved state after this point!!!!!
230 */
231
232 /* Release statistics: number of ATA DMA commands. */
233 STAMCOUNTER StatATADMA;
234 /* Release statistics: number of ATA PIO commands. */
235 STAMCOUNTER StatATAPIO;
236 /* Release statistics: number of ATAPI PIO commands. */
237 STAMCOUNTER StatATAPIDMA;
238 /* Release statistics: number of ATAPI PIO commands. */
239 STAMCOUNTER StatATAPIPIO;
240#ifdef VBOX_INSTRUMENT_DMA_WRITES
241 /* Release statistics: number of DMA sector writes and the time spent. */
242 STAMPROFILEADV StatInstrVDWrites;
243#endif
244
245 /** Statistics: number of read operations and the time spent reading. */
246 STAMPROFILEADV StatReads;
247 /** Statistics: number of bytes read. */
248 STAMCOUNTER StatBytesRead;
249 /** Statistics: number of write operations and the time spent writing. */
250 STAMPROFILEADV StatWrites;
251 /** Statistics: number of bytes written. */
252 STAMCOUNTER StatBytesWritten;
253 /** Statistics: number of flush operations and the time spend flushing. */
254 STAMPROFILE StatFlushes;
255
256 /** Enable passing through commands directly to the ATAPI drive. */
257 bool fATAPIPassthrough;
258 /** Number of errors we've reported to the release log.
259 * This is to prevent flooding caused by something going horribly wrong.
260 * this value against MAX_LOG_REL_ERRORS in places likely to cause floods
261 * like the ones we currently seeing on the linux smoke tests (2006-11-10). */
262 uint32_t cErrors;
263 /** Timestamp of last started command. 0 if no command pending. */
264 uint64_t u64CmdTS;
265
266 /** Pointer to the attached driver's base interface. */
267 R3PTRTYPE(PPDMIBASE) pDrvBase;
268 /** Pointer to the attached driver's block interface. */
269 R3PTRTYPE(PPDMIBLOCK) pDrvBlock;
270 /** Pointer to the attached driver's block bios interface. */
271 R3PTRTYPE(PPDMIBLOCKBIOS) pDrvBlockBios;
272 /** Pointer to the attached driver's mount interface.
273 * This is NULL if the driver isn't a removable unit. */
274 R3PTRTYPE(PPDMIMOUNT) pDrvMount;
275 /** The base interface. */
276 PDMIBASE IBase;
277 /** The block port interface. */
278 PDMIBLOCKPORT IPort;
279 /** The mount notify interface. */
280 PDMIMOUNTNOTIFY IMountNotify;
281 /** The LUN #. */
282 RTUINT iLUN;
283 RTUINT Alignment2; /**< Align pDevInsR3 correctly. */
284 /** Pointer to device instance. */
285 PPDMDEVINSR3 pDevInsR3;
286 /** Pointer to controller instance. */
287 R3PTRTYPE(struct ATACONTROLLER *) pControllerR3;
288 /** Pointer to device instance. */
289 PPDMDEVINSR0 pDevInsR0;
290 /** Pointer to controller instance. */
291 R0PTRTYPE(struct ATACONTROLLER *) pControllerR0;
292 /** Pointer to device instance. */
293 PPDMDEVINSRC pDevInsRC;
294 /** Pointer to controller instance. */
295 RCPTRTYPE(struct ATACONTROLLER *) pControllerRC;
296
297 /** The serial numnber to use for IDENTIFY DEVICE commands. */
298 char szSerialNumber[ATA_SERIAL_NUMBER_LENGTH+1];
299 /** The firmware revision to use for IDENTIFY DEVICE commands. */
300 char szFirmwareRevision[ATA_FIRMWARE_REVISION_LENGTH+1];
301 /** The model number to use for IDENTIFY DEVICE commands. */
302 char szModelNumber[ATA_MODEL_NUMBER_LENGTH+1];
303 /** The vendor identification string for SCSI INQUIRY commands. */
304 char szInquiryVendorId[ATAPI_INQUIRY_VENDOR_ID_LENGTH+1];
305 /** The product identification string for SCSI INQUIRY commands. */
306 char szInquiryProductId[ATAPI_INQUIRY_PRODUCT_ID_LENGTH+1];
307 /** The revision string for SCSI INQUIRY commands. */
308 char szInquiryRevision[ATAPI_INQUIRY_REVISION_LENGTH+1];
309
310 uint8_t abAlignment3[7];
311} ATADevState;
312AssertCompileMemberAlignment(ATADevState, cTotalSectors, 8);
313AssertCompileMemberAlignment(ATADevState, StatATADMA, 8);
314AssertCompileMemberAlignment(ATADevState, u64CmdTS, 8);
315AssertCompileMemberAlignment(ATADevState, pDevInsR3, 8);
316AssertCompileMemberAlignment(ATADevState, szSerialNumber, 8);
317AssertCompileSizeAlignment(ATADevState, 8);
318
319
320typedef struct ATATransferRequest
321{
322 uint8_t iIf;
323 uint8_t iBeginTransfer;
324 uint8_t iSourceSink;
325 uint32_t cbTotalTransfer;
326 uint8_t uTxDir;
327} ATATransferRequest;
328
329
330typedef struct ATAAbortRequest
331{
332 uint8_t iIf;
333 bool fResetDrive;
334} ATAAbortRequest;
335
336
337typedef enum
338{
339 /** Begin a new transfer. */
340 ATA_AIO_NEW = 0,
341 /** Continue a DMA transfer. */
342 ATA_AIO_DMA,
343 /** Continue a PIO transfer. */
344 ATA_AIO_PIO,
345 /** Reset the drives on current controller, stop all transfer activity. */
346 ATA_AIO_RESET_ASSERTED,
347 /** Reset the drives on current controller, resume operation. */
348 ATA_AIO_RESET_CLEARED,
349 /** Abort the current transfer of a particular drive. */
350 ATA_AIO_ABORT
351} ATAAIO;
352
353
354typedef struct ATARequest
355{
356 ATAAIO ReqType;
357 union
358 {
359 ATATransferRequest t;
360 ATAAbortRequest a;
361 } u;
362} ATARequest;
363
364
365typedef struct ATACONTROLLER
366{
367 /** The base of the first I/O Port range. */
368 RTIOPORT IOPortBase1;
369 /** The base of the second I/O Port range. (0 if none) */
370 RTIOPORT IOPortBase2;
371 /** The assigned IRQ. */
372 RTUINT irq;
373 /** Access critical section */
374 PDMCRITSECT lock;
375
376 /** Selected drive. */
377 uint8_t iSelectedIf;
378 /** The interface on which to handle async I/O. */
379 uint8_t iAIOIf;
380 /** The state of the async I/O thread. */
381 uint8_t uAsyncIOState;
382 /** Flag indicating whether the next transfer is part of the current command. */
383 bool fChainedTransfer;
384 /** Set when the reset processing is currently active on this controller. */
385 bool fReset;
386 /** Flag whether the current transfer needs to be redone. */
387 bool fRedo;
388 /** Flag whether the redo suspend has been finished. */
389 bool fRedoIdle;
390 /** Flag whether the DMA operation to be redone is the final transfer. */
391 bool fRedoDMALastDesc;
392 /** The BusMaster DMA state. */
393 BMDMAState BmDma;
394 /** Pointer to first DMA descriptor. */
395 RTGCPHYS32 pFirstDMADesc;
396 /** Pointer to last DMA descriptor. */
397 RTGCPHYS32 pLastDMADesc;
398 /** Pointer to current DMA buffer (for redo operations). */
399 RTGCPHYS32 pRedoDMABuffer;
400 /** Size of current DMA buffer (for redo operations). */
401 uint32_t cbRedoDMABuffer;
402
403 /** The ATA/ATAPI interfaces of this controller. */
404 ATADevState aIfs[2];
405
406 /** Pointer to device instance. */
407 PPDMDEVINSR3 pDevInsR3;
408 /** Pointer to device instance. */
409 PPDMDEVINSR0 pDevInsR0;
410 /** Pointer to device instance. */
411 PPDMDEVINSRC pDevInsRC;
412
413 /** Set when the destroying the device instance and the thread must exit. */
414 uint32_t volatile fShutdown;
415 /** The async I/O thread handle. NIL_RTTHREAD if no thread. */
416 RTTHREAD AsyncIOThread;
417 /** The event semaphore the thread is waiting on for requests. */
418 RTSEMEVENT AsyncIOSem;
419 /** The request queue for the AIO thread. One element is always unused. */
420 ATARequest aAsyncIORequests[4];
421 /** The position at which to insert a new request for the AIO thread. */
422 uint8_t AsyncIOReqHead;
423 /** The position at which to get a new request for the AIO thread. */
424 uint8_t AsyncIOReqTail;
425 /** Whether to call PDMDevHlpAsyncNotificationCompleted when idle. */
426 bool volatile fSignalIdle;
427 uint8_t Alignment3[1]; /**< Explicit padding of the 1 byte gap. */
428 /** Magic delay before triggering interrupts in DMA mode. */
429 uint32_t DelayIRQMillies;
430 /** The mutex protecting the request queue. */
431 RTSEMMUTEX AsyncIORequestMutex;
432 /** The event semaphore the thread is waiting on during suspended I/O. */
433 RTSEMEVENT SuspendIOSem;
434#if 0 /*HC_ARCH_BITS == 32*/
435 uint32_t Alignment0;
436#endif
437
438 /** Timestamp we started the reset. */
439 uint64_t u64ResetTime;
440
441 /* Statistics */
442 STAMCOUNTER StatAsyncOps;
443 uint64_t StatAsyncMinWait;
444 uint64_t StatAsyncMaxWait;
445 STAMCOUNTER StatAsyncTimeUS;
446 STAMPROFILEADV StatAsyncTime;
447 STAMPROFILE StatLockWait;
448} ATACONTROLLER, *PATACONTROLLER;
449AssertCompileMemberAlignment(ATACONTROLLER, lock, 8);
450AssertCompileMemberAlignment(ATACONTROLLER, aIfs, 8);
451AssertCompileMemberAlignment(ATACONTROLLER, u64ResetTime, 8);
452AssertCompileMemberAlignment(ATACONTROLLER, StatAsyncOps, 8);
453
454typedef enum CHIPSET
455{
456 /** PIIX3 chipset, must be 0 for saved state compatibility */
457 CHIPSET_PIIX3 = 0,
458 /** PIIX4 chipset, must be 1 for saved state compatibility */
459 CHIPSET_PIIX4 = 1,
460 /** ICH6 chipset */
461 CHIPSET_ICH6 = 2
462} CHIPSET;
463
464/**
465 * The state of the ATA PCI device.
466 *
467 * @extends PCIDEVICE
468 * @implements PDMILEDPORTS
469 */
470typedef struct PCIATAState
471{
472 PCIDEVICE dev;
473 /** The controllers. */
474 ATACONTROLLER aCts[2];
475 /** Pointer to device instance. */
476 PPDMDEVINSR3 pDevIns;
477 /** Status LUN: Base interface. */
478 PDMIBASE IBase;
479 /** Status LUN: Leds interface. */
480 PDMILEDPORTS ILeds;
481 /** Status LUN: Partner of ILeds. */
482 R3PTRTYPE(PPDMILEDCONNECTORS) pLedsConnector;
483 /** Flag whether GC is enabled. */
484 bool fGCEnabled;
485 /** Flag whether R0 is enabled. */
486 bool fR0Enabled;
487 /** Flag indicating chipset being emulated. */
488 uint8_t u8Type;
489 bool Alignment0[HC_ARCH_BITS == 64 ? 5 : 1 ]; /**< Align the struct size. */
490} PCIATAState;
491
492#define PDMIBASE_2_PCIATASTATE(pInterface) ( (PCIATAState *)((uintptr_t)(pInterface) - RT_OFFSETOF(PCIATAState, IBase)) )
493#define PDMILEDPORTS_2_PCIATASTATE(pInterface) ( (PCIATAState *)((uintptr_t)(pInterface) - RT_OFFSETOF(PCIATAState, ILeds)) )
494#define PDMIBLOCKPORT_2_ATASTATE(pInterface) ( (ATADevState *)((uintptr_t)(pInterface) - RT_OFFSETOF(ATADevState, IPort)) )
495#define PDMIMOUNT_2_ATASTATE(pInterface) ( (ATADevState *)((uintptr_t)(pInterface) - RT_OFFSETOF(ATADevState, IMount)) )
496#define PDMIMOUNTNOTIFY_2_ATASTATE(pInterface) ( (ATADevState *)((uintptr_t)(pInterface) - RT_OFFSETOF(ATADevState, IMountNotify)) )
497#define PCIDEV_2_PCIATASTATE(pPciDev) ( (PCIATAState *)(pPciDev) )
498
499#define ATACONTROLLER_IDX(pController) ( (pController) - PDMINS_2_DATA(CONTROLLER_2_DEVINS(pController), PCIATAState *)->aCts )
500
501#define ATADEVSTATE_2_CONTROLLER(pIf) ( (pIf)->CTX_SUFF(pController) )
502#define ATADEVSTATE_2_DEVINS(pIf) ( (pIf)->CTX_SUFF(pDevIns) )
503#define CONTROLLER_2_DEVINS(pController) ( (pController)->CTX_SUFF(pDevIns) )
504#define PDMIBASE_2_ATASTATE(pInterface) ( (ATADevState *)((uintptr_t)(pInterface) - RT_OFFSETOF(ATADevState, IBase)) )
505
506#ifndef VBOX_DEVICE_STRUCT_TESTCASE
507/*******************************************************************************
508 * Internal Functions *
509 ******************************************************************************/
510RT_C_DECLS_BEGIN
511PDMBOTHCBDECL(int) ataIOPortWrite1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb);
512PDMBOTHCBDECL(int) ataIOPortRead1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *u32, unsigned cb);
513PDMBOTHCBDECL(int) ataIOPortWriteStr1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, RTGCPTR *pGCPtrSrc, PRTGCUINTREG pcTransfer, unsigned cb);
514PDMBOTHCBDECL(int) ataIOPortReadStr1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, RTGCPTR *pGCPtrDst, PRTGCUINTREG pcTransfer, unsigned cb);
515PDMBOTHCBDECL(int) ataIOPortWrite2(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb);
516PDMBOTHCBDECL(int) ataIOPortRead2(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *u32, unsigned cb);
517PDMBOTHCBDECL(int) ataBMDMAIOPortWrite(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb);
518PDMBOTHCBDECL(int) ataBMDMAIOPortRead(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *pu32, unsigned cb);
519RT_C_DECLS_END
520
521
522
523DECLINLINE(void) ataSetStatusValue(ATADevState *s, uint8_t stat)
524{
525 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
526
527 /* Freeze status register contents while processing RESET. */
528 if (!pCtl->fReset)
529 {
530 s->uATARegStatus = stat;
531 Log2(("%s: LUN#%d status %#04x\n", __FUNCTION__, s->iLUN, s->uATARegStatus));
532 }
533}
534
535
536DECLINLINE(void) ataSetStatus(ATADevState *s, uint8_t stat)
537{
538 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
539
540 /* Freeze status register contents while processing RESET. */
541 if (!pCtl->fReset)
542 {
543 s->uATARegStatus |= stat;
544 Log2(("%s: LUN#%d status %#04x\n", __FUNCTION__, s->iLUN, s->uATARegStatus));
545 }
546}
547
548
549DECLINLINE(void) ataUnsetStatus(ATADevState *s, uint8_t stat)
550{
551 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
552
553 /* Freeze status register contents while processing RESET. */
554 if (!pCtl->fReset)
555 {
556 s->uATARegStatus &= ~stat;
557 Log2(("%s: LUN#%d status %#04x\n", __FUNCTION__, s->iLUN, s->uATARegStatus));
558 }
559}
560
561#ifdef IN_RING3
562
563typedef void (*PBeginTransferFunc)(ATADevState *);
564typedef bool (*PSourceSinkFunc)(ATADevState *);
565
566static void ataReadWriteSectorsBT(ATADevState *);
567static void ataPacketBT(ATADevState *);
568static void atapiCmdBT(ATADevState *);
569static void atapiPassthroughCmdBT(ATADevState *);
570
571static bool ataIdentifySS(ATADevState *);
572static bool ataFlushSS(ATADevState *);
573static bool ataReadSectorsSS(ATADevState *);
574static bool ataWriteSectorsSS(ATADevState *);
575static bool ataExecuteDeviceDiagnosticSS(ATADevState *);
576static bool ataPacketSS(ATADevState *);
577static bool atapiGetConfigurationSS(ATADevState *);
578static bool atapiGetEventStatusNotificationSS(ATADevState *);
579static bool atapiIdentifySS(ATADevState *);
580static bool atapiInquirySS(ATADevState *);
581static bool atapiMechanismStatusSS(ATADevState *);
582static bool atapiModeSenseErrorRecoverySS(ATADevState *);
583static bool atapiModeSenseCDStatusSS(ATADevState *);
584static bool atapiReadSS(ATADevState *);
585static bool atapiReadCapacitySS(ATADevState *);
586static bool atapiReadDiscInformationSS(ATADevState *);
587static bool atapiReadTOCNormalSS(ATADevState *);
588static bool atapiReadTOCMultiSS(ATADevState *);
589static bool atapiReadTOCRawSS(ATADevState *);
590static bool atapiReadTrackInformationSS(ATADevState *);
591static bool atapiRequestSenseSS(ATADevState *);
592static bool atapiPassthroughSS(ATADevState *);
593static bool atapiReadDVDStructureSS(ATADevState *);
594
595/**
596 * Begin of transfer function indexes for g_apfnBeginTransFuncs.
597 */
598typedef enum ATAFNBT
599{
600 ATAFN_BT_NULL = 0,
601 ATAFN_BT_READ_WRITE_SECTORS,
602 ATAFN_BT_PACKET,
603 ATAFN_BT_ATAPI_CMD,
604 ATAFN_BT_ATAPI_PASSTHROUGH_CMD,
605 ATAFN_BT_MAX
606} ATAFNBT;
607
608/**
609 * Array of end transfer functions, the index is ATAFNET.
610 * Make sure ATAFNET and this array match!
611 */
612static const PBeginTransferFunc g_apfnBeginTransFuncs[ATAFN_BT_MAX] =
613{
614 NULL,
615 ataReadWriteSectorsBT,
616 ataPacketBT,
617 atapiCmdBT,
618 atapiPassthroughCmdBT,
619};
620
621/**
622 * Source/sink function indexes for g_apfnSourceSinkFuncs.
623 */
624typedef enum ATAFNSS
625{
626 ATAFN_SS_NULL = 0,
627 ATAFN_SS_IDENTIFY,
628 ATAFN_SS_FLUSH,
629 ATAFN_SS_READ_SECTORS,
630 ATAFN_SS_WRITE_SECTORS,
631 ATAFN_SS_EXECUTE_DEVICE_DIAGNOSTIC,
632 ATAFN_SS_PACKET,
633 ATAFN_SS_ATAPI_GET_CONFIGURATION,
634 ATAFN_SS_ATAPI_GET_EVENT_STATUS_NOTIFICATION,
635 ATAFN_SS_ATAPI_IDENTIFY,
636 ATAFN_SS_ATAPI_INQUIRY,
637 ATAFN_SS_ATAPI_MECHANISM_STATUS,
638 ATAFN_SS_ATAPI_MODE_SENSE_ERROR_RECOVERY,
639 ATAFN_SS_ATAPI_MODE_SENSE_CD_STATUS,
640 ATAFN_SS_ATAPI_READ,
641 ATAFN_SS_ATAPI_READ_CAPACITY,
642 ATAFN_SS_ATAPI_READ_DISC_INFORMATION,
643 ATAFN_SS_ATAPI_READ_TOC_NORMAL,
644 ATAFN_SS_ATAPI_READ_TOC_MULTI,
645 ATAFN_SS_ATAPI_READ_TOC_RAW,
646 ATAFN_SS_ATAPI_READ_TRACK_INFORMATION,
647 ATAFN_SS_ATAPI_REQUEST_SENSE,
648 ATAFN_SS_ATAPI_PASSTHROUGH,
649 ATAFN_SS_ATAPI_READ_DVD_STRUCTURE,
650 ATAFN_SS_MAX
651} ATAFNSS;
652
653/**
654 * Array of source/sink functions, the index is ATAFNSS.
655 * Make sure ATAFNSS and this array match!
656 */
657static const PSourceSinkFunc g_apfnSourceSinkFuncs[ATAFN_SS_MAX] =
658{
659 NULL,
660 ataIdentifySS,
661 ataFlushSS,
662 ataReadSectorsSS,
663 ataWriteSectorsSS,
664 ataExecuteDeviceDiagnosticSS,
665 ataPacketSS,
666 atapiGetConfigurationSS,
667 atapiGetEventStatusNotificationSS,
668 atapiIdentifySS,
669 atapiInquirySS,
670 atapiMechanismStatusSS,
671 atapiModeSenseErrorRecoverySS,
672 atapiModeSenseCDStatusSS,
673 atapiReadSS,
674 atapiReadCapacitySS,
675 atapiReadDiscInformationSS,
676 atapiReadTOCNormalSS,
677 atapiReadTOCMultiSS,
678 atapiReadTOCRawSS,
679 atapiReadTrackInformationSS,
680 atapiRequestSenseSS,
681 atapiPassthroughSS,
682 atapiReadDVDStructureSS
683};
684
685
686static const ATARequest g_ataDMARequest = { ATA_AIO_DMA, };
687static const ATARequest g_ataPIORequest = { ATA_AIO_PIO, };
688static const ATARequest g_ataResetARequest = { ATA_AIO_RESET_ASSERTED, };
689static const ATARequest g_ataResetCRequest = { ATA_AIO_RESET_CLEARED, };
690
691
692static void ataAsyncIOClearRequests(PATACONTROLLER pCtl)
693{
694 int rc;
695
696 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
697 AssertRC(rc);
698 pCtl->AsyncIOReqHead = 0;
699 pCtl->AsyncIOReqTail = 0;
700 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
701 AssertRC(rc);
702}
703
704
705static void ataAsyncIOPutRequest(PATACONTROLLER pCtl, const ATARequest *pReq)
706{
707 int rc;
708
709 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
710 AssertRC(rc);
711 Assert((pCtl->AsyncIOReqHead + 1) % RT_ELEMENTS(pCtl->aAsyncIORequests) != pCtl->AsyncIOReqTail);
712 memcpy(&pCtl->aAsyncIORequests[pCtl->AsyncIOReqHead], pReq, sizeof(*pReq));
713 pCtl->AsyncIOReqHead++;
714 pCtl->AsyncIOReqHead %= RT_ELEMENTS(pCtl->aAsyncIORequests);
715 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
716 AssertRC(rc);
717 rc = PDMR3CritSectScheduleExitEvent(&pCtl->lock, pCtl->AsyncIOSem);
718 if (RT_FAILURE(rc))
719 {
720 rc = RTSemEventSignal(pCtl->AsyncIOSem);
721 AssertRC(rc);
722 }
723}
724
725
726static const ATARequest *ataAsyncIOGetCurrentRequest(PATACONTROLLER pCtl)
727{
728 int rc;
729 const ATARequest *pReq;
730
731 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
732 AssertRC(rc);
733 if (pCtl->AsyncIOReqHead != pCtl->AsyncIOReqTail)
734 pReq = &pCtl->aAsyncIORequests[pCtl->AsyncIOReqTail];
735 else
736 pReq = NULL;
737 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
738 AssertRC(rc);
739 return pReq;
740}
741
742
743/**
744 * Remove the request with the given type, as it's finished. The request
745 * is not removed blindly, as this could mean a RESET request that is not
746 * yet processed (but has cleared the request queue) is lost.
747 *
748 * @param pCtl Controller for which to remove the request.
749 * @param ReqType Type of the request to remove.
750 */
751static void ataAsyncIORemoveCurrentRequest(PATACONTROLLER pCtl, ATAAIO ReqType)
752{
753 int rc;
754
755 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
756 AssertRC(rc);
757 if (pCtl->AsyncIOReqHead != pCtl->AsyncIOReqTail && pCtl->aAsyncIORequests[pCtl->AsyncIOReqTail].ReqType == ReqType)
758 {
759 pCtl->AsyncIOReqTail++;
760 pCtl->AsyncIOReqTail %= RT_ELEMENTS(pCtl->aAsyncIORequests);
761 }
762 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
763 AssertRC(rc);
764}
765
766
767/**
768 * Dump the request queue for a particular controller. First dump the queue
769 * contents, then the already processed entries, as long as they haven't been
770 * overwritten.
771 *
772 * @param pCtl Controller for which to dump the queue.
773 */
774static void ataAsyncIODumpRequests(PATACONTROLLER pCtl)
775{
776 int rc;
777 uint8_t curr;
778
779 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
780 AssertRC(rc);
781 LogRel(("PIIX3 ATA: Ctl#%d: request queue dump (topmost is current):\n", ATACONTROLLER_IDX(pCtl)));
782 curr = pCtl->AsyncIOReqTail;
783 do
784 {
785 if (curr == pCtl->AsyncIOReqHead)
786 LogRel(("PIIX3 ATA: Ctl#%d: processed requests (topmost is oldest):\n", ATACONTROLLER_IDX(pCtl)));
787 switch (pCtl->aAsyncIORequests[curr].ReqType)
788 {
789 case ATA_AIO_NEW:
790 LogRel(("new transfer request, iIf=%d iBeginTransfer=%d iSourceSink=%d cbTotalTransfer=%d uTxDir=%d\n", pCtl->aAsyncIORequests[curr].u.t.iIf, pCtl->aAsyncIORequests[curr].u.t.iBeginTransfer, pCtl->aAsyncIORequests[curr].u.t.iSourceSink, pCtl->aAsyncIORequests[curr].u.t.cbTotalTransfer, pCtl->aAsyncIORequests[curr].u.t.uTxDir));
791 break;
792 case ATA_AIO_DMA:
793 LogRel(("dma transfer continuation\n"));
794 break;
795 case ATA_AIO_PIO:
796 LogRel(("pio transfer continuation\n"));
797 break;
798 case ATA_AIO_RESET_ASSERTED:
799 LogRel(("reset asserted request\n"));
800 break;
801 case ATA_AIO_RESET_CLEARED:
802 LogRel(("reset cleared request\n"));
803 break;
804 case ATA_AIO_ABORT:
805 LogRel(("abort request, iIf=%d fResetDrive=%d\n", pCtl->aAsyncIORequests[curr].u.a.iIf, pCtl->aAsyncIORequests[curr].u.a.fResetDrive));
806 break;
807 default:
808 LogRel(("unknown request %d\n", pCtl->aAsyncIORequests[curr].ReqType));
809 }
810 curr = (curr + 1) % RT_ELEMENTS(pCtl->aAsyncIORequests);
811 } while (curr != pCtl->AsyncIOReqTail);
812 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
813 AssertRC(rc);
814}
815
816
817/**
818 * Checks whether the request queue for a particular controller is empty
819 * or whether a particular controller is idle.
820 *
821 * @param pCtl Controller for which to check the queue.
822 * @param fStrict If set then the controller is checked to be idle.
823 */
824static bool ataAsyncIOIsIdle(PATACONTROLLER pCtl, bool fStrict)
825{
826 int rc;
827 bool fIdle;
828
829 rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT);
830 AssertRC(rc);
831 fIdle = pCtl->fRedoIdle;
832 if (!fIdle)
833 fIdle = (pCtl->AsyncIOReqHead == pCtl->AsyncIOReqTail);
834 if (fStrict)
835 fIdle &= (pCtl->uAsyncIOState == ATA_AIO_NEW);
836 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex);
837 AssertRC(rc);
838 return fIdle;
839}
840
841
842/**
843 * Send a transfer request to the async I/O thread.
844 *
845 * @param s Pointer to the ATA device state data.
846 * @param cbTotalTransfer Data transfer size.
847 * @param uTxDir Data transfer direction.
848 * @param iBeginTransfer Index of BeginTransfer callback.
849 * @param iSourceSink Index of SourceSink callback.
850 * @param fChainedTransfer Whether this is a transfer that is part of the previous command/transfer.
851 */
852static void ataStartTransfer(ATADevState *s, uint32_t cbTotalTransfer, uint8_t uTxDir, ATAFNBT iBeginTransfer, ATAFNSS iSourceSink, bool fChainedTransfer)
853{
854 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
855 ATARequest Req;
856
857 Assert(PDMCritSectIsOwner(&pCtl->lock));
858
859 /* Do not issue new requests while the RESET line is asserted. */
860 if (pCtl->fReset)
861 {
862 Log2(("%s: Ctl#%d: suppressed new request as RESET is active\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
863 return;
864 }
865
866 /* If the controller is already doing something else right now, ignore
867 * the command that is being submitted. Some broken guests issue commands
868 * twice (e.g. the Linux kernel that comes with Acronis True Image 8). */
869 if (!fChainedTransfer && !ataAsyncIOIsIdle(pCtl, true /*fStrict*/))
870 {
871 Log(("%s: Ctl#%d: ignored command %#04x, controller state %d\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), s->uATARegCommand, pCtl->uAsyncIOState));
872 LogRel(("PIIX3 IDE: guest issued command %#04x while controller busy\n", s->uATARegCommand));
873 return;
874 }
875
876 Req.ReqType = ATA_AIO_NEW;
877 if (fChainedTransfer)
878 Req.u.t.iIf = pCtl->iAIOIf;
879 else
880 Req.u.t.iIf = pCtl->iSelectedIf;
881 Req.u.t.cbTotalTransfer = cbTotalTransfer;
882 Req.u.t.uTxDir = uTxDir;
883 Req.u.t.iBeginTransfer = iBeginTransfer;
884 Req.u.t.iSourceSink = iSourceSink;
885 ataSetStatusValue(s, ATA_STAT_BUSY);
886 pCtl->fChainedTransfer = fChainedTransfer;
887
888 /*
889 * Kick the worker thread into action.
890 */
891 Log2(("%s: Ctl#%d: message to async I/O thread, new request\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
892 ataAsyncIOPutRequest(pCtl, &Req);
893}
894
895
896/**
897 * Send an abort command request to the async I/O thread.
898 *
899 * @param s Pointer to the ATA device state data.
900 * @param fResetDrive Whether to reset the drive or just abort a command.
901 */
902static void ataAbortCurrentCommand(ATADevState *s, bool fResetDrive)
903{
904 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
905 ATARequest Req;
906
907 Assert(PDMCritSectIsOwner(&pCtl->lock));
908
909 /* Do not issue new requests while the RESET line is asserted. */
910 if (pCtl->fReset)
911 {
912 Log2(("%s: Ctl#%d: suppressed aborting command as RESET is active\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
913 return;
914 }
915
916 Req.ReqType = ATA_AIO_ABORT;
917 Req.u.a.iIf = pCtl->iSelectedIf;
918 Req.u.a.fResetDrive = fResetDrive;
919 ataSetStatus(s, ATA_STAT_BUSY);
920 Log2(("%s: Ctl#%d: message to async I/O thread, abort command on LUN#%d\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), s->iLUN));
921 ataAsyncIOPutRequest(pCtl, &Req);
922}
923
924
925static void ataSetIRQ(ATADevState *s)
926{
927 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
928 PPDMDEVINS pDevIns = ATADEVSTATE_2_DEVINS(s);
929
930 if (!(s->uATARegDevCtl & ATA_DEVCTL_DISABLE_IRQ))
931 {
932 Log2(("%s: LUN#%d asserting IRQ\n", __FUNCTION__, s->iLUN));
933 /* The BMDMA unit unconditionally sets BM_STATUS_INT if the interrupt
934 * line is asserted. It monitors the line for a rising edge. */
935 if (!s->fIrqPending)
936 pCtl->BmDma.u8Status |= BM_STATUS_INT;
937 /* Only actually set the IRQ line if updating the currently selected drive. */
938 if (s == &pCtl->aIfs[pCtl->iSelectedIf])
939 {
940 /** @todo experiment with adaptive IRQ delivery: for reads it is
941 * better to wait for IRQ delivery, as it reduces latency. */
942 if (pCtl->irq == 16)
943 PDMDevHlpPCISetIrqNoWait(pDevIns, 0, 1);
944 else
945 PDMDevHlpISASetIrqNoWait(pDevIns, pCtl->irq, 1);
946 }
947 }
948 s->fIrqPending = true;
949}
950
951#endif /* IN_RING3 */
952
953static void ataUnsetIRQ(ATADevState *s)
954{
955 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
956 PPDMDEVINS pDevIns = ATADEVSTATE_2_DEVINS(s);
957
958 if (!(s->uATARegDevCtl & ATA_DEVCTL_DISABLE_IRQ))
959 {
960 Log2(("%s: LUN#%d deasserting IRQ\n", __FUNCTION__, s->iLUN));
961 /* Only actually unset the IRQ line if updating the currently selected drive. */
962 if (s == &pCtl->aIfs[pCtl->iSelectedIf])
963 {
964 if (pCtl->irq == 16)
965 PDMDevHlpPCISetIrqNoWait(pDevIns, 0, 0);
966 else
967 PDMDevHlpISASetIrqNoWait(pDevIns, pCtl->irq, 0);
968 }
969 }
970 s->fIrqPending = false;
971}
972
973#ifdef IN_RING3
974
975static void ataPIOTransferStart(ATADevState *s, uint32_t start, uint32_t size)
976{
977 Log2(("%s: LUN#%d start %d size %d\n", __FUNCTION__, s->iLUN, start, size));
978 s->iIOBufferPIODataStart = start;
979 s->iIOBufferPIODataEnd = start + size;
980 ataSetStatus(s, ATA_STAT_DRQ);
981}
982
983
984static void ataPIOTransferStop(ATADevState *s)
985{
986 Log2(("%s: LUN#%d\n", __FUNCTION__, s->iLUN));
987 if (s->fATAPITransfer)
988 {
989 s->uATARegNSector = (s->uATARegNSector & ~7) | ATAPI_INT_REASON_IO | ATAPI_INT_REASON_CD;
990 Log2(("%s: interrupt reason %#04x\n", __FUNCTION__, s->uATARegNSector));
991 ataSetIRQ(s);
992 s->fATAPITransfer = false;
993 }
994 s->cbTotalTransfer = 0;
995 s->cbElementaryTransfer = 0;
996 s->iIOBufferPIODataStart = 0;
997 s->iIOBufferPIODataEnd = 0;
998 s->iBeginTransfer = ATAFN_BT_NULL;
999 s->iSourceSink = ATAFN_SS_NULL;
1000}
1001
1002
1003static void ataPIOTransferLimitATAPI(ATADevState *s)
1004{
1005 uint32_t cbLimit, cbTransfer;
1006
1007 cbLimit = s->uATARegLCyl | (s->uATARegHCyl << 8);
1008 /* Use maximum transfer size if the guest requested 0. Avoids a hang. */
1009 if (cbLimit == 0)
1010 cbLimit = 0xfffe;
1011 Log2(("%s: byte count limit=%d\n", __FUNCTION__, cbLimit));
1012 if (cbLimit == 0xffff)
1013 cbLimit--;
1014 cbTransfer = RT_MIN(s->cbTotalTransfer, s->iIOBufferEnd - s->iIOBufferCur);
1015 if (cbTransfer > cbLimit)
1016 {
1017 /* Byte count limit for clipping must be even in this case */
1018 if (cbLimit & 1)
1019 cbLimit--;
1020 cbTransfer = cbLimit;
1021 }
1022 s->uATARegLCyl = cbTransfer;
1023 s->uATARegHCyl = cbTransfer >> 8;
1024 s->cbElementaryTransfer = cbTransfer;
1025}
1026
1027
1028static uint32_t ataGetNSectors(ATADevState *s)
1029{
1030 /* 0 means either 256 (LBA28) or 65536 (LBA48) sectors. */
1031 if (s->fLBA48)
1032 {
1033 if (!s->uATARegNSector && !s->uATARegNSectorHOB)
1034 return 65536;
1035 else
1036 return s->uATARegNSectorHOB << 8 | s->uATARegNSector;
1037 }
1038 else
1039 {
1040 if (!s->uATARegNSector)
1041 return 256;
1042 else
1043 return s->uATARegNSector;
1044 }
1045}
1046
1047
1048static void ataPadString(uint8_t *pbDst, const char *pbSrc, uint32_t cbSize)
1049{
1050 for (uint32_t i = 0; i < cbSize; i++)
1051 {
1052 if (*pbSrc)
1053 pbDst[i ^ 1] = *pbSrc++;
1054 else
1055 pbDst[i ^ 1] = ' ';
1056 }
1057}
1058
1059
1060static void ataSCSIPadStr(uint8_t *pbDst, const char *pbSrc, uint32_t cbSize)
1061{
1062 for (uint32_t i = 0; i < cbSize; i++)
1063 {
1064 if (*pbSrc)
1065 pbDst[i] = *pbSrc++;
1066 else
1067 pbDst[i] = ' ';
1068 }
1069}
1070
1071
1072DECLINLINE(void) ataH2BE_U16(uint8_t *pbBuf, uint16_t val)
1073{
1074 pbBuf[0] = val >> 8;
1075 pbBuf[1] = val;
1076}
1077
1078
1079DECLINLINE(void) ataH2BE_U24(uint8_t *pbBuf, uint32_t val)
1080{
1081 pbBuf[0] = val >> 16;
1082 pbBuf[1] = val >> 8;
1083 pbBuf[2] = val;
1084}
1085
1086
1087DECLINLINE(void) ataH2BE_U32(uint8_t *pbBuf, uint32_t val)
1088{
1089 pbBuf[0] = val >> 24;
1090 pbBuf[1] = val >> 16;
1091 pbBuf[2] = val >> 8;
1092 pbBuf[3] = val;
1093}
1094
1095
1096DECLINLINE(uint16_t) ataBE2H_U16(const uint8_t *pbBuf)
1097{
1098 return (pbBuf[0] << 8) | pbBuf[1];
1099}
1100
1101
1102DECLINLINE(uint32_t) ataBE2H_U24(const uint8_t *pbBuf)
1103{
1104 return (pbBuf[0] << 16) | (pbBuf[1] << 8) | pbBuf[2];
1105}
1106
1107
1108DECLINLINE(uint32_t) ataBE2H_U32(const uint8_t *pbBuf)
1109{
1110 return (pbBuf[0] << 24) | (pbBuf[1] << 16) | (pbBuf[2] << 8) | pbBuf[3];
1111}
1112
1113
1114DECLINLINE(void) ataLBA2MSF(uint8_t *pbBuf, uint32_t iATAPILBA)
1115{
1116 iATAPILBA += 150;
1117 pbBuf[0] = (iATAPILBA / 75) / 60;
1118 pbBuf[1] = (iATAPILBA / 75) % 60;
1119 pbBuf[2] = iATAPILBA % 75;
1120}
1121
1122
1123DECLINLINE(uint32_t) ataMSF2LBA(const uint8_t *pbBuf)
1124{
1125 return (pbBuf[0] * 60 + pbBuf[1]) * 75 + pbBuf[2];
1126}
1127
1128
1129static void ataCmdOK(ATADevState *s, uint8_t status)
1130{
1131 s->uATARegError = 0; /* Not needed by ATA spec, but cannot hurt. */
1132 ataSetStatusValue(s, ATA_STAT_READY | status);
1133}
1134
1135
1136static void ataCmdError(ATADevState *s, uint8_t uErrorCode)
1137{
1138 Log(("%s: code=%#x\n", __FUNCTION__, uErrorCode));
1139 s->uATARegError = uErrorCode;
1140 ataSetStatusValue(s, ATA_STAT_READY | ATA_STAT_ERR);
1141 s->cbTotalTransfer = 0;
1142 s->cbElementaryTransfer = 0;
1143 s->iIOBufferCur = 0;
1144 s->iIOBufferEnd = 0;
1145 s->uTxDir = PDMBLOCKTXDIR_NONE;
1146 s->iBeginTransfer = ATAFN_BT_NULL;
1147 s->iSourceSink = ATAFN_SS_NULL;
1148}
1149
1150
1151static bool ataIdentifySS(ATADevState *s)
1152{
1153 uint16_t *p;
1154
1155 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
1156 Assert(s->cbElementaryTransfer == 512);
1157
1158 p = (uint16_t *)s->CTX_SUFF(pbIOBuffer);
1159 memset(p, 0, 512);
1160 p[0] = RT_H2LE_U16(0x0040);
1161 p[1] = RT_H2LE_U16(RT_MIN(s->PCHSGeometry.cCylinders, 16383));
1162 p[3] = RT_H2LE_U16(s->PCHSGeometry.cHeads);
1163 /* Block size; obsolete, but required for the BIOS. */
1164 p[5] = RT_H2LE_U16(512);
1165 p[6] = RT_H2LE_U16(s->PCHSGeometry.cSectors);
1166 ataPadString((uint8_t *)(p + 10), s->szSerialNumber, ATA_SERIAL_NUMBER_LENGTH); /* serial number */
1167 p[20] = RT_H2LE_U16(3); /* XXX: retired, cache type */
1168 p[21] = RT_H2LE_U16(512); /* XXX: retired, cache size in sectors */
1169 p[22] = RT_H2LE_U16(0); /* ECC bytes per sector */
1170 ataPadString((uint8_t *)(p + 23), s->szFirmwareRevision, ATA_FIRMWARE_REVISION_LENGTH); /* firmware version */
1171 ataPadString((uint8_t *)(p + 27), s->szModelNumber, ATA_MODEL_NUMBER_LENGTH); /* model */
1172#if ATA_MAX_MULT_SECTORS > 1
1173 p[47] = RT_H2LE_U16(0x8000 | ATA_MAX_MULT_SECTORS);
1174#endif
1175 p[48] = RT_H2LE_U16(1); /* dword I/O, used by the BIOS */
1176 p[49] = RT_H2LE_U16(1 << 11 | 1 << 9 | 1 << 8); /* DMA and LBA supported */
1177 p[50] = RT_H2LE_U16(1 << 14); /* No drive specific standby timer minimum */
1178 p[51] = RT_H2LE_U16(240); /* PIO transfer cycle */
1179 p[52] = RT_H2LE_U16(240); /* DMA transfer cycle */
1180 p[53] = RT_H2LE_U16(1 | 1 << 1 | 1 << 2); /* words 54-58,64-70,88 valid */
1181 p[54] = RT_H2LE_U16(RT_MIN(s->PCHSGeometry.cCylinders, 16383));
1182 p[55] = RT_H2LE_U16(s->PCHSGeometry.cHeads);
1183 p[56] = RT_H2LE_U16(s->PCHSGeometry.cSectors);
1184 p[57] = RT_H2LE_U16( RT_MIN(s->PCHSGeometry.cCylinders, 16383)
1185 * s->PCHSGeometry.cHeads
1186 * s->PCHSGeometry.cSectors);
1187 p[58] = RT_H2LE_U16( RT_MIN(s->PCHSGeometry.cCylinders, 16383)
1188 * s->PCHSGeometry.cHeads
1189 * s->PCHSGeometry.cSectors >> 16);
1190 if (s->cMultSectors)
1191 p[59] = RT_H2LE_U16(0x100 | s->cMultSectors);
1192 if (s->cTotalSectors <= (1 << 28) - 1)
1193 {
1194 p[60] = RT_H2LE_U16(s->cTotalSectors);
1195 p[61] = RT_H2LE_U16(s->cTotalSectors >> 16);
1196 }
1197 else
1198 {
1199 /* Report maximum number of sectors possible with LBA28 */
1200 p[60] = RT_H2LE_U16(((1 << 28) - 1) & 0xffff);
1201 p[61] = RT_H2LE_U16(((1 << 28) - 1) >> 16);
1202 }
1203 p[63] = RT_H2LE_U16(ATA_TRANSFER_ID(ATA_MODE_MDMA, ATA_MDMA_MODE_MAX, s->uATATransferMode)); /* MDMA modes supported / mode enabled */
1204 p[64] = RT_H2LE_U16(ATA_PIO_MODE_MAX > 2 ? (1 << (ATA_PIO_MODE_MAX - 2)) - 1 : 0); /* PIO modes beyond PIO2 supported */
1205 p[65] = RT_H2LE_U16(120); /* minimum DMA multiword tx cycle time */
1206 p[66] = RT_H2LE_U16(120); /* recommended DMA multiword tx cycle time */
1207 p[67] = RT_H2LE_U16(120); /* minimum PIO cycle time without flow control */
1208 p[68] = RT_H2LE_U16(120); /* minimum PIO cycle time with IORDY flow control */
1209 p[80] = RT_H2LE_U16(0x7e); /* support everything up to ATA/ATAPI-6 */
1210 p[81] = RT_H2LE_U16(0x22); /* conforms to ATA/ATAPI-6 */
1211 p[82] = RT_H2LE_U16(1 << 3 | 1 << 5 | 1 << 6); /* supports power management, write cache and look-ahead */
1212 if (s->cTotalSectors <= (1 << 28) - 1)
1213 p[83] = RT_H2LE_U16(1 << 14 | 1 << 12); /* supports FLUSH CACHE */
1214 else
1215 p[83] = RT_H2LE_U16(1 << 14 | 1 << 10 | 1 << 12 | 1 << 13); /* supports LBA48, FLUSH CACHE and FLUSH CACHE EXT */
1216 p[84] = RT_H2LE_U16(1 << 14);
1217 p[85] = RT_H2LE_U16(1 << 3 | 1 << 5 | 1 << 6); /* enabled power management, write cache and look-ahead */
1218 if (s->cTotalSectors <= (1 << 28) - 1)
1219 p[86] = RT_H2LE_U16(1 << 12); /* enabled FLUSH CACHE */
1220 else
1221 p[86] = RT_H2LE_U16(1 << 10 | 1 << 12 | 1 << 13); /* enabled LBA48, FLUSH CACHE and FLUSH CACHE EXT */
1222 p[87] = RT_H2LE_U16(1 << 14);
1223 p[88] = RT_H2LE_U16(ATA_TRANSFER_ID(ATA_MODE_UDMA, ATA_UDMA_MODE_MAX, s->uATATransferMode)); /* UDMA modes supported / mode enabled */
1224 p[93] = RT_H2LE_U16((1 | 1 << 1) << ((s->iLUN & 1) == 0 ? 0 : 8) | 1 << 13 | 1 << 14);
1225 if (s->cTotalSectors > (1 << 28) - 1)
1226 {
1227 p[100] = RT_H2LE_U16(s->cTotalSectors);
1228 p[101] = RT_H2LE_U16(s->cTotalSectors >> 16);
1229 p[102] = RT_H2LE_U16(s->cTotalSectors >> 32);
1230 p[103] = RT_H2LE_U16(s->cTotalSectors >> 48);
1231 }
1232 s->iSourceSink = ATAFN_SS_NULL;
1233 ataCmdOK(s, ATA_STAT_SEEK);
1234 return false;
1235}
1236
1237
1238static bool ataFlushSS(ATADevState *s)
1239{
1240 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1241 int rc;
1242
1243 Assert(s->uTxDir == PDMBLOCKTXDIR_NONE);
1244 Assert(!s->cbElementaryTransfer);
1245
1246 PDMCritSectLeave(&pCtl->lock);
1247
1248 STAM_PROFILE_START(&s->StatFlushes, f);
1249 rc = s->pDrvBlock->pfnFlush(s->pDrvBlock);
1250 AssertRC(rc);
1251 STAM_PROFILE_STOP(&s->StatFlushes, f);
1252
1253 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1254 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1255 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1256 ataCmdOK(s, 0);
1257 return false;
1258}
1259
1260
1261static bool atapiIdentifySS(ATADevState *s)
1262{
1263 uint16_t *p;
1264
1265 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
1266 Assert(s->cbElementaryTransfer == 512);
1267
1268 p = (uint16_t *)s->CTX_SUFF(pbIOBuffer);
1269 memset(p, 0, 512);
1270 /* Removable CDROM, 50us response, 12 byte packets */
1271 p[0] = RT_H2LE_U16(2 << 14 | 5 << 8 | 1 << 7 | 2 << 5 | 0 << 0);
1272 ataPadString((uint8_t *)(p + 10), s->szSerialNumber, ATA_SERIAL_NUMBER_LENGTH); /* serial number */
1273 p[20] = RT_H2LE_U16(3); /* XXX: retired, cache type */
1274 p[21] = RT_H2LE_U16(512); /* XXX: retired, cache size in sectors */
1275 ataPadString((uint8_t *)(p + 23), s->szFirmwareRevision, ATA_FIRMWARE_REVISION_LENGTH); /* firmware version */
1276 ataPadString((uint8_t *)(p + 27), s->szModelNumber, ATA_MODEL_NUMBER_LENGTH); /* model */
1277 p[49] = RT_H2LE_U16(1 << 11 | 1 << 9 | 1 << 8); /* DMA and LBA supported */
1278 p[50] = RT_H2LE_U16(1 << 14); /* No drive specific standby timer minimum */
1279 p[51] = RT_H2LE_U16(240); /* PIO transfer cycle */
1280 p[52] = RT_H2LE_U16(240); /* DMA transfer cycle */
1281 p[53] = RT_H2LE_U16(1 << 1 | 1 << 2); /* words 64-70,88 are valid */
1282 p[63] = RT_H2LE_U16(ATA_TRANSFER_ID(ATA_MODE_MDMA, ATA_MDMA_MODE_MAX, s->uATATransferMode)); /* MDMA modes supported / mode enabled */
1283 p[64] = RT_H2LE_U16(ATA_PIO_MODE_MAX > 2 ? (1 << (ATA_PIO_MODE_MAX - 2)) - 1 : 0); /* PIO modes beyond PIO2 supported */
1284 p[65] = RT_H2LE_U16(120); /* minimum DMA multiword tx cycle time */
1285 p[66] = RT_H2LE_U16(120); /* recommended DMA multiword tx cycle time */
1286 p[67] = RT_H2LE_U16(120); /* minimum PIO cycle time without flow control */
1287 p[68] = RT_H2LE_U16(120); /* minimum PIO cycle time with IORDY flow control */
1288 p[73] = RT_H2LE_U16(0x003e); /* ATAPI CDROM major */
1289 p[74] = RT_H2LE_U16(9); /* ATAPI CDROM minor */
1290 p[75] = RT_H2LE_U16(1); /* queue depth 1 */
1291 p[80] = RT_H2LE_U16(0x7e); /* support everything up to ATA/ATAPI-6 */
1292 p[81] = RT_H2LE_U16(0x22); /* conforms to ATA/ATAPI-6 */
1293 p[82] = RT_H2LE_U16(1 << 4 | 1 << 9); /* supports packet command set and DEVICE RESET */
1294 p[83] = RT_H2LE_U16(1 << 14);
1295 p[84] = RT_H2LE_U16(1 << 14);
1296 p[85] = RT_H2LE_U16(1 << 4 | 1 << 9); /* enabled packet command set and DEVICE RESET */
1297 p[86] = RT_H2LE_U16(0);
1298 p[87] = RT_H2LE_U16(1 << 14);
1299 p[88] = RT_H2LE_U16(ATA_TRANSFER_ID(ATA_MODE_UDMA, ATA_UDMA_MODE_MAX, s->uATATransferMode)); /* UDMA modes supported / mode enabled */
1300 p[93] = RT_H2LE_U16((1 | 1 << 1) << ((s->iLUN & 1) == 0 ? 0 : 8) | 1 << 13 | 1 << 14);
1301 s->iSourceSink = ATAFN_SS_NULL;
1302 ataCmdOK(s, ATA_STAT_SEEK);
1303 return false;
1304}
1305
1306
1307static void ataSetSignature(ATADevState *s)
1308{
1309 s->uATARegSelect &= 0xf0; /* clear head */
1310 /* put signature */
1311 s->uATARegNSector = 1;
1312 s->uATARegSector = 1;
1313 if (s->fATAPI)
1314 {
1315 s->uATARegLCyl = 0x14;
1316 s->uATARegHCyl = 0xeb;
1317 }
1318 else if (s->pDrvBlock)
1319 {
1320 s->uATARegLCyl = 0;
1321 s->uATARegHCyl = 0;
1322 }
1323 else
1324 {
1325 s->uATARegLCyl = 0xff;
1326 s->uATARegHCyl = 0xff;
1327 }
1328}
1329
1330
1331static uint64_t ataGetSector(ATADevState *s)
1332{
1333 uint64_t iLBA;
1334 if (s->uATARegSelect & 0x40)
1335 {
1336 /* any LBA variant */
1337 if (s->fLBA48)
1338 {
1339 /* LBA48 */
1340 iLBA = ((uint64_t)s->uATARegHCylHOB << 40) |
1341 ((uint64_t)s->uATARegLCylHOB << 32) |
1342 ((uint64_t)s->uATARegSectorHOB << 24) |
1343 ((uint64_t)s->uATARegHCyl << 16) |
1344 ((uint64_t)s->uATARegLCyl << 8) |
1345 s->uATARegSector;
1346 }
1347 else
1348 {
1349 /* LBA */
1350 iLBA = ((s->uATARegSelect & 0x0f) << 24) | (s->uATARegHCyl << 16) |
1351 (s->uATARegLCyl << 8) | s->uATARegSector;
1352 }
1353 }
1354 else
1355 {
1356 /* CHS */
1357 iLBA = ((s->uATARegHCyl << 8) | s->uATARegLCyl) * s->PCHSGeometry.cHeads * s->PCHSGeometry.cSectors +
1358 (s->uATARegSelect & 0x0f) * s->PCHSGeometry.cSectors +
1359 (s->uATARegSector - 1);
1360 }
1361 return iLBA;
1362}
1363
1364static void ataSetSector(ATADevState *s, uint64_t iLBA)
1365{
1366 uint32_t cyl, r;
1367 if (s->uATARegSelect & 0x40)
1368 {
1369 /* any LBA variant */
1370 if (s->fLBA48)
1371 {
1372 /* LBA48 */
1373 s->uATARegHCylHOB = iLBA >> 40;
1374 s->uATARegLCylHOB = iLBA >> 32;
1375 s->uATARegSectorHOB = iLBA >> 24;
1376 s->uATARegHCyl = iLBA >> 16;
1377 s->uATARegLCyl = iLBA >> 8;
1378 s->uATARegSector = iLBA;
1379 }
1380 else
1381 {
1382 /* LBA */
1383 s->uATARegSelect = (s->uATARegSelect & 0xf0) | (iLBA >> 24);
1384 s->uATARegHCyl = (iLBA >> 16);
1385 s->uATARegLCyl = (iLBA >> 8);
1386 s->uATARegSector = (iLBA);
1387 }
1388 }
1389 else
1390 {
1391 /* CHS */
1392 cyl = iLBA / (s->PCHSGeometry.cHeads * s->PCHSGeometry.cSectors);
1393 r = iLBA % (s->PCHSGeometry.cHeads * s->PCHSGeometry.cSectors);
1394 s->uATARegHCyl = cyl >> 8;
1395 s->uATARegLCyl = cyl;
1396 s->uATARegSelect = (s->uATARegSelect & 0xf0) | ((r / s->PCHSGeometry.cSectors) & 0x0f);
1397 s->uATARegSector = (r % s->PCHSGeometry.cSectors) + 1;
1398 }
1399}
1400
1401
1402static void ataWarningDiskFull(PPDMDEVINS pDevIns)
1403{
1404 int rc;
1405 LogRel(("PIIX3 ATA: Host disk full\n"));
1406 rc = PDMDevHlpVMSetRuntimeError(pDevIns, 0 /*fFlags*/, "DevATA_DISKFULL",
1407 N_("Host system reported disk full. VM execution is suspended. You can resume after freeing some space"));
1408 AssertRC(rc);
1409}
1410
1411static void ataWarningFileTooBig(PPDMDEVINS pDevIns)
1412{
1413 int rc;
1414 LogRel(("PIIX3 ATA: File too big\n"));
1415 rc = PDMDevHlpVMSetRuntimeError(pDevIns, 0 /*fFlags*/, "DevATA_FILETOOBIG",
1416 N_("Host system reported that the file size limit of the host file system has been exceeded. VM execution is suspended. You need to move your virtual hard disk to a filesystem which allows bigger files"));
1417 AssertRC(rc);
1418}
1419
1420static void ataWarningISCSI(PPDMDEVINS pDevIns)
1421{
1422 int rc;
1423 LogRel(("PIIX3 ATA: iSCSI target unavailable\n"));
1424 rc = PDMDevHlpVMSetRuntimeError(pDevIns, 0 /*fFlags*/, "DevATA_ISCSIDOWN",
1425 N_("The iSCSI target has stopped responding. VM execution is suspended. You can resume when it is available again"));
1426 AssertRC(rc);
1427}
1428
1429/**
1430 * Suspend I/O operations on a controller. Also suspends EMT, because it's
1431 * waiting for I/O to make progress. The next attempt to perform an I/O
1432 * operation will be made when EMT is resumed up again (as the resume
1433 * callback below restarts I/O).
1434 *
1435 * @param pCtl Controller for which to suspend I/O.
1436 */
1437static void ataSuspendRedo(PATACONTROLLER pCtl)
1438{
1439 PPDMDEVINS pDevIns = CONTROLLER_2_DEVINS(pCtl);
1440 int rc;
1441
1442 pCtl->fRedoIdle = true;
1443 rc = VMR3ReqCallWait(PDMDevHlpGetVM(pDevIns), VMCPUID_ANY,
1444 (PFNRT)PDMDevHlpVMSuspend, 1, pDevIns);
1445 AssertReleaseRC(rc);
1446}
1447
1448bool ataIsRedoSetWarning(ATADevState *s, int rc)
1449{
1450 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1451 Assert(!PDMCritSectIsOwner(&pCtl->lock));
1452 if (rc == VERR_DISK_FULL)
1453 {
1454 ataWarningDiskFull(ATADEVSTATE_2_DEVINS(s));
1455 ataSuspendRedo(pCtl);
1456 return true;
1457 }
1458 if (rc == VERR_FILE_TOO_BIG)
1459 {
1460 ataWarningFileTooBig(ATADEVSTATE_2_DEVINS(s));
1461 ataSuspendRedo(pCtl);
1462 return true;
1463 }
1464 if (rc == VERR_BROKEN_PIPE || rc == VERR_NET_CONNECTION_REFUSED)
1465 {
1466 /* iSCSI connection abort (first error) or failure to reestablish
1467 * connection (second error). Pause VM. On resume we'll retry. */
1468 ataWarningISCSI(ATADEVSTATE_2_DEVINS(s));
1469 ataSuspendRedo(pCtl);
1470 return true;
1471 }
1472 return false;
1473}
1474
1475
1476static int ataReadSectors(ATADevState *s, uint64_t u64Sector, void *pvBuf, uint32_t cSectors, bool *fRedo)
1477{
1478 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1479 int rc;
1480
1481 PDMCritSectLeave(&pCtl->lock);
1482
1483 STAM_PROFILE_ADV_START(&s->StatReads, r);
1484 s->Led.Asserted.s.fReading = s->Led.Actual.s.fReading = 1;
1485 rc = s->pDrvBlock->pfnRead(s->pDrvBlock, u64Sector * 512, pvBuf, cSectors * 512);
1486 s->Led.Actual.s.fReading = 0;
1487 STAM_PROFILE_ADV_STOP(&s->StatReads, r);
1488
1489 STAM_REL_COUNTER_ADD(&s->StatBytesRead, cSectors * 512);
1490
1491 if (RT_SUCCESS(rc))
1492 *fRedo = false;
1493 else
1494 *fRedo = ataIsRedoSetWarning(s, rc);
1495
1496 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1497 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1498 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1499 return rc;
1500}
1501
1502
1503static int ataWriteSectors(ATADevState *s, uint64_t u64Sector, const void *pvBuf, uint32_t cSectors, bool *fRedo)
1504{
1505 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1506 int rc;
1507
1508 PDMCritSectLeave(&pCtl->lock);
1509
1510 STAM_PROFILE_ADV_START(&s->StatWrites, w);
1511 s->Led.Asserted.s.fWriting = s->Led.Actual.s.fWriting = 1;
1512#ifdef VBOX_INSTRUMENT_DMA_WRITES
1513 if (s->fDMA)
1514 STAM_PROFILE_ADV_START(&s->StatInstrVDWrites, vw);
1515#endif
1516 rc = s->pDrvBlock->pfnWrite(s->pDrvBlock, u64Sector * 512, pvBuf, cSectors * 512);
1517#ifdef VBOX_INSTRUMENT_DMA_WRITES
1518 if (s->fDMA)
1519 STAM_PROFILE_ADV_STOP(&s->StatInstrVDWrites, vw);
1520#endif
1521 s->Led.Actual.s.fWriting = 0;
1522 STAM_PROFILE_ADV_STOP(&s->StatWrites, w);
1523
1524 STAM_REL_COUNTER_ADD(&s->StatBytesWritten, cSectors * 512);
1525
1526 if (RT_SUCCESS(rc))
1527 *fRedo = false;
1528 else
1529 *fRedo = ataIsRedoSetWarning(s, rc);
1530
1531 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1532 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1533 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1534 return rc;
1535}
1536
1537
1538static void ataReadWriteSectorsBT(ATADevState *s)
1539{
1540 uint32_t cSectors;
1541
1542 cSectors = s->cbTotalTransfer / 512;
1543 if (cSectors > s->cSectorsPerIRQ)
1544 s->cbElementaryTransfer = s->cSectorsPerIRQ * 512;
1545 else
1546 s->cbElementaryTransfer = cSectors * 512;
1547 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE)
1548 ataCmdOK(s, 0);
1549}
1550
1551
1552static bool ataReadSectorsSS(ATADevState *s)
1553{
1554 int rc;
1555 uint32_t cSectors;
1556 uint64_t iLBA;
1557 bool fRedo;
1558
1559 cSectors = s->cbElementaryTransfer / 512;
1560 Assert(cSectors);
1561 iLBA = ataGetSector(s);
1562 Log(("%s: %d sectors at LBA %d\n", __FUNCTION__, cSectors, iLBA));
1563 rc = ataReadSectors(s, iLBA, s->CTX_SUFF(pbIOBuffer), cSectors, &fRedo);
1564 if (RT_SUCCESS(rc))
1565 {
1566 ataSetSector(s, iLBA + cSectors);
1567 if (s->cbElementaryTransfer == s->cbTotalTransfer)
1568 s->iSourceSink = ATAFN_SS_NULL;
1569 ataCmdOK(s, ATA_STAT_SEEK);
1570 }
1571 else
1572 {
1573 if (fRedo)
1574 return fRedo;
1575 if (s->cErrors++ < MAX_LOG_REL_ERRORS)
1576 LogRel(("PIIX3 ATA: LUN#%d: disk read error (rc=%Rrc iSector=%#RX64 cSectors=%#RX32)\n",
1577 s->iLUN, rc, iLBA, cSectors));
1578
1579 /*
1580 * Check if we got interrupted. We don't need to set status variables
1581 * because the request was aborted.
1582 */
1583 if (rc != VERR_INTERRUPTED)
1584 ataCmdError(s, ID_ERR);
1585 }
1586 return false;
1587}
1588
1589
1590static bool ataWriteSectorsSS(ATADevState *s)
1591{
1592 int rc;
1593 uint32_t cSectors;
1594 uint64_t iLBA;
1595 bool fRedo;
1596
1597 cSectors = s->cbElementaryTransfer / 512;
1598 Assert(cSectors);
1599 iLBA = ataGetSector(s);
1600 Log(("%s: %d sectors at LBA %d\n", __FUNCTION__, cSectors, iLBA));
1601 rc = ataWriteSectors(s, iLBA, s->CTX_SUFF(pbIOBuffer), cSectors, &fRedo);
1602 if (RT_SUCCESS(rc))
1603 {
1604 ataSetSector(s, iLBA + cSectors);
1605 if (!s->cbTotalTransfer)
1606 s->iSourceSink = ATAFN_SS_NULL;
1607 ataCmdOK(s, ATA_STAT_SEEK);
1608 }
1609 else
1610 {
1611 if (fRedo)
1612 return fRedo;
1613 if (s->cErrors++ < MAX_LOG_REL_ERRORS)
1614 LogRel(("PIIX3 ATA: LUN#%d: disk write error (rc=%Rrc iSector=%#RX64 cSectors=%#RX32)\n",
1615 s->iLUN, rc, iLBA, cSectors));
1616
1617 /*
1618 * Check if we got interrupted. We don't need to set status variables
1619 * because the request was aborted.
1620 */
1621 if (rc != VERR_INTERRUPTED)
1622 ataCmdError(s, ID_ERR);
1623 }
1624 return false;
1625}
1626
1627
1628static void atapiCmdOK(ATADevState *s)
1629{
1630 s->uATARegError = 0;
1631 ataSetStatusValue(s, ATA_STAT_READY);
1632 s->uATARegNSector = (s->uATARegNSector & ~7)
1633 | ((s->uTxDir != PDMBLOCKTXDIR_TO_DEVICE) ? ATAPI_INT_REASON_IO : 0)
1634 | (!s->cbTotalTransfer ? ATAPI_INT_REASON_CD : 0);
1635 Log2(("%s: interrupt reason %#04x\n", __FUNCTION__, s->uATARegNSector));
1636
1637 memset(s->abATAPISense, '\0', sizeof(s->abATAPISense));
1638 s->abATAPISense[0] = 0x70 | (1 << 7);
1639 s->abATAPISense[7] = 10;
1640}
1641
1642
1643static void atapiCmdError(ATADevState *s, const uint8_t *pabATAPISense, size_t cbATAPISense)
1644{
1645 Log(("%s: sense=%#x (%s) asc=%#x ascq=%#x (%s)\n", __FUNCTION__, pabATAPISense[2] & 0x0f, SCSISenseText(pabATAPISense[2] & 0x0f),
1646 pabATAPISense[12], pabATAPISense[13], SCSISenseExtText(pabATAPISense[12], pabATAPISense[13])));
1647 s->uATARegError = pabATAPISense[2] << 4;
1648 ataSetStatusValue(s, ATA_STAT_READY | ATA_STAT_ERR);
1649 s->uATARegNSector = (s->uATARegNSector & ~7) | ATAPI_INT_REASON_IO | ATAPI_INT_REASON_CD;
1650 Log2(("%s: interrupt reason %#04x\n", __FUNCTION__, s->uATARegNSector));
1651 memset(s->abATAPISense, '\0', sizeof(s->abATAPISense));
1652 memcpy(s->abATAPISense, pabATAPISense, RT_MIN(cbATAPISense, sizeof(s->abATAPISense)));
1653 s->cbTotalTransfer = 0;
1654 s->cbElementaryTransfer = 0;
1655 s->iIOBufferCur = 0;
1656 s->iIOBufferEnd = 0;
1657 s->uTxDir = PDMBLOCKTXDIR_NONE;
1658 s->iBeginTransfer = ATAFN_BT_NULL;
1659 s->iSourceSink = ATAFN_SS_NULL;
1660}
1661
1662
1663/** @todo deprecated function - doesn't provide enough info. Replace by direct
1664 * calls to atapiCmdError() with full data. */
1665static void atapiCmdErrorSimple(ATADevState *s, uint8_t uATAPISenseKey, uint8_t uATAPIASC)
1666{
1667 uint8_t abATAPISense[ATAPI_SENSE_SIZE];
1668 memset(abATAPISense, '\0', sizeof(abATAPISense));
1669 abATAPISense[0] = 0x70 | (1 << 7);
1670 abATAPISense[2] = uATAPISenseKey & 0x0f;
1671 abATAPISense[7] = 10;
1672 abATAPISense[12] = uATAPIASC;
1673 atapiCmdError(s, abATAPISense, sizeof(abATAPISense));
1674}
1675
1676
1677static void atapiCmdBT(ATADevState *s)
1678{
1679 s->fATAPITransfer = true;
1680 s->cbElementaryTransfer = s->cbTotalTransfer;
1681 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE)
1682 atapiCmdOK(s);
1683}
1684
1685
1686static void atapiPassthroughCmdBT(ATADevState *s)
1687{
1688 /* @todo implement an algorithm for correctly determining the read and
1689 * write sector size without sending additional commands to the drive.
1690 * This should be doable by saving processing the configuration requests
1691 * and replies. */
1692#if 0
1693 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE)
1694 {
1695 uint8_t cmd = s->aATAPICmd[0];
1696 if (cmd == SCSI_WRITE_10 || cmd == SCSI_WRITE_12 || cmd == SCSI_WRITE_AND_VERIFY_10)
1697 {
1698 uint8_t aModeSenseCmd[10];
1699 uint8_t aModeSenseResult[16];
1700 uint8_t uDummySense;
1701 uint32_t cbTransfer;
1702 int rc;
1703
1704 cbTransfer = sizeof(aModeSenseResult);
1705 aModeSenseCmd[0] = SCSI_MODE_SENSE_10;
1706 aModeSenseCmd[1] = 0x08; /* disable block descriptor = 1 */
1707 aModeSenseCmd[2] = (SCSI_PAGECONTROL_CURRENT << 6) | SCSI_MODEPAGE_WRITE_PARAMETER;
1708 aModeSenseCmd[3] = 0; /* subpage code */
1709 aModeSenseCmd[4] = 0; /* reserved */
1710 aModeSenseCmd[5] = 0; /* reserved */
1711 aModeSenseCmd[6] = 0; /* reserved */
1712 aModeSenseCmd[7] = cbTransfer >> 8;
1713 aModeSenseCmd[8] = cbTransfer & 0xff;
1714 aModeSenseCmd[9] = 0; /* control */
1715 rc = s->pDrvBlock->pfnSendCmd(s->pDrvBlock, aModeSenseCmd, PDMBLOCKTXDIR_FROM_DEVICE, aModeSenseResult, &cbTransfer, &uDummySense, 500);
1716 if (RT_FAILURE(rc))
1717 {
1718 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_NONE);
1719 return;
1720 }
1721 /* Select sector size based on the current data block type. */
1722 switch (aModeSenseResult[12] & 0x0f)
1723 {
1724 case 0:
1725 s->cbATAPISector = 2352;
1726 break;
1727 case 1:
1728 s->cbATAPISector = 2368;
1729 break;
1730 case 2:
1731 case 3:
1732 s->cbATAPISector = 2448;
1733 break;
1734 case 8:
1735 case 10:
1736 s->cbATAPISector = 2048;
1737 break;
1738 case 9:
1739 s->cbATAPISector = 2336;
1740 break;
1741 case 11:
1742 s->cbATAPISector = 2056;
1743 break;
1744 case 12:
1745 s->cbATAPISector = 2324;
1746 break;
1747 case 13:
1748 s->cbATAPISector = 2332;
1749 break;
1750 default:
1751 s->cbATAPISector = 0;
1752 }
1753 Log2(("%s: sector size %d\n", __FUNCTION__, s->cbATAPISector));
1754 s->cbTotalTransfer *= s->cbATAPISector;
1755 if (s->cbTotalTransfer == 0)
1756 s->uTxDir = PDMBLOCKTXDIR_NONE;
1757 }
1758 }
1759#endif
1760 atapiCmdBT(s);
1761}
1762
1763
1764static bool atapiReadSS(ATADevState *s)
1765{
1766 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1767 int rc = VINF_SUCCESS;
1768 uint32_t cbTransfer, cSectors;
1769
1770 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
1771 cbTransfer = RT_MIN(s->cbTotalTransfer, s->cbIOBuffer);
1772 cSectors = cbTransfer / s->cbATAPISector;
1773 Assert(cSectors * s->cbATAPISector <= cbTransfer);
1774 Log(("%s: %d sectors at LBA %d\n", __FUNCTION__, cSectors, s->iATAPILBA));
1775
1776 PDMCritSectLeave(&pCtl->lock);
1777
1778 STAM_PROFILE_ADV_START(&s->StatReads, r);
1779 s->Led.Asserted.s.fReading = s->Led.Actual.s.fReading = 1;
1780 switch (s->cbATAPISector)
1781 {
1782 case 2048:
1783 rc = s->pDrvBlock->pfnRead(s->pDrvBlock, (uint64_t)s->iATAPILBA * s->cbATAPISector, s->CTX_SUFF(pbIOBuffer), s->cbATAPISector * cSectors);
1784 break;
1785 case 2352:
1786 {
1787 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
1788
1789 for (uint32_t i = s->iATAPILBA; i < s->iATAPILBA + cSectors; i++)
1790 {
1791 /* Sync bytes, see 4.2.3.8 CD Main Channel Block Formats */
1792 *pbBuf++ = 0x00;
1793 memset(pbBuf, 0xff, 10);
1794 pbBuf += 10;
1795 *pbBuf++ = 0x00;
1796 /* MSF */
1797 ataLBA2MSF(pbBuf, i);
1798 pbBuf += 3;
1799 *pbBuf++ = 0x01; /* mode 1 data */
1800 /* data */
1801 rc = s->pDrvBlock->pfnRead(s->pDrvBlock, (uint64_t)i * 2048, pbBuf, 2048);
1802 if (RT_FAILURE(rc))
1803 break;
1804 pbBuf += 2048;
1805 /**
1806 * @todo: maybe compute ECC and parity, layout is:
1807 * 2072 4 EDC
1808 * 2076 172 P parity symbols
1809 * 2248 104 Q parity symbols
1810 */
1811 memset(pbBuf, 0, 280);
1812 pbBuf += 280;
1813 }
1814 }
1815 break;
1816 default:
1817 break;
1818 }
1819 STAM_PROFILE_ADV_STOP(&s->StatReads, r);
1820
1821 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1822 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1823 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1824
1825 if (RT_SUCCESS(rc))
1826 {
1827 s->Led.Actual.s.fReading = 0;
1828 STAM_REL_COUNTER_ADD(&s->StatBytesRead, s->cbATAPISector * cSectors);
1829
1830 /* The initial buffer end value has been set up based on the total
1831 * transfer size. But the I/O buffer size limits what can actually be
1832 * done in one transfer, so set the actual value of the buffer end. */
1833 s->cbElementaryTransfer = cbTransfer;
1834 if (cbTransfer >= s->cbTotalTransfer)
1835 s->iSourceSink = ATAFN_SS_NULL;
1836 atapiCmdOK(s);
1837 s->iATAPILBA += cSectors;
1838 }
1839 else
1840 {
1841 if (s->cErrors++ < MAX_LOG_REL_ERRORS)
1842 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM read error, %d sectors at LBA %d\n", s->iLUN, cSectors, s->iATAPILBA));
1843
1844 /*
1845 * Check if we got interrupted. We don't need to set status variables
1846 * because the request was aborted.
1847 */
1848 if (rc != VERR_INTERRUPTED)
1849 atapiCmdErrorSimple(s, SCSI_SENSE_MEDIUM_ERROR, SCSI_ASC_READ_ERROR);
1850 }
1851 return false;
1852}
1853
1854
1855static bool atapiPassthroughSS(ATADevState *s)
1856{
1857 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
1858 int rc = VINF_SUCCESS;
1859 uint8_t abATAPISense[ATAPI_SENSE_SIZE];
1860 uint32_t cbTransfer;
1861 PSTAMPROFILEADV pProf = NULL;
1862
1863 cbTransfer = s->cbElementaryTransfer;
1864
1865 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE)
1866 Log3(("ATAPI PT data write (%d): %.*Rhxs\n", cbTransfer, cbTransfer, s->CTX_SUFF(pbIOBuffer)));
1867
1868 /* Simple heuristics: if there is at least one sector of data
1869 * to transfer, it's worth updating the LEDs. */
1870 if (cbTransfer >= 2048)
1871 {
1872 if (s->uTxDir != PDMBLOCKTXDIR_TO_DEVICE)
1873 {
1874 s->Led.Asserted.s.fReading = s->Led.Actual.s.fReading = 1;
1875 pProf = &s->StatReads;
1876 }
1877 else
1878 {
1879 s->Led.Asserted.s.fWriting = s->Led.Actual.s.fWriting = 1;
1880 pProf = &s->StatWrites;
1881 }
1882 }
1883
1884 PDMCritSectLeave(&pCtl->lock);
1885
1886 if (pProf) { STAM_PROFILE_ADV_START(pProf, b); }
1887 if (cbTransfer > SCSI_MAX_BUFFER_SIZE)
1888 {
1889 /* Linux accepts commands with up to 100KB of data, but expects
1890 * us to handle commands with up to 128KB of data. The usual
1891 * imbalance of powers. */
1892 uint8_t aATAPICmd[ATAPI_PACKET_SIZE];
1893 uint32_t iATAPILBA, cSectors, cReqSectors, cbCurrTX;
1894 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
1895
1896 switch (s->aATAPICmd[0])
1897 {
1898 case SCSI_READ_10:
1899 case SCSI_WRITE_10:
1900 case SCSI_WRITE_AND_VERIFY_10:
1901 iATAPILBA = ataBE2H_U32(s->aATAPICmd + 2);
1902 cSectors = ataBE2H_U16(s->aATAPICmd + 7);
1903 break;
1904 case SCSI_READ_12:
1905 case SCSI_WRITE_12:
1906 iATAPILBA = ataBE2H_U32(s->aATAPICmd + 2);
1907 cSectors = ataBE2H_U32(s->aATAPICmd + 6);
1908 break;
1909 case SCSI_READ_CD:
1910 iATAPILBA = ataBE2H_U32(s->aATAPICmd + 2);
1911 cSectors = ataBE2H_U24(s->aATAPICmd + 6) / s->cbATAPISector;
1912 break;
1913 case SCSI_READ_CD_MSF:
1914 iATAPILBA = ataMSF2LBA(s->aATAPICmd + 3);
1915 cSectors = ataMSF2LBA(s->aATAPICmd + 6) - iATAPILBA;
1916 break;
1917 default:
1918 AssertMsgFailed(("Don't know how to split command %#04x\n", s->aATAPICmd[0]));
1919 if (s->cErrors++ < MAX_LOG_REL_ERRORS)
1920 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM passthrough split error\n", s->iLUN));
1921 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_ILLEGAL_OPCODE);
1922 {
1923 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1924 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1925 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1926 }
1927 return false;
1928 }
1929 memcpy(aATAPICmd, s->aATAPICmd, ATAPI_PACKET_SIZE);
1930 cReqSectors = 0;
1931 for (uint32_t i = cSectors; i > 0; i -= cReqSectors)
1932 {
1933 if (i * s->cbATAPISector > SCSI_MAX_BUFFER_SIZE)
1934 cReqSectors = SCSI_MAX_BUFFER_SIZE / s->cbATAPISector;
1935 else
1936 cReqSectors = i;
1937 cbCurrTX = s->cbATAPISector * cReqSectors;
1938 switch (s->aATAPICmd[0])
1939 {
1940 case SCSI_READ_10:
1941 case SCSI_WRITE_10:
1942 case SCSI_WRITE_AND_VERIFY_10:
1943 ataH2BE_U32(aATAPICmd + 2, iATAPILBA);
1944 ataH2BE_U16(aATAPICmd + 7, cReqSectors);
1945 break;
1946 case SCSI_READ_12:
1947 case SCSI_WRITE_12:
1948 ataH2BE_U32(aATAPICmd + 2, iATAPILBA);
1949 ataH2BE_U32(aATAPICmd + 6, cReqSectors);
1950 break;
1951 case SCSI_READ_CD:
1952 ataH2BE_U32(s->aATAPICmd + 2, iATAPILBA);
1953 ataH2BE_U24(s->aATAPICmd + 6, cbCurrTX);
1954 break;
1955 case SCSI_READ_CD_MSF:
1956 ataLBA2MSF(aATAPICmd + 3, iATAPILBA);
1957 ataLBA2MSF(aATAPICmd + 6, iATAPILBA + cReqSectors);
1958 break;
1959 }
1960 rc = s->pDrvBlock->pfnSendCmd(s->pDrvBlock, aATAPICmd, (PDMBLOCKTXDIR)s->uTxDir, pbBuf, &cbCurrTX, abATAPISense, sizeof(abATAPISense), 30000 /**< @todo timeout */);
1961 if (rc != VINF_SUCCESS)
1962 break;
1963 iATAPILBA += cReqSectors;
1964 pbBuf += s->cbATAPISector * cReqSectors;
1965 }
1966 }
1967 else
1968 rc = s->pDrvBlock->pfnSendCmd(s->pDrvBlock, s->aATAPICmd, (PDMBLOCKTXDIR)s->uTxDir, s->CTX_SUFF(pbIOBuffer), &cbTransfer, abATAPISense, sizeof(abATAPISense), 30000 /**< @todo timeout */);
1969 if (pProf) { STAM_PROFILE_ADV_STOP(pProf, b); }
1970
1971 STAM_PROFILE_START(&pCtl->StatLockWait, a);
1972 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
1973 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
1974
1975 /* Update the LEDs and the read/write statistics. */
1976 if (cbTransfer >= 2048)
1977 {
1978 if (s->uTxDir != PDMBLOCKTXDIR_TO_DEVICE)
1979 {
1980 s->Led.Actual.s.fReading = 0;
1981 STAM_REL_COUNTER_ADD(&s->StatBytesRead, cbTransfer);
1982 }
1983 else
1984 {
1985 s->Led.Actual.s.fWriting = 0;
1986 STAM_REL_COUNTER_ADD(&s->StatBytesWritten, cbTransfer);
1987 }
1988 }
1989
1990 if (RT_SUCCESS(rc))
1991 {
1992 if (s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE)
1993 {
1994 Assert(cbTransfer <= s->cbTotalTransfer);
1995 /* Reply with the same amount of data as the real drive. */
1996 s->cbTotalTransfer = cbTransfer;
1997 /* The initial buffer end value has been set up based on the total
1998 * transfer size. But the I/O buffer size limits what can actually be
1999 * done in one transfer, so set the actual value of the buffer end. */
2000 s->cbElementaryTransfer = cbTransfer;
2001 if (s->aATAPICmd[0] == SCSI_INQUIRY)
2002 {
2003 /* Make sure that the real drive cannot be identified.
2004 * Motivation: changing the VM configuration should be as
2005 * invisible as possible to the guest. */
2006 Log3(("ATAPI PT inquiry data before (%d): %.*Rhxs\n", cbTransfer, cbTransfer, s->CTX_SUFF(pbIOBuffer)));
2007 ataSCSIPadStr(s->CTX_SUFF(pbIOBuffer) + 8, "VBOX", 8);
2008 ataSCSIPadStr(s->CTX_SUFF(pbIOBuffer) + 16, "CD-ROM", 16);
2009 ataSCSIPadStr(s->CTX_SUFF(pbIOBuffer) + 32, "1.0", 4);
2010 }
2011 if (cbTransfer)
2012 Log3(("ATAPI PT data read (%d): %.*Rhxs\n", cbTransfer, cbTransfer, s->CTX_SUFF(pbIOBuffer)));
2013 }
2014 s->iSourceSink = ATAFN_SS_NULL;
2015 atapiCmdOK(s);
2016 }
2017 else
2018 {
2019 if (s->cErrors < MAX_LOG_REL_ERRORS)
2020 {
2021 uint8_t u8Cmd = s->aATAPICmd[0];
2022 do
2023 {
2024 /* don't log superflous errors */
2025 if ( rc == VERR_DEV_IO_ERROR
2026 && ( u8Cmd == SCSI_TEST_UNIT_READY
2027 || u8Cmd == SCSI_READ_CAPACITY
2028 || u8Cmd == SCSI_READ_DVD_STRUCTURE
2029 || u8Cmd == SCSI_READ_TOC_PMA_ATIP))
2030 break;
2031 s->cErrors++;
2032 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM passthrough cmd=%#04x sense=%d ASC=%#02x ASCQ=%#02x %Rrc\n",
2033 s->iLUN, u8Cmd, abATAPISense[2] & 0x0f, abATAPISense[12], abATAPISense[13], rc));
2034 } while (0);
2035 }
2036 atapiCmdError(s, abATAPISense, sizeof(abATAPISense));
2037 }
2038 return false;
2039}
2040
2041/** @todo: Revise ASAP. */
2042static bool atapiReadDVDStructureSS(ATADevState *s)
2043{
2044 uint8_t *buf = s->CTX_SUFF(pbIOBuffer);
2045 int media = s->aATAPICmd[1];
2046 int format = s->aATAPICmd[7];
2047
2048 uint16_t max_len = ataBE2H_U16(&s->aATAPICmd[8]);
2049
2050 memset(buf, 0, max_len);
2051
2052 switch (format) {
2053 case 0x00:
2054 case 0x01:
2055 case 0x02:
2056 case 0x03:
2057 case 0x04:
2058 case 0x05:
2059 case 0x06:
2060 case 0x07:
2061 case 0x08:
2062 case 0x09:
2063 case 0x0a:
2064 case 0x0b:
2065 case 0x0c:
2066 case 0x0d:
2067 case 0x0e:
2068 case 0x0f:
2069 case 0x10:
2070 case 0x11:
2071 case 0x30:
2072 case 0x31:
2073 case 0xff:
2074 if (media == 0)
2075 {
2076 int uASC = SCSI_ASC_NONE;
2077
2078 switch (format)
2079 {
2080 case 0x0: /* Physical format information */
2081 {
2082 int layer = s->aATAPICmd[6];
2083 uint64_t total_sectors;
2084
2085 if (layer != 0)
2086 {
2087 uASC = -SCSI_ASC_INV_FIELD_IN_CMD_PACKET;
2088 break;
2089 }
2090
2091 total_sectors = s->cTotalSectors;
2092 total_sectors >>= 2;
2093 if (total_sectors == 0)
2094 {
2095 uASC = -SCSI_ASC_MEDIUM_NOT_PRESENT;
2096 break;
2097 }
2098
2099 buf[4] = 1; /* DVD-ROM, part version 1 */
2100 buf[5] = 0xf; /* 120mm disc, minimum rate unspecified */
2101 buf[6] = 1; /* one layer, read-only (per MMC-2 spec) */
2102 buf[7] = 0; /* default densities */
2103
2104 /* FIXME: 0x30000 per spec? */
2105 ataH2BE_U32(buf + 8, 0); /* start sector */
2106 ataH2BE_U32(buf + 12, total_sectors - 1); /* end sector */
2107 ataH2BE_U32(buf + 16, total_sectors - 1); /* l0 end sector */
2108
2109 /* Size of buffer, not including 2 byte size field */
2110 ataH2BE_U32(&buf[0], 2048 + 2);
2111
2112 /* 2k data + 4 byte header */
2113 uASC = (2048 + 4);
2114 }
2115 break;
2116 case 0x01: /* DVD copyright information */
2117 buf[4] = 0; /* no copyright data */
2118 buf[5] = 0; /* no region restrictions */
2119
2120 /* Size of buffer, not including 2 byte size field */
2121 ataH2BE_U16(buf, 4 + 2);
2122
2123 /* 4 byte header + 4 byte data */
2124 uASC = (4 + 4);
2125
2126 case 0x03: /* BCA information - invalid field for no BCA info */
2127 uASC = -SCSI_ASC_INV_FIELD_IN_CMD_PACKET;
2128 break;
2129
2130 case 0x04: /* DVD disc manufacturing information */
2131 /* Size of buffer, not including 2 byte size field */
2132 ataH2BE_U16(buf, 2048 + 2);
2133
2134 /* 2k data + 4 byte header */
2135 uASC = (2048 + 4);
2136 break;
2137 case 0xff:
2138 /*
2139 * This lists all the command capabilities above. Add new ones
2140 * in order and update the length and buffer return values.
2141 */
2142
2143 buf[4] = 0x00; /* Physical format */
2144 buf[5] = 0x40; /* Not writable, is readable */
2145 ataH2BE_U16((buf + 6), 2048 + 4);
2146
2147 buf[8] = 0x01; /* Copyright info */
2148 buf[9] = 0x40; /* Not writable, is readable */
2149 ataH2BE_U16((buf + 10), 4 + 4);
2150
2151 buf[12] = 0x03; /* BCA info */
2152 buf[13] = 0x40; /* Not writable, is readable */
2153 ataH2BE_U16((buf + 14), 188 + 4);
2154
2155 buf[16] = 0x04; /* Manufacturing info */
2156 buf[17] = 0x40; /* Not writable, is readable */
2157 ataH2BE_U16((buf + 18), 2048 + 4);
2158
2159 /* Size of buffer, not including 2 byte size field */
2160 ataH2BE_U16(buf, 16 + 2);
2161
2162 /* data written + 4 byte header */
2163 uASC = (16 + 4);
2164 break;
2165 default: /* TODO: formats beyond DVD-ROM requires */
2166 uASC = -SCSI_ASC_INV_FIELD_IN_CMD_PACKET;
2167 }
2168
2169 if (uASC < 0)
2170 {
2171 s->iSourceSink = ATAFN_SS_NULL;
2172 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, -uASC);
2173 return false;
2174 }
2175 break;
2176 }
2177 /* TODO: BD support, fall through for now */
2178
2179 /* Generic disk structures */
2180 case 0x80: /* TODO: AACS volume identifier */
2181 case 0x81: /* TODO: AACS media serial number */
2182 case 0x82: /* TODO: AACS media identifier */
2183 case 0x83: /* TODO: AACS media key block */
2184 case 0x90: /* TODO: List of recognized format layers */
2185 case 0xc0: /* TODO: Write protection status */
2186 default:
2187 s->iSourceSink = ATAFN_SS_NULL;
2188 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST,
2189 SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2190 return false;
2191 }
2192
2193 s->iSourceSink = ATAFN_SS_NULL;
2194 atapiCmdOK(s);
2195 return false;
2196}
2197
2198static bool atapiReadSectors(ATADevState *s, uint32_t iATAPILBA, uint32_t cSectors, uint32_t cbSector)
2199{
2200 Assert(cSectors > 0);
2201 s->iATAPILBA = iATAPILBA;
2202 s->cbATAPISector = cbSector;
2203 ataStartTransfer(s, cSectors * cbSector, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ, true);
2204 return false;
2205}
2206
2207
2208static bool atapiReadCapacitySS(ATADevState *s)
2209{
2210 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2211
2212 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2213 Assert(s->cbElementaryTransfer <= 8);
2214 ataH2BE_U32(pbBuf, s->cTotalSectors - 1);
2215 ataH2BE_U32(pbBuf + 4, 2048);
2216 s->iSourceSink = ATAFN_SS_NULL;
2217 atapiCmdOK(s);
2218 return false;
2219}
2220
2221
2222static bool atapiReadDiscInformationSS(ATADevState *s)
2223{
2224 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2225
2226 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2227 Assert(s->cbElementaryTransfer <= 34);
2228 memset(pbBuf, '\0', 34);
2229 ataH2BE_U16(pbBuf, 32);
2230 pbBuf[2] = (0 << 4) | (3 << 2) | (2 << 0); /* not erasable, complete session, complete disc */
2231 pbBuf[3] = 1; /* number of first track */
2232 pbBuf[4] = 1; /* number of sessions (LSB) */
2233 pbBuf[5] = 1; /* first track number in last session (LSB) */
2234 pbBuf[6] = 1; /* last track number in last session (LSB) */
2235 pbBuf[7] = (0 << 7) | (0 << 6) | (1 << 5) | (0 << 2) | (0 << 0); /* disc id not valid, disc bar code not valid, unrestricted use, not dirty, not RW medium */
2236 pbBuf[8] = 0; /* disc type = CD-ROM */
2237 pbBuf[9] = 0; /* number of sessions (MSB) */
2238 pbBuf[10] = 0; /* number of sessions (MSB) */
2239 pbBuf[11] = 0; /* number of sessions (MSB) */
2240 ataH2BE_U32(pbBuf + 16, 0x00ffffff); /* last session lead-in start time is not available */
2241 ataH2BE_U32(pbBuf + 20, 0x00ffffff); /* last possible start time for lead-out is not available */
2242 s->iSourceSink = ATAFN_SS_NULL;
2243 atapiCmdOK(s);
2244 return false;
2245}
2246
2247
2248static bool atapiReadTrackInformationSS(ATADevState *s)
2249{
2250 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2251
2252 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2253 Assert(s->cbElementaryTransfer <= 36);
2254 /* Accept address/number type of 1 only, and only track 1 exists. */
2255 if ((s->aATAPICmd[1] & 0x03) != 1 || ataBE2H_U32(&s->aATAPICmd[2]) != 1)
2256 {
2257 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2258 return false;
2259 }
2260 memset(pbBuf, '\0', 36);
2261 ataH2BE_U16(pbBuf, 34);
2262 pbBuf[2] = 1; /* track number (LSB) */
2263 pbBuf[3] = 1; /* session number (LSB) */
2264 pbBuf[5] = (0 << 5) | (0 << 4) | (4 << 0); /* not damaged, primary copy, data track */
2265 pbBuf[6] = (0 << 7) | (0 << 6) | (0 << 5) | (0 << 6) | (1 << 0); /* not reserved track, not blank, not packet writing, not fixed packet, data mode 1 */
2266 pbBuf[7] = (0 << 1) | (0 << 0); /* last recorded address not valid, next recordable address not valid */
2267 ataH2BE_U32(pbBuf + 8, 0); /* track start address is 0 */
2268 ataH2BE_U32(pbBuf + 24, s->cTotalSectors); /* track size */
2269 pbBuf[32] = 0; /* track number (MSB) */
2270 pbBuf[33] = 0; /* session number (MSB) */
2271 s->iSourceSink = ATAFN_SS_NULL;
2272 atapiCmdOK(s);
2273 return false;
2274}
2275
2276
2277static bool atapiGetConfigurationSS(ATADevState *s)
2278{
2279 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2280 uint16_t u16Sfn = ataBE2H_U16(&s->aATAPICmd[2]);
2281
2282 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2283 Assert(s->cbElementaryTransfer <= 32);
2284 /* Accept valid request types only, and only starting feature 0. */
2285 if ((s->aATAPICmd[1] & 0x03) == 3 || u16Sfn != 0)
2286 {
2287 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2288 return false;
2289 }
2290 memset(pbBuf, '\0', 32);
2291 ataH2BE_U32(pbBuf, 16);
2292 /** @todo implement switching between CD-ROM and DVD-ROM profile (the only
2293 * way to differentiate them right now is based on the image size). Also
2294 * implement signalling "no current profile" if no medium is loaded. */
2295 ataH2BE_U16(pbBuf + 6, 0x08); /* current profile: read-only CD */
2296
2297 ataH2BE_U16(pbBuf + 8, 0); /* feature 0: list of profiles supported */
2298 pbBuf[10] = (0 << 2) | (1 << 1) | (1 || 0); /* version 0, persistent, current */
2299 pbBuf[11] = 8; /* additional bytes for profiles */
2300 /* The MMC-3 spec says that DVD-ROM read capability should be reported
2301 * before CD-ROM read capability. */
2302 ataH2BE_U16(pbBuf + 12, 0x10); /* profile: read-only DVD */
2303 pbBuf[14] = (0 << 0); /* NOT current profile */
2304 ataH2BE_U16(pbBuf + 16, 0x08); /* profile: read only CD */
2305 pbBuf[18] = (1 << 0); /* current profile */
2306 /* Other profiles we might want to add in the future: 0x40 (BD-ROM) and 0x50 (HDDVD-ROM) */
2307 s->iSourceSink = ATAFN_SS_NULL;
2308 atapiCmdOK(s);
2309 return false;
2310}
2311
2312
2313static bool atapiGetEventStatusNotificationSS(ATADevState *s)
2314{
2315 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2316
2317 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2318 Assert(s->cbElementaryTransfer <= 8);
2319
2320 if (!(s->aATAPICmd[1] & 1))
2321 {
2322 /* no asynchronous operation supported */
2323 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2324 return false;
2325 }
2326
2327 uint32_t OldStatus, NewStatus;
2328 do
2329 {
2330 OldStatus = ASMAtomicReadU32(&s->MediaEventStatus);
2331 NewStatus = ATA_EVENT_STATUS_UNCHANGED;
2332 switch (OldStatus)
2333 {
2334 case ATA_EVENT_STATUS_MEDIA_NEW:
2335 /* mount */
2336 ataH2BE_U16(pbBuf + 0, 6);
2337 pbBuf[2] = 0x04;
2338 pbBuf[3] = 0x5e;
2339 pbBuf[4] = 0x02;
2340 pbBuf[5] = 0x02;
2341 pbBuf[6] = 0x00;
2342 pbBuf[7] = 0x00;
2343 break;
2344
2345 case ATA_EVENT_STATUS_MEDIA_CHANGED:
2346 case ATA_EVENT_STATUS_MEDIA_REMOVED:
2347 /* umount */
2348 ataH2BE_U16(pbBuf + 0, 6);
2349 pbBuf[2] = 0x04;
2350 pbBuf[3] = 0x5e;
2351 pbBuf[4] = 0x03;
2352 pbBuf[5] = 0x00;
2353 pbBuf[6] = 0x00;
2354 pbBuf[7] = 0x00;
2355 if (OldStatus == ATA_EVENT_STATUS_MEDIA_CHANGED)
2356 NewStatus = ATA_EVENT_STATUS_MEDIA_NEW;
2357 break;
2358
2359 case ATA_EVENT_STATUS_UNCHANGED:
2360 default:
2361 ataH2BE_U16(pbBuf + 0, 6);
2362 pbBuf[2] = 0x01;
2363 pbBuf[3] = 0x5e;
2364 pbBuf[4] = 0x00;
2365 pbBuf[5] = 0x00;
2366 pbBuf[6] = 0x00;
2367 pbBuf[7] = 0x00;
2368 break;
2369 }
2370 } while (!ASMAtomicCmpXchgU32(&s->MediaEventStatus, NewStatus, OldStatus));
2371
2372 s->iSourceSink = ATAFN_SS_NULL;
2373 atapiCmdOK(s);
2374 return false;
2375}
2376
2377
2378static bool atapiInquirySS(ATADevState *s)
2379{
2380 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2381
2382 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2383 Assert(s->cbElementaryTransfer <= 36);
2384 pbBuf[0] = 0x05; /* CD-ROM */
2385 pbBuf[1] = 0x80; /* removable */
2386#if 1/*ndef VBOX*/ /** @todo implement MESN + AENC. (async notification on removal and stuff.) */
2387 pbBuf[2] = 0x00; /* ISO */
2388 pbBuf[3] = 0x21; /* ATAPI-2 (XXX: put ATAPI-4 ?) */
2389#else
2390 pbBuf[2] = 0x00; /* ISO */
2391 pbBuf[3] = 0x91; /* format 1, MESN=1, AENC=9 ??? */
2392#endif
2393 pbBuf[4] = 31; /* additional length */
2394 pbBuf[5] = 0; /* reserved */
2395 pbBuf[6] = 0; /* reserved */
2396 pbBuf[7] = 0; /* reserved */
2397 ataSCSIPadStr(pbBuf + 8, s->szInquiryVendorId, 8);
2398 ataSCSIPadStr(pbBuf + 16, s->szInquiryProductId, 16);
2399 ataSCSIPadStr(pbBuf + 32, s->szInquiryRevision, 4);
2400 s->iSourceSink = ATAFN_SS_NULL;
2401 atapiCmdOK(s);
2402 return false;
2403}
2404
2405
2406static bool atapiModeSenseErrorRecoverySS(ATADevState *s)
2407{
2408 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2409
2410 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2411 Assert(s->cbElementaryTransfer <= 16);
2412 ataH2BE_U16(&pbBuf[0], 16 + 6);
2413 pbBuf[2] = 0x70;
2414 pbBuf[3] = 0;
2415 pbBuf[4] = 0;
2416 pbBuf[5] = 0;
2417 pbBuf[6] = 0;
2418 pbBuf[7] = 0;
2419
2420 pbBuf[8] = 0x01;
2421 pbBuf[9] = 0x06;
2422 pbBuf[10] = 0x00;
2423 pbBuf[11] = 0x05;
2424 pbBuf[12] = 0x00;
2425 pbBuf[13] = 0x00;
2426 pbBuf[14] = 0x00;
2427 pbBuf[15] = 0x00;
2428 s->iSourceSink = ATAFN_SS_NULL;
2429 atapiCmdOK(s);
2430 return false;
2431}
2432
2433
2434static bool atapiModeSenseCDStatusSS(ATADevState *s)
2435{
2436 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2437
2438 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2439 Assert(s->cbElementaryTransfer <= 40);
2440 ataH2BE_U16(&pbBuf[0], 38);
2441 pbBuf[2] = 0x70;
2442 pbBuf[3] = 0;
2443 pbBuf[4] = 0;
2444 pbBuf[5] = 0;
2445 pbBuf[6] = 0;
2446 pbBuf[7] = 0;
2447
2448 pbBuf[8] = 0x2a;
2449 pbBuf[9] = 30; /* page length */
2450 pbBuf[10] = 0x08; /* DVD-ROM read support */
2451 pbBuf[11] = 0x00; /* no write support */
2452 /* The following claims we support audio play. This is obviously false,
2453 * but the Linux generic CDROM support makes many features depend on this
2454 * capability. If it's not set, this causes many things to be disabled. */
2455 pbBuf[12] = 0x71; /* multisession support, mode 2 form 1/2 support, audio play */
2456 pbBuf[13] = 0x00; /* no subchannel reads supported */
2457 pbBuf[14] = (1 << 0) | (1 << 3) | (1 << 5); /* lock supported, eject supported, tray type loading mechanism */
2458 if (s->pDrvMount->pfnIsLocked(s->pDrvMount))
2459 pbBuf[14] |= 1 << 1; /* report lock state */
2460 pbBuf[15] = 0; /* no subchannel reads supported, no separate audio volume control, no changer etc. */
2461 ataH2BE_U16(&pbBuf[16], 5632); /* (obsolete) claim 32x speed support */
2462 ataH2BE_U16(&pbBuf[18], 2); /* number of audio volume levels */
2463 ataH2BE_U16(&pbBuf[20], s->cbIOBuffer / _1K); /* buffer size supported in Kbyte */
2464 ataH2BE_U16(&pbBuf[22], 5632); /* (obsolete) current read speed 32x */
2465 pbBuf[24] = 0; /* reserved */
2466 pbBuf[25] = 0; /* reserved for digital audio (see idx 15) */
2467 ataH2BE_U16(&pbBuf[26], 0); /* (obsolete) maximum write speed */
2468 ataH2BE_U16(&pbBuf[28], 0); /* (obsolete) current write speed */
2469 ataH2BE_U16(&pbBuf[30], 0); /* copy management revision supported 0=no CSS */
2470 pbBuf[32] = 0; /* reserved */
2471 pbBuf[33] = 0; /* reserved */
2472 pbBuf[34] = 0; /* reserved */
2473 pbBuf[35] = 1; /* rotation control CAV */
2474 ataH2BE_U16(&pbBuf[36], 0); /* current write speed */
2475 ataH2BE_U16(&pbBuf[38], 0); /* number of write speed performance descriptors */
2476 s->iSourceSink = ATAFN_SS_NULL;
2477 atapiCmdOK(s);
2478 return false;
2479}
2480
2481
2482static bool atapiRequestSenseSS(ATADevState *s)
2483{
2484 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2485
2486 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2487 memset(pbBuf, '\0', s->cbElementaryTransfer);
2488 memcpy(pbBuf, s->abATAPISense, RT_MIN(s->cbElementaryTransfer, sizeof(s->abATAPISense)));
2489 s->iSourceSink = ATAFN_SS_NULL;
2490 atapiCmdOK(s);
2491 return false;
2492}
2493
2494
2495static bool atapiMechanismStatusSS(ATADevState *s)
2496{
2497 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2498
2499 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2500 Assert(s->cbElementaryTransfer <= 8);
2501 ataH2BE_U16(pbBuf, 0);
2502 /* no current LBA */
2503 pbBuf[2] = 0;
2504 pbBuf[3] = 0;
2505 pbBuf[4] = 0;
2506 pbBuf[5] = 1;
2507 ataH2BE_U16(pbBuf + 6, 0);
2508 s->iSourceSink = ATAFN_SS_NULL;
2509 atapiCmdOK(s);
2510 return false;
2511}
2512
2513
2514static bool atapiReadTOCNormalSS(ATADevState *s)
2515{
2516 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer), *q, iStartTrack;
2517 bool fMSF;
2518 uint32_t cbSize;
2519
2520 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2521 fMSF = (s->aATAPICmd[1] >> 1) & 1;
2522 iStartTrack = s->aATAPICmd[6];
2523 if (iStartTrack > 1 && iStartTrack != 0xaa)
2524 {
2525 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2526 return false;
2527 }
2528 q = pbBuf + 2;
2529 *q++ = 1; /* first session */
2530 *q++ = 1; /* last session */
2531 if (iStartTrack <= 1)
2532 {
2533 *q++ = 0; /* reserved */
2534 *q++ = 0x14; /* ADR, control */
2535 *q++ = 1; /* track number */
2536 *q++ = 0; /* reserved */
2537 if (fMSF)
2538 {
2539 *q++ = 0; /* reserved */
2540 ataLBA2MSF(q, 0);
2541 q += 3;
2542 }
2543 else
2544 {
2545 /* sector 0 */
2546 ataH2BE_U32(q, 0);
2547 q += 4;
2548 }
2549 }
2550 /* lead out track */
2551 *q++ = 0; /* reserved */
2552 *q++ = 0x14; /* ADR, control */
2553 *q++ = 0xaa; /* track number */
2554 *q++ = 0; /* reserved */
2555 if (fMSF)
2556 {
2557 *q++ = 0; /* reserved */
2558 ataLBA2MSF(q, s->cTotalSectors);
2559 q += 3;
2560 }
2561 else
2562 {
2563 ataH2BE_U32(q, s->cTotalSectors);
2564 q += 4;
2565 }
2566 cbSize = q - pbBuf;
2567 ataH2BE_U16(pbBuf, cbSize - 2);
2568 if (cbSize < s->cbTotalTransfer)
2569 s->cbTotalTransfer = cbSize;
2570 s->iSourceSink = ATAFN_SS_NULL;
2571 atapiCmdOK(s);
2572 return false;
2573}
2574
2575
2576static bool atapiReadTOCMultiSS(ATADevState *s)
2577{
2578 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer);
2579 bool fMSF;
2580
2581 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2582 Assert(s->cbElementaryTransfer <= 12);
2583 fMSF = (s->aATAPICmd[1] >> 1) & 1;
2584 /* multi session: only a single session defined */
2585/** @todo double-check this stuff against what a real drive says for a CD-ROM (not a CD-R) with only a single data session. Maybe solve the problem with "cdrdao read-toc" not being able to figure out whether numbers are in BCD or hex. */
2586 memset(pbBuf, 0, 12);
2587 pbBuf[1] = 0x0a;
2588 pbBuf[2] = 0x01;
2589 pbBuf[3] = 0x01;
2590 pbBuf[5] = 0x14; /* ADR, control */
2591 pbBuf[6] = 1; /* first track in last complete session */
2592 if (fMSF)
2593 {
2594 pbBuf[8] = 0; /* reserved */
2595 ataLBA2MSF(&pbBuf[9], 0);
2596 }
2597 else
2598 {
2599 /* sector 0 */
2600 ataH2BE_U32(pbBuf + 8, 0);
2601 }
2602 s->iSourceSink = ATAFN_SS_NULL;
2603 atapiCmdOK(s);
2604 return false;
2605}
2606
2607
2608static bool atapiReadTOCRawSS(ATADevState *s)
2609{
2610 uint8_t *pbBuf = s->CTX_SUFF(pbIOBuffer), *q, iStartTrack;
2611 bool fMSF;
2612 uint32_t cbSize;
2613
2614 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
2615 fMSF = (s->aATAPICmd[1] >> 1) & 1;
2616 iStartTrack = s->aATAPICmd[6];
2617
2618 q = pbBuf + 2;
2619 *q++ = 1; /* first session */
2620 *q++ = 1; /* last session */
2621
2622 *q++ = 1; /* session number */
2623 *q++ = 0x14; /* data track */
2624 *q++ = 0; /* track number */
2625 *q++ = 0xa0; /* first track in program area */
2626 *q++ = 0; /* min */
2627 *q++ = 0; /* sec */
2628 *q++ = 0; /* frame */
2629 *q++ = 0;
2630 *q++ = 1; /* first track */
2631 *q++ = 0x00; /* disk type CD-DA or CD data */
2632 *q++ = 0;
2633
2634 *q++ = 1; /* session number */
2635 *q++ = 0x14; /* data track */
2636 *q++ = 0; /* track number */
2637 *q++ = 0xa1; /* last track in program area */
2638 *q++ = 0; /* min */
2639 *q++ = 0; /* sec */
2640 *q++ = 0; /* frame */
2641 *q++ = 0;
2642 *q++ = 1; /* last track */
2643 *q++ = 0;
2644 *q++ = 0;
2645
2646 *q++ = 1; /* session number */
2647 *q++ = 0x14; /* data track */
2648 *q++ = 0; /* track number */
2649 *q++ = 0xa2; /* lead-out */
2650 *q++ = 0; /* min */
2651 *q++ = 0; /* sec */
2652 *q++ = 0; /* frame */
2653 if (fMSF)
2654 {
2655 *q++ = 0; /* reserved */
2656 ataLBA2MSF(q, s->cTotalSectors);
2657 q += 3;
2658 }
2659 else
2660 {
2661 ataH2BE_U32(q, s->cTotalSectors);
2662 q += 4;
2663 }
2664
2665 *q++ = 1; /* session number */
2666 *q++ = 0x14; /* ADR, control */
2667 *q++ = 0; /* track number */
2668 *q++ = 1; /* point */
2669 *q++ = 0; /* min */
2670 *q++ = 0; /* sec */
2671 *q++ = 0; /* frame */
2672 if (fMSF)
2673 {
2674 *q++ = 0; /* reserved */
2675 ataLBA2MSF(q, 0);
2676 q += 3;
2677 }
2678 else
2679 {
2680 /* sector 0 */
2681 ataH2BE_U32(q, 0);
2682 q += 4;
2683 }
2684
2685 cbSize = q - pbBuf;
2686 ataH2BE_U16(pbBuf, cbSize - 2);
2687 if (cbSize < s->cbTotalTransfer)
2688 s->cbTotalTransfer = cbSize;
2689 s->iSourceSink = ATAFN_SS_NULL;
2690 atapiCmdOK(s);
2691 return false;
2692}
2693
2694
2695static void atapiParseCmdVirtualATAPI(ATADevState *s)
2696{
2697 const uint8_t *pbPacket;
2698 uint8_t *pbBuf;
2699 uint32_t cbMax;
2700
2701 pbPacket = s->aATAPICmd;
2702 pbBuf = s->CTX_SUFF(pbIOBuffer);
2703 switch (pbPacket[0])
2704 {
2705 case SCSI_TEST_UNIT_READY:
2706 if (s->cNotifiedMediaChange > 0)
2707 {
2708 if (s->cNotifiedMediaChange-- > 2)
2709 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2710 else
2711 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2712 }
2713 else if (s->pDrvMount->pfnIsMounted(s->pDrvMount))
2714 atapiCmdOK(s);
2715 else
2716 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2717 break;
2718 case SCSI_GET_EVENT_STATUS_NOTIFICATION:
2719 cbMax = ataBE2H_U16(pbPacket + 7);
2720 ataStartTransfer(s, RT_MIN(cbMax, 8), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_GET_EVENT_STATUS_NOTIFICATION, true);
2721 break;
2722 case SCSI_MODE_SENSE_10:
2723 {
2724 uint8_t uPageControl, uPageCode;
2725 cbMax = ataBE2H_U16(pbPacket + 7);
2726 uPageControl = pbPacket[2] >> 6;
2727 uPageCode = pbPacket[2] & 0x3f;
2728 switch (uPageControl)
2729 {
2730 case SCSI_PAGECONTROL_CURRENT:
2731 switch (uPageCode)
2732 {
2733 case SCSI_MODEPAGE_ERROR_RECOVERY:
2734 ataStartTransfer(s, RT_MIN(cbMax, 16), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_MODE_SENSE_ERROR_RECOVERY, true);
2735 break;
2736 case SCSI_MODEPAGE_CD_STATUS:
2737 ataStartTransfer(s, RT_MIN(cbMax, 40), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_MODE_SENSE_CD_STATUS, true);
2738 break;
2739 default:
2740 goto error_cmd;
2741 }
2742 break;
2743 case SCSI_PAGECONTROL_CHANGEABLE:
2744 goto error_cmd;
2745 case SCSI_PAGECONTROL_DEFAULT:
2746 goto error_cmd;
2747 default:
2748 case SCSI_PAGECONTROL_SAVED:
2749 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_SAVING_PARAMETERS_NOT_SUPPORTED);
2750 break;
2751 }
2752 }
2753 break;
2754 case SCSI_REQUEST_SENSE:
2755 cbMax = pbPacket[4];
2756 ataStartTransfer(s, RT_MIN(cbMax, 18), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_REQUEST_SENSE, true);
2757 break;
2758 case SCSI_PREVENT_ALLOW_MEDIUM_REMOVAL:
2759 if (s->pDrvMount->pfnIsMounted(s->pDrvMount))
2760 {
2761 if (pbPacket[4] & 1)
2762 s->pDrvMount->pfnLock(s->pDrvMount);
2763 else
2764 s->pDrvMount->pfnUnlock(s->pDrvMount);
2765 atapiCmdOK(s);
2766 }
2767 else
2768 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2769 break;
2770 case SCSI_READ_10:
2771 case SCSI_READ_12:
2772 {
2773 uint32_t cSectors, iATAPILBA;
2774
2775 if (s->cNotifiedMediaChange > 0)
2776 {
2777 s->cNotifiedMediaChange-- ;
2778 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2779 break;
2780 }
2781 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
2782 {
2783 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2784 break;
2785 }
2786 if (pbPacket[0] == SCSI_READ_10)
2787 cSectors = ataBE2H_U16(pbPacket + 7);
2788 else
2789 cSectors = ataBE2H_U32(pbPacket + 6);
2790 iATAPILBA = ataBE2H_U32(pbPacket + 2);
2791 if (cSectors == 0)
2792 {
2793 atapiCmdOK(s);
2794 break;
2795 }
2796 if ((uint64_t)iATAPILBA + cSectors > s->cTotalSectors)
2797 {
2798 /* Rate limited logging, one log line per second. For
2799 * guests that insist on reading from places outside the
2800 * valid area this often generates too many release log
2801 * entries otherwise. */
2802 static uint64_t uLastLogTS = 0;
2803 if (RTTimeMilliTS() >= uLastLogTS + 1000)
2804 {
2805 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM block number %Ld invalid (READ)\n", s->iLUN, (uint64_t)iATAPILBA + cSectors));
2806 uLastLogTS = RTTimeMilliTS();
2807 }
2808 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_LOGICAL_BLOCK_OOR);
2809 break;
2810 }
2811 atapiReadSectors(s, iATAPILBA, cSectors, 2048);
2812 }
2813 break;
2814 case SCSI_READ_CD:
2815 {
2816 uint32_t cSectors, iATAPILBA;
2817
2818 if (s->cNotifiedMediaChange > 0)
2819 {
2820 s->cNotifiedMediaChange-- ;
2821 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2822 break;
2823 }
2824 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
2825 {
2826 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2827 break;
2828 }
2829 cSectors = (pbPacket[6] << 16) | (pbPacket[7] << 8) | pbPacket[8];
2830 iATAPILBA = ataBE2H_U32(pbPacket + 2);
2831 if (cSectors == 0)
2832 {
2833 atapiCmdOK(s);
2834 break;
2835 }
2836 if ((uint64_t)iATAPILBA + cSectors > s->cTotalSectors)
2837 {
2838 /* Rate limited logging, one log line per second. For
2839 * guests that insist on reading from places outside the
2840 * valid area this often generates too many release log
2841 * entries otherwise. */
2842 static uint64_t uLastLogTS = 0;
2843 if (RTTimeMilliTS() >= uLastLogTS + 1000)
2844 {
2845 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM block number %Ld invalid (READ CD)\n", s->iLUN, (uint64_t)iATAPILBA + cSectors));
2846 uLastLogTS = RTTimeMilliTS();
2847 }
2848 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_LOGICAL_BLOCK_OOR);
2849 break;
2850 }
2851 switch (pbPacket[9] & 0xf8)
2852 {
2853 case 0x00:
2854 /* nothing */
2855 atapiCmdOK(s);
2856 break;
2857 case 0x10:
2858 /* normal read */
2859 atapiReadSectors(s, iATAPILBA, cSectors, 2048);
2860 break;
2861 case 0xf8:
2862 /* read all data */
2863 atapiReadSectors(s, iATAPILBA, cSectors, 2352);
2864 break;
2865 default:
2866 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM sector format not supported (%#x)\n", s->iLUN, pbPacket[9] & 0xf8));
2867 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2868 break;
2869 }
2870 }
2871 break;
2872 case SCSI_SEEK_10:
2873 {
2874 uint32_t iATAPILBA;
2875 if (s->cNotifiedMediaChange > 0)
2876 {
2877 s->cNotifiedMediaChange-- ;
2878 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2879 break;
2880 }
2881 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
2882 {
2883 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2884 break;
2885 }
2886 iATAPILBA = ataBE2H_U32(pbPacket + 2);
2887 if (iATAPILBA > s->cTotalSectors)
2888 {
2889 /* Rate limited logging, one log line per second. For
2890 * guests that insist on seeking to places outside the
2891 * valid area this often generates too many release log
2892 * entries otherwise. */
2893 static uint64_t uLastLogTS = 0;
2894 if (RTTimeMilliTS() >= uLastLogTS + 1000)
2895 {
2896 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM block number %Ld invalid (SEEK)\n", s->iLUN, (uint64_t)iATAPILBA));
2897 uLastLogTS = RTTimeMilliTS();
2898 }
2899 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_LOGICAL_BLOCK_OOR);
2900 break;
2901 }
2902 atapiCmdOK(s);
2903 ataSetStatus(s, ATA_STAT_SEEK); /* Linux expects this. */
2904 }
2905 break;
2906 case SCSI_START_STOP_UNIT:
2907 {
2908 int rc = VINF_SUCCESS;
2909 switch (pbPacket[4] & 3)
2910 {
2911 case 0: /* 00 - Stop motor */
2912 case 1: /* 01 - Start motor */
2913 break;
2914 case 2: /* 10 - Eject media */
2915 /* This must be done from EMT. */
2916 {
2917 PATACONTROLLER pCtl = ATADEVSTATE_2_CONTROLLER(s);
2918 PPDMDEVINS pDevIns = ATADEVSTATE_2_DEVINS(s);
2919
2920 PDMCritSectLeave(&pCtl->lock);
2921 rc = VMR3ReqCallWait(PDMDevHlpGetVM(pDevIns), VMCPUID_ANY,
2922 (PFNRT)s->pDrvMount->pfnUnmount, 2, s->pDrvMount, false);
2923 Assert(RT_SUCCESS(rc) || (rc == VERR_PDM_MEDIA_LOCKED));
2924 {
2925 STAM_PROFILE_START(&pCtl->StatLockWait, a);
2926 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
2927 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
2928 }
2929 }
2930 break;
2931 case 3: /* 11 - Load media */
2932 /** @todo rc = s->pDrvMount->pfnLoadMedia(s->pDrvMount) */
2933 break;
2934 }
2935 if (RT_SUCCESS(rc))
2936 atapiCmdOK(s);
2937 else
2938 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIA_LOAD_OR_EJECT_FAILED);
2939 }
2940 break;
2941 case SCSI_MECHANISM_STATUS:
2942 {
2943 cbMax = ataBE2H_U16(pbPacket + 8);
2944 ataStartTransfer(s, RT_MIN(cbMax, 8), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_MECHANISM_STATUS, true);
2945 }
2946 break;
2947 case SCSI_READ_TOC_PMA_ATIP:
2948 {
2949 uint8_t format;
2950
2951 if (s->cNotifiedMediaChange > 0)
2952 {
2953 s->cNotifiedMediaChange-- ;
2954 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2955 break;
2956 }
2957 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
2958 {
2959 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2960 break;
2961 }
2962 cbMax = ataBE2H_U16(pbPacket + 7);
2963 /* SCSI MMC-3 spec says format is at offset 2 (lower 4 bits),
2964 * but Linux kernel uses offset 9 (topmost 2 bits). Hope that
2965 * the other field is clear... */
2966 format = (pbPacket[2] & 0xf) | (pbPacket[9] >> 6);
2967 switch (format)
2968 {
2969 case 0:
2970 ataStartTransfer(s, cbMax, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_TOC_NORMAL, true);
2971 break;
2972 case 1:
2973 ataStartTransfer(s, RT_MIN(cbMax, 12), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_TOC_MULTI, true);
2974 break;
2975 case 2:
2976 ataStartTransfer(s, cbMax, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_TOC_RAW, true);
2977 break;
2978 default:
2979 error_cmd:
2980 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
2981 break;
2982 }
2983 }
2984 break;
2985 case SCSI_READ_CAPACITY:
2986 if (s->cNotifiedMediaChange > 0)
2987 {
2988 s->cNotifiedMediaChange-- ;
2989 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
2990 break;
2991 }
2992 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
2993 {
2994 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
2995 break;
2996 }
2997 ataStartTransfer(s, 8, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_CAPACITY, true);
2998 break;
2999 case SCSI_READ_DISC_INFORMATION:
3000 if (s->cNotifiedMediaChange > 0)
3001 {
3002 s->cNotifiedMediaChange-- ;
3003 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
3004 break;
3005 }
3006 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
3007 {
3008 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
3009 break;
3010 }
3011 cbMax = ataBE2H_U16(pbPacket + 7);
3012 ataStartTransfer(s, RT_MIN(cbMax, 34), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_DISC_INFORMATION, true);
3013 break;
3014 case SCSI_READ_TRACK_INFORMATION:
3015 if (s->cNotifiedMediaChange > 0)
3016 {
3017 s->cNotifiedMediaChange-- ;
3018 atapiCmdErrorSimple(s, SCSI_SENSE_UNIT_ATTENTION, SCSI_ASC_MEDIUM_MAY_HAVE_CHANGED); /* media changed */
3019 break;
3020 }
3021 else if (!s->pDrvMount->pfnIsMounted(s->pDrvMount))
3022 {
3023 atapiCmdErrorSimple(s, SCSI_SENSE_NOT_READY, SCSI_ASC_MEDIUM_NOT_PRESENT);
3024 break;
3025 }
3026 cbMax = ataBE2H_U16(pbPacket + 7);
3027 ataStartTransfer(s, RT_MIN(cbMax, 36), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_TRACK_INFORMATION, true);
3028 break;
3029 case SCSI_GET_CONFIGURATION:
3030 /* No media change stuff here, it can confuse Linux guests. */
3031 cbMax = ataBE2H_U16(pbPacket + 7);
3032 ataStartTransfer(s, RT_MIN(cbMax, 32), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_GET_CONFIGURATION, true);
3033 break;
3034 case SCSI_INQUIRY:
3035 cbMax = ataBE2H_U16(pbPacket + 3);
3036 ataStartTransfer(s, RT_MIN(cbMax, 36), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_INQUIRY, true);
3037 break;
3038 case SCSI_READ_DVD_STRUCTURE:
3039 {
3040 /* Only available for ICH6 for now. */
3041 PCIATAState *pDevice = PDMINS_2_DATA(s->CTX_SUFF(pDevIns), PCIATAState *);
3042
3043 if ( (PCIDevGetVendorId(&pDevice->dev) == 0x8086)
3044 && (PCIDevGetDeviceId(&pDevice->dev) == 0x269e))
3045 {
3046 cbMax = ataBE2H_U16(pbPacket + 8);
3047 ataStartTransfer(s, RT_MIN(cbMax, 4), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_READ_DVD_STRUCTURE, true);
3048 }
3049 else
3050 {
3051 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_ILLEGAL_OPCODE);
3052 }
3053 break;
3054 }
3055 default:
3056 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_ILLEGAL_OPCODE);
3057 break;
3058 }
3059}
3060
3061
3062/*
3063 * Parse ATAPI commands, passing them directly to the CD/DVD drive.
3064 */
3065static void atapiParseCmdPassthrough(ATADevState *s)
3066{
3067 const uint8_t *pbPacket;
3068 uint8_t *pbBuf;
3069 uint32_t cSectors, iATAPILBA;
3070 uint32_t cbTransfer = 0;
3071 PDMBLOCKTXDIR uTxDir = PDMBLOCKTXDIR_NONE;
3072
3073 pbPacket = s->aATAPICmd;
3074 pbBuf = s->CTX_SUFF(pbIOBuffer);
3075 switch (pbPacket[0])
3076 {
3077 case SCSI_BLANK:
3078 goto sendcmd;
3079 case SCSI_CLOSE_TRACK_SESSION:
3080 goto sendcmd;
3081 case SCSI_ERASE_10:
3082 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3083 cbTransfer = ataBE2H_U16(pbPacket + 7);
3084 Log2(("ATAPI PT: lba %d\n", iATAPILBA));
3085 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3086 goto sendcmd;
3087 case SCSI_FORMAT_UNIT:
3088 cbTransfer = s->uATARegLCyl | (s->uATARegHCyl << 8); /* use ATAPI transfer length */
3089 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3090 goto sendcmd;
3091 case SCSI_GET_CONFIGURATION:
3092 cbTransfer = ataBE2H_U16(pbPacket + 7);
3093 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3094 goto sendcmd;
3095 case SCSI_GET_EVENT_STATUS_NOTIFICATION:
3096 cbTransfer = ataBE2H_U16(pbPacket + 7);
3097 if (ASMAtomicReadU32(&s->MediaEventStatus) != ATA_EVENT_STATUS_UNCHANGED)
3098 {
3099 ataStartTransfer(s, RT_MIN(cbTransfer, 8), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_GET_EVENT_STATUS_NOTIFICATION, true);
3100 break;
3101 }
3102 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3103 goto sendcmd;
3104 case SCSI_GET_PERFORMANCE:
3105 cbTransfer = s->uATARegLCyl | (s->uATARegHCyl << 8); /* use ATAPI transfer length */
3106 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3107 goto sendcmd;
3108 case SCSI_INQUIRY:
3109 cbTransfer = ataBE2H_U16(pbPacket + 3);
3110 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3111 goto sendcmd;
3112 case SCSI_LOAD_UNLOAD_MEDIUM:
3113 goto sendcmd;
3114 case SCSI_MECHANISM_STATUS:
3115 cbTransfer = ataBE2H_U16(pbPacket + 8);
3116 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3117 goto sendcmd;
3118 case SCSI_MODE_SELECT_10:
3119 cbTransfer = ataBE2H_U16(pbPacket + 7);
3120 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3121 goto sendcmd;
3122 case SCSI_MODE_SENSE_10:
3123 cbTransfer = ataBE2H_U16(pbPacket + 7);
3124 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3125 goto sendcmd;
3126 case SCSI_PAUSE_RESUME:
3127 goto sendcmd;
3128 case SCSI_PLAY_AUDIO_10:
3129 goto sendcmd;
3130 case SCSI_PLAY_AUDIO_12:
3131 goto sendcmd;
3132 case SCSI_PLAY_AUDIO_MSF:
3133 goto sendcmd;
3134 case SCSI_PREVENT_ALLOW_MEDIUM_REMOVAL:
3135 /** @todo do not forget to unlock when a VM is shut down */
3136 goto sendcmd;
3137 case SCSI_READ_10:
3138 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3139 cSectors = ataBE2H_U16(pbPacket + 7);
3140 Log2(("ATAPI PT: lba %d sectors %d\n", iATAPILBA, cSectors));
3141 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3142 cbTransfer = cSectors * s->cbATAPISector;
3143 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3144 goto sendcmd;
3145 case SCSI_READ_12:
3146 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3147 cSectors = ataBE2H_U32(pbPacket + 6);
3148 Log2(("ATAPI PT: lba %d sectors %d\n", iATAPILBA, cSectors));
3149 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3150 cbTransfer = cSectors * s->cbATAPISector;
3151 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3152 goto sendcmd;
3153 case SCSI_READ_BUFFER:
3154 cbTransfer = ataBE2H_U24(pbPacket + 6);
3155 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3156 goto sendcmd;
3157 case SCSI_READ_BUFFER_CAPACITY:
3158 cbTransfer = ataBE2H_U16(pbPacket + 7);
3159 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3160 goto sendcmd;
3161 case SCSI_READ_CAPACITY:
3162 cbTransfer = 8;
3163 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3164 goto sendcmd;
3165 case SCSI_READ_CD:
3166 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3167 cbTransfer = ataBE2H_U24(pbPacket + 6) / s->cbATAPISector * s->cbATAPISector;
3168 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3169 goto sendcmd;
3170 case SCSI_READ_CD_MSF:
3171 cSectors = ataMSF2LBA(pbPacket + 6) - ataMSF2LBA(pbPacket + 3);
3172 if (cSectors > 32)
3173 cSectors = 32; /* Limit transfer size to 64~74K. Safety first. In any case this can only harm software doing CDDA extraction. */
3174 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3175 cbTransfer = cSectors * s->cbATAPISector;
3176 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3177 goto sendcmd;
3178 case SCSI_READ_DISC_INFORMATION:
3179 cbTransfer = ataBE2H_U16(pbPacket + 7);
3180 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3181 goto sendcmd;
3182 case SCSI_READ_DVD_STRUCTURE:
3183 cbTransfer = ataBE2H_U16(pbPacket + 8);
3184 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3185 goto sendcmd;
3186 case SCSI_READ_FORMAT_CAPACITIES:
3187 cbTransfer = ataBE2H_U16(pbPacket + 7);
3188 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3189 goto sendcmd;
3190 case SCSI_READ_SUBCHANNEL:
3191 cbTransfer = ataBE2H_U16(pbPacket + 7);
3192 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3193 goto sendcmd;
3194 case SCSI_READ_TOC_PMA_ATIP:
3195 cbTransfer = ataBE2H_U16(pbPacket + 7);
3196 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3197 goto sendcmd;
3198 case SCSI_READ_TRACK_INFORMATION:
3199 cbTransfer = ataBE2H_U16(pbPacket + 7);
3200 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3201 goto sendcmd;
3202 case SCSI_REPAIR_TRACK:
3203 goto sendcmd;
3204 case SCSI_REPORT_KEY:
3205 cbTransfer = ataBE2H_U16(pbPacket + 8);
3206 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3207 goto sendcmd;
3208 case SCSI_REQUEST_SENSE:
3209 cbTransfer = pbPacket[4];
3210 if ((s->abATAPISense[2] & 0x0f) != SCSI_SENSE_NONE)
3211 {
3212 ataStartTransfer(s, RT_MIN(cbTransfer, 18), PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_ATAPI_CMD, ATAFN_SS_ATAPI_REQUEST_SENSE, true);
3213 break;
3214 }
3215 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3216 goto sendcmd;
3217 case SCSI_RESERVE_TRACK:
3218 goto sendcmd;
3219 case SCSI_SCAN:
3220 goto sendcmd;
3221 case SCSI_SEEK_10:
3222 goto sendcmd;
3223 case SCSI_SEND_CUE_SHEET:
3224 cbTransfer = ataBE2H_U24(pbPacket + 6);
3225 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3226 goto sendcmd;
3227 case SCSI_SEND_DVD_STRUCTURE:
3228 cbTransfer = ataBE2H_U16(pbPacket + 8);
3229 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3230 goto sendcmd;
3231 case SCSI_SEND_EVENT:
3232 cbTransfer = ataBE2H_U16(pbPacket + 8);
3233 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3234 goto sendcmd;
3235 case SCSI_SEND_KEY:
3236 cbTransfer = ataBE2H_U16(pbPacket + 8);
3237 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3238 goto sendcmd;
3239 case SCSI_SEND_OPC_INFORMATION:
3240 cbTransfer = ataBE2H_U16(pbPacket + 7);
3241 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3242 goto sendcmd;
3243 case SCSI_SET_CD_SPEED:
3244 goto sendcmd;
3245 case SCSI_SET_READ_AHEAD:
3246 goto sendcmd;
3247 case SCSI_SET_STREAMING:
3248 cbTransfer = ataBE2H_U16(pbPacket + 9);
3249 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3250 goto sendcmd;
3251 case SCSI_START_STOP_UNIT:
3252 goto sendcmd;
3253 case SCSI_STOP_PLAY_SCAN:
3254 goto sendcmd;
3255 case SCSI_SYNCHRONIZE_CACHE:
3256 goto sendcmd;
3257 case SCSI_TEST_UNIT_READY:
3258 goto sendcmd;
3259 case SCSI_VERIFY_10:
3260 goto sendcmd;
3261 case SCSI_WRITE_10:
3262 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3263 cSectors = ataBE2H_U16(pbPacket + 7);
3264 Log2(("ATAPI PT: lba %d sectors %d\n", iATAPILBA, cSectors));
3265#if 0
3266 /* The sector size is determined by the async I/O thread. */
3267 s->cbATAPISector = 0;
3268 /* Preliminary, will be corrected once the sector size is known. */
3269 cbTransfer = cSectors;
3270#else
3271 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3272 cbTransfer = cSectors * s->cbATAPISector;
3273#endif
3274 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3275 goto sendcmd;
3276 case SCSI_WRITE_12:
3277 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3278 cSectors = ataBE2H_U32(pbPacket + 6);
3279 Log2(("ATAPI PT: lba %d sectors %d\n", iATAPILBA, cSectors));
3280#if 0
3281 /* The sector size is determined by the async I/O thread. */
3282 s->cbATAPISector = 0;
3283 /* Preliminary, will be corrected once the sector size is known. */
3284 cbTransfer = cSectors;
3285#else
3286 s->cbATAPISector = 2048; /**< @todo this size is not always correct */
3287 cbTransfer = cSectors * s->cbATAPISector;
3288#endif
3289 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3290 goto sendcmd;
3291 case SCSI_WRITE_AND_VERIFY_10:
3292 iATAPILBA = ataBE2H_U32(pbPacket + 2);
3293 cSectors = ataBE2H_U16(pbPacket + 7);
3294 Log2(("ATAPI PT: lba %d sectors %d\n", iATAPILBA, cSectors));
3295 /* The sector size is determined by the async I/O thread. */
3296 s->cbATAPISector = 0;
3297 /* Preliminary, will be corrected once the sector size is known. */
3298 cbTransfer = cSectors;
3299 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3300 goto sendcmd;
3301 case SCSI_WRITE_BUFFER:
3302 switch (pbPacket[1] & 0x1f)
3303 {
3304 case 0x04: /* download microcode */
3305 case 0x05: /* download microcode and save */
3306 case 0x06: /* download microcode with offsets */
3307 case 0x07: /* download microcode with offsets and save */
3308 case 0x0e: /* download microcode with offsets and defer activation */
3309 case 0x0f: /* activate deferred microcode */
3310 LogRel(("PIIX3 ATA: LUN#%d: CD-ROM passthrough command attempted to update firmware, blocked\n", s->iLUN));
3311 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_INV_FIELD_IN_CMD_PACKET);
3312 break;
3313 default:
3314 cbTransfer = ataBE2H_U16(pbPacket + 6);
3315 uTxDir = PDMBLOCKTXDIR_TO_DEVICE;
3316 goto sendcmd;
3317 }
3318 break;
3319 case SCSI_REPORT_LUNS: /* Not part of MMC-3, but used by Windows. */
3320 cbTransfer = ataBE2H_U32(pbPacket + 6);
3321 uTxDir = PDMBLOCKTXDIR_FROM_DEVICE;
3322 goto sendcmd;
3323 case SCSI_REZERO_UNIT:
3324 /* Obsolete command used by cdrecord. What else would one expect?
3325 * This command is not sent to the drive, it is handled internally,
3326 * as the Linux kernel doesn't like it (message "scsi: unknown
3327 * opcode 0x01" in syslog) and replies with a sense code of 0,
3328 * which sends cdrecord to an endless loop. */
3329 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_ILLEGAL_OPCODE);
3330 break;
3331 default:
3332 LogRel(("PIIX3 ATA: LUN#%d: passthrough unimplemented for command %#x\n", s->iLUN, pbPacket[0]));
3333 atapiCmdErrorSimple(s, SCSI_SENSE_ILLEGAL_REQUEST, SCSI_ASC_ILLEGAL_OPCODE);
3334 break;
3335 sendcmd:
3336 /* Send a command to the drive, passing data in/out as required. */
3337 Log2(("ATAPI PT: max size %d\n", cbTransfer));
3338 Assert(cbTransfer <= s->cbIOBuffer);
3339 if (cbTransfer == 0)
3340 uTxDir = PDMBLOCKTXDIR_NONE;
3341 ataStartTransfer(s, cbTransfer, uTxDir, ATAFN_BT_ATAPI_PASSTHROUGH_CMD, ATAFN_SS_ATAPI_PASSTHROUGH, true);
3342 }
3343}
3344
3345
3346static void atapiParseCmd(ATADevState *s)
3347{
3348 const uint8_t *pbPacket;
3349
3350 pbPacket = s->aATAPICmd;
3351#ifdef DEBUG
3352 Log(("%s: LUN#%d DMA=%d CMD=%#04x \"%s\"\n", __FUNCTION__, s->iLUN, s->fDMA, pbPacket[0], SCSICmdText(pbPacket[0])));
3353#else /* !DEBUG */
3354 Log(("%s: LUN#%d DMA=%d CMD=%#04x\n", __FUNCTION__, s->iLUN, s->fDMA, pbPacket[0]));
3355#endif /* !DEBUG */
3356 Log2(("%s: limit=%#x packet: %.*Rhxs\n", __FUNCTION__, s->uATARegLCyl | (s->uATARegHCyl << 8), ATAPI_PACKET_SIZE, pbPacket));
3357
3358 if (s->fATAPIPassthrough)
3359 atapiParseCmdPassthrough(s);
3360 else
3361 atapiParseCmdVirtualATAPI(s);
3362}
3363
3364
3365static bool ataPacketSS(ATADevState *s)
3366{
3367 s->fDMA = !!(s->uATARegFeature & 1);
3368 memcpy(s->aATAPICmd, s->CTX_SUFF(pbIOBuffer), ATAPI_PACKET_SIZE);
3369 s->uTxDir = PDMBLOCKTXDIR_NONE;
3370 s->cbTotalTransfer = 0;
3371 s->cbElementaryTransfer = 0;
3372 atapiParseCmd(s);
3373 return false;
3374}
3375
3376
3377/**
3378 * SCSI_GET_EVENT_STATUS_NOTIFICATION should return "medium removed" event
3379 * from now on, regardless if there was a medium inserted or not.
3380 */
3381static void ataMediumRemoved(ATADevState *s)
3382{
3383 ASMAtomicWriteU32(&s->MediaEventStatus, ATA_EVENT_STATUS_MEDIA_REMOVED);
3384}
3385
3386
3387/**
3388 * SCSI_GET_EVENT_STATUS_NOTIFICATION should return "medium inserted". If
3389 * there was already a medium inserted, don't forget to send the "medium
3390 * removed" event first.
3391 */
3392static void ataMediumInserted(ATADevState *s)
3393{
3394 uint32_t OldStatus, NewStatus;
3395 do
3396 {
3397 OldStatus = ASMAtomicReadU32(&s->MediaEventStatus);
3398 switch (OldStatus)
3399 {
3400 case ATA_EVENT_STATUS_MEDIA_CHANGED:
3401 case ATA_EVENT_STATUS_MEDIA_REMOVED:
3402 /* no change, we will send "medium removed" + "medium inserted" */
3403 NewStatus = ATA_EVENT_STATUS_MEDIA_CHANGED;
3404 break;
3405 default:
3406 NewStatus = ATA_EVENT_STATUS_MEDIA_NEW;
3407 break;
3408 }
3409 } while (!ASMAtomicCmpXchgU32(&s->MediaEventStatus, NewStatus, OldStatus));
3410}
3411
3412
3413/**
3414 * Called when a media is mounted.
3415 *
3416 * @param pInterface Pointer to the interface structure containing the called function pointer.
3417 */
3418static DECLCALLBACK(void) ataMountNotify(PPDMIMOUNTNOTIFY pInterface)
3419{
3420 ATADevState *pIf = PDMIMOUNTNOTIFY_2_ATASTATE(pInterface);
3421 Log(("%s: changing LUN#%d\n", __FUNCTION__, pIf->iLUN));
3422
3423 /* Ignore the call if we're called while being attached. */
3424 if (!pIf->pDrvBlock)
3425 return;
3426
3427 if (pIf->fATAPI)
3428 pIf->cTotalSectors = pIf->pDrvBlock->pfnGetSize(pIf->pDrvBlock) / 2048;
3429 else
3430 pIf->cTotalSectors = pIf->pDrvBlock->pfnGetSize(pIf->pDrvBlock) / 512;
3431
3432 LogRel(("PIIX3 ATA: LUN#%d: CD/DVD, total number of sectors %Ld, passthrough unchanged\n", pIf->iLUN, pIf->cTotalSectors));
3433
3434 /* Report media changed in TEST UNIT and other (probably incorrect) places. */
3435 if (pIf->cNotifiedMediaChange < 2)
3436 pIf->cNotifiedMediaChange = 2;
3437 ataMediumInserted(pIf);
3438}
3439
3440/**
3441 * Called when a media is unmounted
3442 * @param pInterface Pointer to the interface structure containing the called function pointer.
3443 */
3444static DECLCALLBACK(void) ataUnmountNotify(PPDMIMOUNTNOTIFY pInterface)
3445{
3446 ATADevState *pIf = PDMIMOUNTNOTIFY_2_ATASTATE(pInterface);
3447 Log(("%s:\n", __FUNCTION__));
3448 pIf->cTotalSectors = 0;
3449
3450 /*
3451 * Whatever I do, XP will not use the GET MEDIA STATUS nor the EVENT stuff.
3452 * However, it will respond to TEST UNIT with a 0x6 0x28 (media changed) sense code.
3453 * So, we'll give it 4 TEST UNIT command to catch up, two which the media is not
3454 * present and 2 in which it is changed.
3455 */
3456 pIf->cNotifiedMediaChange = 4;
3457 ataMediumRemoved(pIf);
3458}
3459
3460static void ataPacketBT(ATADevState *s)
3461{
3462 s->cbElementaryTransfer = s->cbTotalTransfer;
3463 s->uATARegNSector = (s->uATARegNSector & ~7) | ATAPI_INT_REASON_CD;
3464 Log2(("%s: interrupt reason %#04x\n", __FUNCTION__, s->uATARegNSector));
3465 ataSetStatusValue(s, ATA_STAT_READY);
3466}
3467
3468
3469static void ataResetDevice(ATADevState *s)
3470{
3471 s->cMultSectors = ATA_MAX_MULT_SECTORS;
3472 s->cNotifiedMediaChange = 0;
3473 ASMAtomicWriteU32(&s->MediaEventStatus, ATA_EVENT_STATUS_UNCHANGED);
3474 ataUnsetIRQ(s);
3475
3476 s->uATARegSelect = 0x20;
3477 ataSetStatusValue(s, ATA_STAT_READY);
3478 ataSetSignature(s);
3479 s->cbTotalTransfer = 0;
3480 s->cbElementaryTransfer = 0;
3481 s->iIOBufferPIODataStart = 0;
3482 s->iIOBufferPIODataEnd = 0;
3483 s->iBeginTransfer = ATAFN_BT_NULL;
3484 s->iSourceSink = ATAFN_SS_NULL;
3485 s->fDMA = false;
3486 s->fATAPITransfer = false;
3487 s->uATATransferMode = ATA_MODE_UDMA | 2; /* PIIX3 supports only up to UDMA2 */
3488
3489 s->uATARegFeature = 0;
3490}
3491
3492
3493static bool ataExecuteDeviceDiagnosticSS(ATADevState *s)
3494{
3495 ataSetSignature(s);
3496 if (s->fATAPI)
3497 ataSetStatusValue(s, 0); /* NOTE: READY is _not_ set */
3498 else
3499 ataSetStatusValue(s, ATA_STAT_READY);
3500 s->uATARegError = 0x01;
3501 return false;
3502}
3503
3504
3505static void ataParseCmd(ATADevState *s, uint8_t cmd)
3506{
3507#ifdef DEBUG
3508 Log(("%s: LUN#%d CMD=%#04x \"%s\"\n", __FUNCTION__, s->iLUN, cmd, ATACmdText(cmd)));
3509#else /* !DEBUG */
3510 Log(("%s: LUN#%d CMD=%#04x\n", __FUNCTION__, s->iLUN, cmd));
3511#endif /* !DEBUG */
3512 s->fLBA48 = false;
3513 s->fDMA = false;
3514 if (cmd == ATA_IDLE_IMMEDIATE)
3515 {
3516 /* Detect Linux timeout recovery, first tries IDLE IMMEDIATE (which
3517 * would overwrite the failing command unfortunately), then RESET. */
3518 int32_t uCmdWait = -1;
3519 uint64_t uNow = RTTimeNanoTS();
3520 if (s->u64CmdTS)
3521 uCmdWait = (uNow - s->u64CmdTS) / 1000;
3522 LogRel(("PIIX3 ATA: LUN#%d: IDLE IMMEDIATE, CmdIf=%#04x (%d usec ago)\n",
3523 s->iLUN, s->uATARegCommand, uCmdWait));
3524 }
3525 s->uATARegCommand = cmd;
3526 switch (cmd)
3527 {
3528 case ATA_IDENTIFY_DEVICE:
3529 if (s->pDrvBlock && !s->fATAPI)
3530 ataStartTransfer(s, 512, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_NULL, ATAFN_SS_IDENTIFY, false);
3531 else
3532 {
3533 if (s->fATAPI)
3534 ataSetSignature(s);
3535 ataCmdError(s, ABRT_ERR);
3536 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3537 }
3538 break;
3539 case ATA_INITIALIZE_DEVICE_PARAMETERS:
3540 case ATA_RECALIBRATE:
3541 ataCmdOK(s, ATA_STAT_SEEK);
3542 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3543 break;
3544 case ATA_SET_MULTIPLE_MODE:
3545 if ( s->uATARegNSector != 0
3546 && ( s->uATARegNSector > ATA_MAX_MULT_SECTORS
3547 || (s->uATARegNSector & (s->uATARegNSector - 1)) != 0))
3548 {
3549 ataCmdError(s, ABRT_ERR);
3550 }
3551 else
3552 {
3553 Log2(("%s: set multi sector count to %d\n", __FUNCTION__, s->uATARegNSector));
3554 s->cMultSectors = s->uATARegNSector;
3555 ataCmdOK(s, 0);
3556 }
3557 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3558 break;
3559 case ATA_READ_VERIFY_SECTORS_EXT:
3560 s->fLBA48 = true;
3561 case ATA_READ_VERIFY_SECTORS:
3562 case ATA_READ_VERIFY_SECTORS_WITHOUT_RETRIES:
3563 /* do sector number check ? */
3564 ataCmdOK(s, 0);
3565 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3566 break;
3567 case ATA_READ_SECTORS_EXT:
3568 s->fLBA48 = true;
3569 case ATA_READ_SECTORS:
3570 case ATA_READ_SECTORS_WITHOUT_RETRIES:
3571 if (!s->pDrvBlock)
3572 goto abort_cmd;
3573 s->cSectorsPerIRQ = 1;
3574 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_READ_SECTORS, false);
3575 break;
3576 case ATA_WRITE_SECTORS_EXT:
3577 s->fLBA48 = true;
3578 case ATA_WRITE_SECTORS:
3579 case ATA_WRITE_SECTORS_WITHOUT_RETRIES:
3580 s->cSectorsPerIRQ = 1;
3581 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_TO_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_WRITE_SECTORS, false);
3582 break;
3583 case ATA_READ_MULTIPLE_EXT:
3584 s->fLBA48 = true;
3585 case ATA_READ_MULTIPLE:
3586 if (!s->cMultSectors)
3587 goto abort_cmd;
3588 s->cSectorsPerIRQ = s->cMultSectors;
3589 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_READ_SECTORS, false);
3590 break;
3591 case ATA_WRITE_MULTIPLE_EXT:
3592 s->fLBA48 = true;
3593 case ATA_WRITE_MULTIPLE:
3594 if (!s->cMultSectors)
3595 goto abort_cmd;
3596 s->cSectorsPerIRQ = s->cMultSectors;
3597 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_TO_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_WRITE_SECTORS, false);
3598 break;
3599 case ATA_READ_DMA_EXT:
3600 s->fLBA48 = true;
3601 case ATA_READ_DMA:
3602 case ATA_READ_DMA_WITHOUT_RETRIES:
3603 if (!s->pDrvBlock)
3604 goto abort_cmd;
3605 s->cSectorsPerIRQ = ATA_MAX_MULT_SECTORS;
3606 s->fDMA = true;
3607 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_READ_SECTORS, false);
3608 break;
3609 case ATA_WRITE_DMA_EXT:
3610 s->fLBA48 = true;
3611 case ATA_WRITE_DMA:
3612 case ATA_WRITE_DMA_WITHOUT_RETRIES:
3613 if (!s->pDrvBlock)
3614 goto abort_cmd;
3615 s->cSectorsPerIRQ = ATA_MAX_MULT_SECTORS;
3616 s->fDMA = true;
3617 ataStartTransfer(s, ataGetNSectors(s) * 512, PDMBLOCKTXDIR_TO_DEVICE, ATAFN_BT_READ_WRITE_SECTORS, ATAFN_SS_WRITE_SECTORS, false);
3618 break;
3619 case ATA_READ_NATIVE_MAX_ADDRESS_EXT:
3620 s->fLBA48 = true;
3621 ataSetSector(s, s->cTotalSectors - 1);
3622 ataCmdOK(s, 0);
3623 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3624 break;
3625 case ATA_SEEK: /* Used by the SCO OpenServer. Command is marked as obsolete */
3626 ataCmdOK(s, 0);
3627 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3628 break;
3629 case ATA_READ_NATIVE_MAX_ADDRESS:
3630 ataSetSector(s, RT_MIN(s->cTotalSectors, 1 << 28) - 1);
3631 ataCmdOK(s, 0);
3632 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3633 break;
3634 case ATA_CHECK_POWER_MODE:
3635 s->uATARegNSector = 0xff; /* drive active or idle */
3636 ataCmdOK(s, 0);
3637 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3638 break;
3639 case ATA_SET_FEATURES:
3640 Log2(("%s: feature=%#x\n", __FUNCTION__, s->uATARegFeature));
3641 if (!s->pDrvBlock)
3642 goto abort_cmd;
3643 switch (s->uATARegFeature)
3644 {
3645 case 0x02: /* write cache enable */
3646 Log2(("%s: write cache enable\n", __FUNCTION__));
3647 ataCmdOK(s, ATA_STAT_SEEK);
3648 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3649 break;
3650 case 0xaa: /* read look-ahead enable */
3651 Log2(("%s: read look-ahead enable\n", __FUNCTION__));
3652 ataCmdOK(s, ATA_STAT_SEEK);
3653 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3654 break;
3655 case 0x55: /* read look-ahead disable */
3656 Log2(("%s: read look-ahead disable\n", __FUNCTION__));
3657 ataCmdOK(s, ATA_STAT_SEEK);
3658 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3659 break;
3660 case 0xcc: /* reverting to power-on defaults enable */
3661 Log2(("%s: revert to power-on defaults enable\n", __FUNCTION__));
3662 ataCmdOK(s, ATA_STAT_SEEK);
3663 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3664 break;
3665 case 0x66: /* reverting to power-on defaults disable */
3666 Log2(("%s: revert to power-on defaults disable\n", __FUNCTION__));
3667 ataCmdOK(s, ATA_STAT_SEEK);
3668 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3669 break;
3670 case 0x82: /* write cache disable */
3671 Log2(("%s: write cache disable\n", __FUNCTION__));
3672 /* As per the ATA/ATAPI-6 specs, a write cache disable
3673 * command MUST flush the write buffers to disc. */
3674 ataStartTransfer(s, 0, PDMBLOCKTXDIR_NONE, ATAFN_BT_NULL, ATAFN_SS_FLUSH, false);
3675 break;
3676 case 0x03: { /* set transfer mode */
3677 Log2(("%s: transfer mode %#04x\n", __FUNCTION__, s->uATARegNSector));
3678 switch (s->uATARegNSector & 0xf8)
3679 {
3680 case 0x00: /* PIO default */
3681 case 0x08: /* PIO mode */
3682 break;
3683 case ATA_MODE_MDMA: /* MDMA mode */
3684 s->uATATransferMode = (s->uATARegNSector & 0xf8) | RT_MIN(s->uATARegNSector & 0x07, ATA_MDMA_MODE_MAX);
3685 break;
3686 case ATA_MODE_UDMA: /* UDMA mode */
3687 s->uATATransferMode = (s->uATARegNSector & 0xf8) | RT_MIN(s->uATARegNSector & 0x07, ATA_UDMA_MODE_MAX);
3688 break;
3689 default:
3690 goto abort_cmd;
3691 }
3692 ataCmdOK(s, ATA_STAT_SEEK);
3693 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3694 break;
3695 }
3696 default:
3697 goto abort_cmd;
3698 }
3699 /*
3700 * OS/2 workarond:
3701 * The OS/2 IDE driver from MCP2 appears to rely on the feature register being
3702 * reset here. According to the specification, this is a driver bug as the register
3703 * contents are undefined after the call. This means we can just as well reset it.
3704 */
3705 s->uATARegFeature = 0;
3706 break;
3707 case ATA_FLUSH_CACHE_EXT:
3708 case ATA_FLUSH_CACHE:
3709 if (!s->pDrvBlock || s->fATAPI)
3710 goto abort_cmd;
3711 ataStartTransfer(s, 0, PDMBLOCKTXDIR_NONE, ATAFN_BT_NULL, ATAFN_SS_FLUSH, false);
3712 break;
3713 case ATA_STANDBY_IMMEDIATE:
3714 ataCmdOK(s, 0);
3715 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3716 break;
3717 case ATA_IDLE_IMMEDIATE:
3718 LogRel(("PIIX3 ATA: LUN#%d: aborting current command\n", s->iLUN));
3719 ataAbortCurrentCommand(s, false);
3720 break;
3721 /* ATAPI commands */
3722 case ATA_IDENTIFY_PACKET_DEVICE:
3723 if (s->fATAPI)
3724 ataStartTransfer(s, 512, PDMBLOCKTXDIR_FROM_DEVICE, ATAFN_BT_NULL, ATAFN_SS_ATAPI_IDENTIFY, false);
3725 else
3726 {
3727 ataCmdError(s, ABRT_ERR);
3728 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3729 }
3730 break;
3731 case ATA_EXECUTE_DEVICE_DIAGNOSTIC:
3732 ataStartTransfer(s, 0, PDMBLOCKTXDIR_NONE, ATAFN_BT_NULL, ATAFN_SS_EXECUTE_DEVICE_DIAGNOSTIC, false);
3733 break;
3734 case ATA_DEVICE_RESET:
3735 if (!s->fATAPI)
3736 goto abort_cmd;
3737 LogRel(("PIIX3 ATA: LUN#%d: performing device RESET\n", s->iLUN));
3738 ataAbortCurrentCommand(s, true);
3739 break;
3740 case ATA_PACKET:
3741 if (!s->fATAPI)
3742 goto abort_cmd;
3743 /* overlapping commands not supported */
3744 if (s->uATARegFeature & 0x02)
3745 goto abort_cmd;
3746 ataStartTransfer(s, ATAPI_PACKET_SIZE, PDMBLOCKTXDIR_TO_DEVICE, ATAFN_BT_PACKET, ATAFN_SS_PACKET, false);
3747 break;
3748 default:
3749 abort_cmd:
3750 ataCmdError(s, ABRT_ERR);
3751 ataSetIRQ(s); /* Shortcut, do not use AIO thread. */
3752 break;
3753 }
3754}
3755
3756#endif /* IN_RING3 */
3757
3758static int ataIOPortWriteU8(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
3759{
3760 Log2(("%s: write addr=%#x val=%#04x\n", __FUNCTION__, addr, val));
3761 addr &= 7;
3762 switch (addr)
3763 {
3764 case 0:
3765 break;
3766 case 1: /* feature register */
3767 /* NOTE: data is written to the two drives */
3768 pCtl->aIfs[0].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3769 pCtl->aIfs[1].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3770 pCtl->aIfs[0].uATARegFeatureHOB = pCtl->aIfs[0].uATARegFeature;
3771 pCtl->aIfs[1].uATARegFeatureHOB = pCtl->aIfs[1].uATARegFeature;
3772 pCtl->aIfs[0].uATARegFeature = val;
3773 pCtl->aIfs[1].uATARegFeature = val;
3774 break;
3775 case 2: /* sector count */
3776 pCtl->aIfs[0].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3777 pCtl->aIfs[1].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3778 pCtl->aIfs[0].uATARegNSectorHOB = pCtl->aIfs[0].uATARegNSector;
3779 pCtl->aIfs[1].uATARegNSectorHOB = pCtl->aIfs[1].uATARegNSector;
3780 pCtl->aIfs[0].uATARegNSector = val;
3781 pCtl->aIfs[1].uATARegNSector = val;
3782 break;
3783 case 3: /* sector number */
3784 pCtl->aIfs[0].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3785 pCtl->aIfs[1].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3786 pCtl->aIfs[0].uATARegSectorHOB = pCtl->aIfs[0].uATARegSector;
3787 pCtl->aIfs[1].uATARegSectorHOB = pCtl->aIfs[1].uATARegSector;
3788 pCtl->aIfs[0].uATARegSector = val;
3789 pCtl->aIfs[1].uATARegSector = val;
3790 break;
3791 case 4: /* cylinder low */
3792 pCtl->aIfs[0].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3793 pCtl->aIfs[1].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3794 pCtl->aIfs[0].uATARegLCylHOB = pCtl->aIfs[0].uATARegLCyl;
3795 pCtl->aIfs[1].uATARegLCylHOB = pCtl->aIfs[1].uATARegLCyl;
3796 pCtl->aIfs[0].uATARegLCyl = val;
3797 pCtl->aIfs[1].uATARegLCyl = val;
3798 break;
3799 case 5: /* cylinder high */
3800 pCtl->aIfs[0].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3801 pCtl->aIfs[1].uATARegDevCtl &= ~ATA_DEVCTL_HOB;
3802 pCtl->aIfs[0].uATARegHCylHOB = pCtl->aIfs[0].uATARegHCyl;
3803 pCtl->aIfs[1].uATARegHCylHOB = pCtl->aIfs[1].uATARegHCyl;
3804 pCtl->aIfs[0].uATARegHCyl = val;
3805 pCtl->aIfs[1].uATARegHCyl = val;
3806 break;
3807 case 6: /* drive/head */
3808 pCtl->aIfs[0].uATARegSelect = (val & ~0x10) | 0xa0;
3809 pCtl->aIfs[1].uATARegSelect = (val | 0x10) | 0xa0;
3810 if (((val >> 4) & 1) != pCtl->iSelectedIf)
3811 {
3812 PPDMDEVINS pDevIns = CONTROLLER_2_DEVINS(pCtl);
3813
3814 /* select another drive */
3815 pCtl->iSelectedIf = (val >> 4) & 1;
3816 /* The IRQ line is multiplexed between the two drives, so
3817 * update the state when switching to another drive. Only need
3818 * to update interrupt line if it is enabled and there is a
3819 * state change. */
3820 if ( !(pCtl->aIfs[pCtl->iSelectedIf].uATARegDevCtl & ATA_DEVCTL_DISABLE_IRQ)
3821 && ( pCtl->aIfs[pCtl->iSelectedIf].fIrqPending
3822 != pCtl->aIfs[pCtl->iSelectedIf ^ 1].fIrqPending))
3823 {
3824 if (pCtl->aIfs[pCtl->iSelectedIf].fIrqPending)
3825 {
3826 Log2(("%s: LUN#%d asserting IRQ (drive select change)\n", __FUNCTION__, pCtl->aIfs[pCtl->iSelectedIf].iLUN));
3827 /* The BMDMA unit unconditionally sets BM_STATUS_INT if
3828 * the interrupt line is asserted. It monitors the line
3829 * for a rising edge. */
3830 pCtl->BmDma.u8Status |= BM_STATUS_INT;
3831 if (pCtl->irq == 16)
3832 PDMDevHlpPCISetIrqNoWait(pDevIns, 0, 1);
3833 else
3834 PDMDevHlpISASetIrqNoWait(pDevIns, pCtl->irq, 1);
3835 }
3836 else
3837 {
3838 Log2(("%s: LUN#%d deasserting IRQ (drive select change)\n", __FUNCTION__, pCtl->aIfs[pCtl->iSelectedIf].iLUN));
3839 if (pCtl->irq == 16)
3840 PDMDevHlpPCISetIrqNoWait(pDevIns, 0, 0);
3841 else
3842 PDMDevHlpISASetIrqNoWait(pDevIns, pCtl->irq, 0);
3843 }
3844 }
3845 }
3846 break;
3847 default:
3848 case 7: /* command */
3849 /* ignore commands to non existant slave */
3850 if (pCtl->iSelectedIf && !pCtl->aIfs[pCtl->iSelectedIf].pDrvBlock)
3851 break;
3852#ifndef IN_RING3
3853 /* Don't do anything complicated in GC */
3854 return VINF_IOM_HC_IOPORT_WRITE;
3855#else /* IN_RING3 */
3856 ataParseCmd(&pCtl->aIfs[pCtl->iSelectedIf], val);
3857#endif /* !IN_RING3 */
3858 }
3859 return VINF_SUCCESS;
3860}
3861
3862
3863static int ataIOPortReadU8(PATACONTROLLER pCtl, uint32_t addr, uint32_t *pu32)
3864{
3865 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
3866 uint32_t val;
3867 bool fHOB;
3868
3869 fHOB = !!(s->uATARegDevCtl & (1 << 7));
3870 switch (addr & 7)
3871 {
3872 case 0: /* data register */
3873 val = 0xff;
3874 break;
3875 case 1: /* error register */
3876 /* The ATA specification is very terse when it comes to specifying
3877 * the precise effects of reading back the error/feature register.
3878 * The error register (read-only) shares the register number with
3879 * the feature register (write-only), so it seems that it's not
3880 * necessary to support the usual HOB readback here. */
3881 if (!s->pDrvBlock)
3882 val = 0;
3883 else
3884 val = s->uATARegError;
3885 break;
3886 case 2: /* sector count */
3887 if (!s->pDrvBlock)
3888 val = 0;
3889 else if (fHOB)
3890 val = s->uATARegNSectorHOB;
3891 else
3892 val = s->uATARegNSector;
3893 break;
3894 case 3: /* sector number */
3895 if (!s->pDrvBlock)
3896 val = 0;
3897 else if (fHOB)
3898 val = s->uATARegSectorHOB;
3899 else
3900 val = s->uATARegSector;
3901 break;
3902 case 4: /* cylinder low */
3903 if (!s->pDrvBlock)
3904 val = 0;
3905 else if (fHOB)
3906 val = s->uATARegLCylHOB;
3907 else
3908 val = s->uATARegLCyl;
3909 break;
3910 case 5: /* cylinder high */
3911 if (!s->pDrvBlock)
3912 val = 0;
3913 else if (fHOB)
3914 val = s->uATARegHCylHOB;
3915 else
3916 val = s->uATARegHCyl;
3917 break;
3918 case 6: /* drive/head */
3919 /* This register must always work as long as there is at least
3920 * one drive attached to the controller. It is common between
3921 * both drives anyway (completely identical content). */
3922 if (!pCtl->aIfs[0].pDrvBlock && !pCtl->aIfs[1].pDrvBlock)
3923 val = 0;
3924 else
3925 val = s->uATARegSelect;
3926 break;
3927 default:
3928 case 7: /* primary status */
3929 {
3930 /* Counter for number of busy status seen in GC in a row. */
3931 static unsigned cBusy = 0;
3932
3933 if (!s->pDrvBlock)
3934 val = 0;
3935 else
3936 val = s->uATARegStatus;
3937
3938 /* Give the async I/O thread an opportunity to make progress,
3939 * don't let it starve by guests polling frequently. EMT has a
3940 * lower priority than the async I/O thread, but sometimes the
3941 * host OS doesn't care. With some guests we are only allowed to
3942 * be busy for about 5 milliseconds in some situations. Note that
3943 * this is no guarantee for any other VBox thread getting
3944 * scheduled, so this just lowers the CPU load a bit when drives
3945 * are busy. It cannot help with timing problems. */
3946 if (val & ATA_STAT_BUSY)
3947 {
3948#ifdef IN_RING3
3949 cBusy = 0;
3950 PDMCritSectLeave(&pCtl->lock);
3951
3952#ifndef RT_OS_WINDOWS
3953 /*
3954 * The thread might be stuck in an I/O operation
3955 * due to a high I/O load on the host. (see @bugref{3301})
3956 * To perform the reset successfully
3957 * we interrupt the operation by sending a signal to the thread
3958 * if the thread didn't responded in 10ms.
3959 * This works only on POSIX hosts (Windows has a CancelSynchronousIo function which
3960 * does the same but it was introduced with Vista) but so far
3961 * this hang was only observed on Linux and Mac OS X.
3962 *
3963 * This is a workaround and needs to be solved properly.
3964 */
3965 if (pCtl->fReset)
3966 {
3967 uint64_t u64ResetTimeStop = RTTimeMilliTS();
3968
3969 if ((u64ResetTimeStop - pCtl->u64ResetTime) >= 10)
3970 {
3971 LogRel(("PIIX3 ATA: Async I/O thread probably stuck in operation, interrupting\n"));
3972 pCtl->u64ResetTime = u64ResetTimeStop;
3973 RTThreadPoke(pCtl->AsyncIOThread);
3974 }
3975 }
3976#endif
3977
3978 RTThreadYield();
3979
3980 {
3981 STAM_PROFILE_START(&pCtl->StatLockWait, a);
3982 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
3983 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
3984 }
3985
3986 val = s->uATARegStatus;
3987#else /* !IN_RING3 */
3988 /* Cannot yield CPU in guest context. And switching to host
3989 * context for each and every busy status is too costly,
3990 * especially on SMP systems where we don't gain much by
3991 * yielding the CPU to someone else. */
3992 if (++cBusy >= 20)
3993 {
3994 cBusy = 0;
3995 return VINF_IOM_HC_IOPORT_READ;
3996 }
3997#endif /* !IN_RING3 */
3998 }
3999 else
4000 cBusy = 0;
4001 ataUnsetIRQ(s);
4002 break;
4003 }
4004 }
4005 Log2(("%s: addr=%#x val=%#04x\n", __FUNCTION__, addr, val));
4006 *pu32 = val;
4007 return VINF_SUCCESS;
4008}
4009
4010
4011static uint32_t ataStatusRead(PATACONTROLLER pCtl, uint32_t addr)
4012{
4013 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
4014 uint32_t val;
4015
4016 if ((!pCtl->aIfs[0].pDrvBlock && !pCtl->aIfs[1].pDrvBlock) ||
4017 (pCtl->iSelectedIf == 1 && !s->pDrvBlock))
4018 val = 0;
4019 else
4020 val = s->uATARegStatus;
4021 Log2(("%s: addr=%#x val=%#04x\n", __FUNCTION__, addr, val));
4022 return val;
4023}
4024
4025static int ataControlWrite(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
4026{
4027#ifndef IN_RING3
4028 if ((val ^ pCtl->aIfs[0].uATARegDevCtl) & ATA_DEVCTL_RESET)
4029 return VINF_IOM_HC_IOPORT_WRITE; /* The RESET stuff is too complicated for GC. */
4030#endif /* !IN_RING3 */
4031
4032 Log2(("%s: addr=%#x val=%#04x\n", __FUNCTION__, addr, val));
4033 /* RESET is common for both drives attached to a controller. */
4034 if (!(pCtl->aIfs[0].uATARegDevCtl & ATA_DEVCTL_RESET) &&
4035 (val & ATA_DEVCTL_RESET))
4036 {
4037#ifdef IN_RING3
4038 /* Software RESET low to high */
4039 int32_t uCmdWait0 = -1, uCmdWait1 = -1;
4040 uint64_t uNow = RTTimeNanoTS();
4041 if (pCtl->aIfs[0].u64CmdTS)
4042 uCmdWait0 = (uNow - pCtl->aIfs[0].u64CmdTS) / 1000;
4043 if (pCtl->aIfs[1].u64CmdTS)
4044 uCmdWait1 = (uNow - pCtl->aIfs[1].u64CmdTS) / 1000;
4045 LogRel(("PIIX3 ATA: Ctl#%d: RESET, DevSel=%d AIOIf=%d CmdIf0=%#04x (%d usec ago) CmdIf1=%#04x (%d usec ago)\n",
4046 ATACONTROLLER_IDX(pCtl), pCtl->iSelectedIf, pCtl->iAIOIf,
4047 pCtl->aIfs[0].uATARegCommand, uCmdWait0,
4048 pCtl->aIfs[1].uATARegCommand, uCmdWait1));
4049 pCtl->fReset = true;
4050 /* Everything must be done after the reset flag is set, otherwise
4051 * there are unavoidable races with the currently executing request
4052 * (which might just finish in the mean time). */
4053 pCtl->fChainedTransfer = false;
4054 for (uint32_t i = 0; i < RT_ELEMENTS(pCtl->aIfs); i++)
4055 {
4056 ataResetDevice(&pCtl->aIfs[i]);
4057 /* The following cannot be done using ataSetStatusValue() since the
4058 * reset flag is already set, which suppresses all status changes. */
4059 pCtl->aIfs[i].uATARegStatus = ATA_STAT_BUSY | ATA_STAT_SEEK;
4060 Log2(("%s: LUN#%d status %#04x\n", __FUNCTION__, pCtl->aIfs[i].iLUN, pCtl->aIfs[i].uATARegStatus));
4061 pCtl->aIfs[i].uATARegError = 0x01;
4062 }
4063 ataAsyncIOClearRequests(pCtl);
4064 Log2(("%s: Ctl#%d: message to async I/O thread, resetA\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4065 if (val & ATA_DEVCTL_HOB)
4066 {
4067 val &= ~ATA_DEVCTL_HOB;
4068 Log2(("%s: ignored setting HOB\n", __FUNCTION__));
4069 }
4070
4071 /* Save the timestamp we started the reset. */
4072 pCtl->u64ResetTime = RTTimeMilliTS();
4073
4074 /* Issue the reset request now. */
4075 ataAsyncIOPutRequest(pCtl, &g_ataResetARequest);
4076#else /* !IN_RING3 */
4077 AssertMsgFailed(("RESET handling is too complicated for GC\n"));
4078#endif /* IN_RING3 */
4079 }
4080 else if ((pCtl->aIfs[0].uATARegDevCtl & ATA_DEVCTL_RESET) &&
4081 !(val & ATA_DEVCTL_RESET))
4082 {
4083#ifdef IN_RING3
4084 /* Software RESET high to low */
4085 Log(("%s: deasserting RESET\n", __FUNCTION__));
4086 Log2(("%s: Ctl#%d: message to async I/O thread, resetC\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4087 if (val & ATA_DEVCTL_HOB)
4088 {
4089 val &= ~ATA_DEVCTL_HOB;
4090 Log2(("%s: ignored setting HOB\n", __FUNCTION__));
4091 }
4092 ataAsyncIOPutRequest(pCtl, &g_ataResetCRequest);
4093#else /* !IN_RING3 */
4094 AssertMsgFailed(("RESET handling is too complicated for GC\n"));
4095#endif /* IN_RING3 */
4096 }
4097
4098 /* Change of interrupt disable flag. Update interrupt line if interrupt
4099 * is pending on the current interface. */
4100 if ((val ^ pCtl->aIfs[0].uATARegDevCtl) & ATA_DEVCTL_DISABLE_IRQ
4101 && pCtl->aIfs[pCtl->iSelectedIf].fIrqPending)
4102 {
4103 if (!(val & ATA_DEVCTL_DISABLE_IRQ))
4104 {
4105 Log2(("%s: LUN#%d asserting IRQ (interrupt disable change)\n", __FUNCTION__, pCtl->aIfs[pCtl->iSelectedIf].iLUN));
4106 /* The BMDMA unit unconditionally sets BM_STATUS_INT if the
4107 * interrupt line is asserted. It monitors the line for a rising
4108 * edge. */
4109 pCtl->BmDma.u8Status |= BM_STATUS_INT;
4110 if (pCtl->irq == 16)
4111 PDMDevHlpPCISetIrqNoWait(CONTROLLER_2_DEVINS(pCtl), 0, 1);
4112 else
4113 PDMDevHlpISASetIrqNoWait(CONTROLLER_2_DEVINS(pCtl), pCtl->irq, 1);
4114 }
4115 else
4116 {
4117 Log2(("%s: LUN#%d deasserting IRQ (interrupt disable change)\n", __FUNCTION__, pCtl->aIfs[pCtl->iSelectedIf].iLUN));
4118 if (pCtl->irq == 16)
4119 PDMDevHlpPCISetIrqNoWait(CONTROLLER_2_DEVINS(pCtl), 0, 0);
4120 else
4121 PDMDevHlpISASetIrqNoWait(CONTROLLER_2_DEVINS(pCtl), pCtl->irq, 0);
4122 }
4123 }
4124
4125 if (val & ATA_DEVCTL_HOB)
4126 Log2(("%s: set HOB\n", __FUNCTION__));
4127
4128 pCtl->aIfs[0].uATARegDevCtl = val;
4129 pCtl->aIfs[1].uATARegDevCtl = val;
4130
4131 return VINF_SUCCESS;
4132}
4133
4134#ifdef IN_RING3
4135
4136static void ataPIOTransfer(PATACONTROLLER pCtl)
4137{
4138 ATADevState *s;
4139
4140 s = &pCtl->aIfs[pCtl->iAIOIf];
4141 Log3(("%s: if=%p\n", __FUNCTION__, s));
4142
4143 if (s->cbTotalTransfer && s->iIOBufferCur > s->iIOBufferEnd)
4144 {
4145 LogRel(("PIIX3 ATA: LUN#%d: %s data in the middle of a PIO transfer - VERY SLOW\n", s->iLUN, s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE ? "loading" : "storing"));
4146 /* Any guest OS that triggers this case has a pathetic ATA driver.
4147 * In a real system it would block the CPU via IORDY, here we do it
4148 * very similarly by not continuing with the current instruction
4149 * until the transfer to/from the storage medium is completed. */
4150 if (s->iSourceSink != ATAFN_SS_NULL)
4151 {
4152 bool fRedo;
4153 uint8_t status = s->uATARegStatus;
4154 ataSetStatusValue(s, ATA_STAT_BUSY);
4155 Log2(("%s: calling source/sink function\n", __FUNCTION__));
4156 fRedo = g_apfnSourceSinkFuncs[s->iSourceSink](s);
4157 pCtl->fRedo = fRedo;
4158 if (RT_UNLIKELY(fRedo))
4159 return;
4160 ataSetStatusValue(s, status);
4161 s->iIOBufferCur = 0;
4162 s->iIOBufferEnd = s->cbElementaryTransfer;
4163 }
4164 }
4165 if (s->cbTotalTransfer)
4166 {
4167 if (s->fATAPITransfer)
4168 ataPIOTransferLimitATAPI(s);
4169
4170 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE && s->cbElementaryTransfer > s->cbTotalTransfer)
4171 s->cbElementaryTransfer = s->cbTotalTransfer;
4172
4173 Log2(("%s: %s tx_size=%d elem_tx_size=%d index=%d end=%d\n",
4174 __FUNCTION__, s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE ? "T2I" : "I2T",
4175 s->cbTotalTransfer, s->cbElementaryTransfer,
4176 s->iIOBufferCur, s->iIOBufferEnd));
4177 ataPIOTransferStart(s, s->iIOBufferCur, s->cbElementaryTransfer);
4178 s->cbTotalTransfer -= s->cbElementaryTransfer;
4179 s->iIOBufferCur += s->cbElementaryTransfer;
4180
4181 if (s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE && s->cbElementaryTransfer > s->cbTotalTransfer)
4182 s->cbElementaryTransfer = s->cbTotalTransfer;
4183 }
4184 else
4185 ataPIOTransferStop(s);
4186}
4187
4188
4189DECLINLINE(void) ataPIOTransferFinish(PATACONTROLLER pCtl, ATADevState *s)
4190{
4191 /* Do not interfere with RESET processing if the PIO transfer finishes
4192 * while the RESET line is asserted. */
4193 if (pCtl->fReset)
4194 {
4195 Log2(("%s: Ctl#%d: suppressed continuing PIO transfer as RESET is active\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4196 return;
4197 }
4198
4199 if ( s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE
4200 || ( s->iSourceSink != ATAFN_SS_NULL
4201 && s->iIOBufferCur >= s->iIOBufferEnd))
4202 {
4203 /* Need to continue the transfer in the async I/O thread. This is
4204 * the case for write operations or generally for not yet finished
4205 * transfers (some data might need to be read). */
4206 ataUnsetStatus(s, ATA_STAT_READY | ATA_STAT_DRQ);
4207 ataSetStatus(s, ATA_STAT_BUSY);
4208
4209 Log2(("%s: Ctl#%d: message to async I/O thread, continuing PIO transfer\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4210 ataAsyncIOPutRequest(pCtl, &g_ataPIORequest);
4211 }
4212 else
4213 {
4214 /* Either everything finished (though some data might still be pending)
4215 * or some data is pending before the next read is due. */
4216
4217 /* Continue a previously started transfer. */
4218 ataUnsetStatus(s, ATA_STAT_DRQ);
4219 ataSetStatus(s, ATA_STAT_READY);
4220
4221 if (s->cbTotalTransfer)
4222 {
4223 /* There is more to transfer, happens usually for large ATAPI
4224 * reads - the protocol limits the chunk size to 65534 bytes. */
4225 ataPIOTransfer(pCtl);
4226 ataSetIRQ(s);
4227 }
4228 else
4229 {
4230 Log2(("%s: Ctl#%d: skipping message to async I/O thread, ending PIO transfer\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4231 /* Finish PIO transfer. */
4232 ataPIOTransfer(pCtl);
4233 Assert(!pCtl->fRedo);
4234 }
4235 }
4236}
4237
4238#endif /* IN_RING3 */
4239
4240static int ataDataWrite(PATACONTROLLER pCtl, uint32_t addr, uint32_t cbSize, const uint8_t *pbBuf)
4241{
4242 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
4243 uint8_t *p;
4244
4245 if (s->iIOBufferPIODataStart < s->iIOBufferPIODataEnd)
4246 {
4247 Assert(s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE);
4248 p = s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart;
4249#ifndef IN_RING3
4250 /* All but the last transfer unit is simple enough for GC, but
4251 * sending a request to the async IO thread is too complicated. */
4252 if (s->iIOBufferPIODataStart + cbSize < s->iIOBufferPIODataEnd)
4253 {
4254 memcpy(p, pbBuf, cbSize);
4255 s->iIOBufferPIODataStart += cbSize;
4256 }
4257 else
4258 return VINF_IOM_HC_IOPORT_WRITE;
4259#else /* IN_RING3 */
4260 memcpy(p, pbBuf, cbSize);
4261 s->iIOBufferPIODataStart += cbSize;
4262 if (s->iIOBufferPIODataStart >= s->iIOBufferPIODataEnd)
4263 ataPIOTransferFinish(pCtl, s);
4264#endif /* !IN_RING3 */
4265 }
4266 else
4267 Log2(("%s: DUMMY data\n", __FUNCTION__));
4268 Log3(("%s: addr=%#x val=%.*Rhxs\n", __FUNCTION__, addr, cbSize, pbBuf));
4269 return VINF_SUCCESS;
4270}
4271
4272static int ataDataRead(PATACONTROLLER pCtl, uint32_t addr, uint32_t cbSize, uint8_t *pbBuf)
4273{
4274 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
4275 uint8_t *p;
4276
4277 if (s->iIOBufferPIODataStart < s->iIOBufferPIODataEnd)
4278 {
4279 Assert(s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE);
4280 p = s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart;
4281#ifndef IN_RING3
4282 /* All but the last transfer unit is simple enough for GC, but
4283 * sending a request to the async IO thread is too complicated. */
4284 if (s->iIOBufferPIODataStart + cbSize < s->iIOBufferPIODataEnd)
4285 {
4286 memcpy(pbBuf, p, cbSize);
4287 s->iIOBufferPIODataStart += cbSize;
4288 }
4289 else
4290 return VINF_IOM_HC_IOPORT_READ;
4291#else /* IN_RING3 */
4292 memcpy(pbBuf, p, cbSize);
4293 s->iIOBufferPIODataStart += cbSize;
4294 if (s->iIOBufferPIODataStart >= s->iIOBufferPIODataEnd)
4295 ataPIOTransferFinish(pCtl, s);
4296#endif /* !IN_RING3 */
4297 }
4298 else
4299 {
4300 Log2(("%s: DUMMY data\n", __FUNCTION__));
4301 memset(pbBuf, '\xff', cbSize);
4302 }
4303 Log3(("%s: addr=%#x val=%.*Rhxs\n", __FUNCTION__, addr, cbSize, pbBuf));
4304 return VINF_SUCCESS;
4305}
4306
4307#ifdef IN_RING3
4308
4309static void ataDMATransferStop(ATADevState *s)
4310{
4311 s->cbTotalTransfer = 0;
4312 s->cbElementaryTransfer = 0;
4313 s->iBeginTransfer = ATAFN_BT_NULL;
4314 s->iSourceSink = ATAFN_SS_NULL;
4315}
4316
4317
4318/**
4319 * Perform the entire DMA transfer in one go (unless a source/sink operation
4320 * has to be redone or a RESET comes in between). Unlike the PIO counterpart
4321 * this function cannot handle empty transfers.
4322 *
4323 * @param pCtl Controller for which to perform the transfer.
4324 */
4325static void ataDMATransfer(PATACONTROLLER pCtl)
4326{
4327 PPDMDEVINS pDevIns = CONTROLLER_2_DEVINS(pCtl);
4328 ATADevState *s = &pCtl->aIfs[pCtl->iAIOIf];
4329 bool fRedo;
4330 RTGCPHYS32 pDesc;
4331 uint32_t cbTotalTransfer, cbElementaryTransfer;
4332 uint32_t iIOBufferCur, iIOBufferEnd;
4333 uint32_t dmalen;
4334 PDMBLOCKTXDIR uTxDir;
4335 bool fLastDesc = false;
4336
4337 Assert(sizeof(BMDMADesc) == 8);
4338
4339 fRedo = pCtl->fRedo;
4340 if (RT_LIKELY(!fRedo))
4341 Assert(s->cbTotalTransfer);
4342 uTxDir = (PDMBLOCKTXDIR)s->uTxDir;
4343 cbTotalTransfer = s->cbTotalTransfer;
4344 cbElementaryTransfer = s->cbElementaryTransfer;
4345 iIOBufferCur = s->iIOBufferCur;
4346 iIOBufferEnd = s->iIOBufferEnd;
4347
4348 /* The DMA loop is designed to hold the lock only when absolutely
4349 * necessary. This avoids long freezes should the guest access the
4350 * ATA registers etc. for some reason. */
4351 PDMCritSectLeave(&pCtl->lock);
4352
4353 Log2(("%s: %s tx_size=%d elem_tx_size=%d index=%d end=%d\n",
4354 __FUNCTION__, uTxDir == PDMBLOCKTXDIR_FROM_DEVICE ? "T2I" : "I2T",
4355 cbTotalTransfer, cbElementaryTransfer,
4356 iIOBufferCur, iIOBufferEnd));
4357 for (pDesc = pCtl->pFirstDMADesc; pDesc <= pCtl->pLastDMADesc; pDesc += sizeof(BMDMADesc))
4358 {
4359 BMDMADesc DMADesc;
4360 RTGCPHYS32 pBuffer;
4361 uint32_t cbBuffer;
4362
4363 if (RT_UNLIKELY(fRedo))
4364 {
4365 pBuffer = pCtl->pRedoDMABuffer;
4366 cbBuffer = pCtl->cbRedoDMABuffer;
4367 fLastDesc = pCtl->fRedoDMALastDesc;
4368 }
4369 else
4370 {
4371 PDMDevHlpPhysRead(pDevIns, pDesc, &DMADesc, sizeof(BMDMADesc));
4372 pBuffer = RT_LE2H_U32(DMADesc.pBuffer);
4373 cbBuffer = RT_LE2H_U32(DMADesc.cbBuffer);
4374 fLastDesc = !!(cbBuffer & 0x80000000);
4375 cbBuffer &= 0xfffe;
4376 if (cbBuffer == 0)
4377 cbBuffer = 0x10000;
4378 if (cbBuffer > cbTotalTransfer)
4379 cbBuffer = cbTotalTransfer;
4380 }
4381
4382 while (RT_UNLIKELY(fRedo) || (cbBuffer && cbTotalTransfer))
4383 {
4384 if (RT_LIKELY(!fRedo))
4385 {
4386 dmalen = RT_MIN(cbBuffer, iIOBufferEnd - iIOBufferCur);
4387 Log2(("%s: DMA desc %#010x: addr=%#010x size=%#010x\n", __FUNCTION__,
4388 (int)pDesc, pBuffer, cbBuffer));
4389 if (uTxDir == PDMBLOCKTXDIR_FROM_DEVICE)
4390 PDMDevHlpPhysWrite(pDevIns, pBuffer, s->CTX_SUFF(pbIOBuffer) + iIOBufferCur, dmalen);
4391 else
4392 PDMDevHlpPhysRead(pDevIns, pBuffer, s->CTX_SUFF(pbIOBuffer) + iIOBufferCur, dmalen);
4393 iIOBufferCur += dmalen;
4394 cbTotalTransfer -= dmalen;
4395 cbBuffer -= dmalen;
4396 pBuffer += dmalen;
4397 }
4398 if ( iIOBufferCur == iIOBufferEnd
4399 && (uTxDir == PDMBLOCKTXDIR_TO_DEVICE || cbTotalTransfer))
4400 {
4401 if (uTxDir == PDMBLOCKTXDIR_FROM_DEVICE && cbElementaryTransfer > cbTotalTransfer)
4402 cbElementaryTransfer = cbTotalTransfer;
4403
4404 {
4405 STAM_PROFILE_START(&pCtl->StatLockWait, a);
4406 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
4407 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
4408 }
4409
4410 /* The RESET handler could have cleared the DMA transfer
4411 * state (since we didn't hold the lock until just now
4412 * the guest can continue in parallel). If so, the state
4413 * is already set up so the loop is exited immediately. */
4414 if (s->iSourceSink != ATAFN_SS_NULL)
4415 {
4416 s->iIOBufferCur = iIOBufferCur;
4417 s->iIOBufferEnd = iIOBufferEnd;
4418 s->cbElementaryTransfer = cbElementaryTransfer;
4419 s->cbTotalTransfer = cbTotalTransfer;
4420 Log2(("%s: calling source/sink function\n", __FUNCTION__));
4421 fRedo = g_apfnSourceSinkFuncs[s->iSourceSink](s);
4422 if (RT_UNLIKELY(fRedo))
4423 {
4424 pCtl->pFirstDMADesc = pDesc;
4425 pCtl->pRedoDMABuffer = pBuffer;
4426 pCtl->cbRedoDMABuffer = cbBuffer;
4427 pCtl->fRedoDMALastDesc = fLastDesc;
4428 }
4429 else
4430 {
4431 cbTotalTransfer = s->cbTotalTransfer;
4432 cbElementaryTransfer = s->cbElementaryTransfer;
4433
4434 if (uTxDir == PDMBLOCKTXDIR_TO_DEVICE && cbElementaryTransfer > cbTotalTransfer)
4435 cbElementaryTransfer = cbTotalTransfer;
4436 iIOBufferCur = 0;
4437 iIOBufferEnd = cbElementaryTransfer;
4438 }
4439 pCtl->fRedo = fRedo;
4440 }
4441 else
4442 {
4443 /* This forces the loop to exit immediately. */
4444 pDesc = pCtl->pLastDMADesc + 1;
4445 }
4446
4447 PDMCritSectLeave(&pCtl->lock);
4448 if (RT_UNLIKELY(fRedo))
4449 break;
4450 }
4451 }
4452
4453 if (RT_UNLIKELY(fRedo))
4454 break;
4455
4456 /* end of transfer */
4457 if (!cbTotalTransfer || fLastDesc)
4458 break;
4459
4460 {
4461 STAM_PROFILE_START(&pCtl->StatLockWait, a);
4462 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
4463 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
4464 }
4465
4466 if (!(pCtl->BmDma.u8Cmd & BM_CMD_START) || pCtl->fReset)
4467 {
4468 LogRel(("PIIX3 ATA: Ctl#%d: ABORT DMA%s\n", ATACONTROLLER_IDX(pCtl), pCtl->fReset ? " due to RESET" : ""));
4469 if (!pCtl->fReset)
4470 ataDMATransferStop(s);
4471 /* This forces the loop to exit immediately. */
4472 pDesc = pCtl->pLastDMADesc + 1;
4473 }
4474
4475 PDMCritSectLeave(&pCtl->lock);
4476 }
4477
4478 {
4479 STAM_PROFILE_START(&pCtl->StatLockWait, a);
4480 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
4481 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
4482 }
4483
4484 if (RT_UNLIKELY(fRedo))
4485 return;
4486
4487 if (fLastDesc)
4488 pCtl->BmDma.u8Status &= ~BM_STATUS_DMAING;
4489 s->cbTotalTransfer = cbTotalTransfer;
4490 s->cbElementaryTransfer = cbElementaryTransfer;
4491 s->iIOBufferCur = iIOBufferCur;
4492 s->iIOBufferEnd = iIOBufferEnd;
4493}
4494
4495/**
4496 * Signal PDM that we're idle (if we actually are).
4497 *
4498 * @param pCtl The controller.
4499 */
4500static void ataR3AsyncSignalIdle(PATACONTROLLER pCtl)
4501{
4502 /*
4503 * Take the mutex here and recheck the idle indicator to avoid
4504 * unnecessary work and racing ataR3WaitForAsyncIOIsIdle.
4505 */
4506 int rc = RTSemMutexRequest(pCtl->AsyncIORequestMutex, RT_INDEFINITE_WAIT); AssertRC(rc);
4507
4508 if ( pCtl->fSignalIdle
4509 && ataAsyncIOIsIdle(pCtl, false /*fStrict*/))
4510 {
4511 PDMDevHlpAsyncNotificationCompleted(pCtl->pDevInsR3);
4512 RTThreadUserSignal(pCtl->AsyncIOThread); /* for ataR3Construct/ataR3ResetCommon. */
4513 }
4514
4515 rc = RTSemMutexRelease(pCtl->AsyncIORequestMutex); AssertRC(rc);
4516}
4517
4518/** Asynch I/O thread for an interface. Once upon a time this was readable
4519 * code with several loops and a different semaphore for each purpose. But
4520 * then came the "how can one save the state in the middle of a PIO transfer"
4521 * question. The solution was to use an ASM, which is what's there now. */
4522static DECLCALLBACK(int) ataAsyncIOLoop(RTTHREAD ThreadSelf, void *pvUser)
4523{
4524 const ATARequest *pReq;
4525 uint64_t u64TS = 0; /* shut up gcc */
4526 uint64_t uWait;
4527 int rc = VINF_SUCCESS;
4528 PATACONTROLLER pCtl = (PATACONTROLLER)pvUser;
4529 ATADevState *s;
4530
4531 pReq = NULL;
4532 pCtl->fChainedTransfer = false;
4533 while (!pCtl->fShutdown)
4534 {
4535 /* Keep this thread from doing anything as long as EMT is suspended. */
4536 while (pCtl->fRedoIdle)
4537 {
4538 if (pCtl->fSignalIdle)
4539 ataR3AsyncSignalIdle(pCtl);
4540 rc = RTSemEventWait(pCtl->SuspendIOSem, RT_INDEFINITE_WAIT);
4541 /* Continue if we got a signal by RTThreadPoke().
4542 * We will get notified if there is a request to process.
4543 */
4544 if (RT_UNLIKELY(rc == VERR_INTERRUPTED))
4545 continue;
4546 if (RT_FAILURE(rc) || pCtl->fShutdown)
4547 break;
4548
4549 pCtl->fRedoIdle = false;
4550 }
4551
4552 /* Wait for work. */
4553 while (pReq == NULL)
4554 {
4555 if (pCtl->fSignalIdle)
4556 ataR3AsyncSignalIdle(pCtl);
4557 rc = RTSemEventWait(pCtl->AsyncIOSem, RT_INDEFINITE_WAIT);
4558 /* Continue if we got a signal by RTThreadPoke().
4559 * We will get notified if there is a request to process.
4560 */
4561 if (RT_UNLIKELY(rc == VERR_INTERRUPTED))
4562 continue;
4563 if (RT_FAILURE(rc) || RT_UNLIKELY(pCtl->fShutdown))
4564 break;
4565
4566 pReq = ataAsyncIOGetCurrentRequest(pCtl);
4567 }
4568
4569 if (RT_FAILURE(rc) || pCtl->fShutdown)
4570 break;
4571
4572 if (pReq == NULL)
4573 continue;
4574
4575 ATAAIO ReqType = pReq->ReqType;
4576
4577 Log2(("%s: Ctl#%d: state=%d, req=%d\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), pCtl->uAsyncIOState, ReqType));
4578 if (pCtl->uAsyncIOState != ReqType)
4579 {
4580 /* The new state is not the state that was expected by the normal
4581 * state changes. This is either a RESET/ABORT or there's something
4582 * really strange going on. */
4583 if ( (pCtl->uAsyncIOState == ATA_AIO_PIO || pCtl->uAsyncIOState == ATA_AIO_DMA)
4584 && (ReqType == ATA_AIO_PIO || ReqType == ATA_AIO_DMA))
4585 {
4586 /* Incorrect sequence of PIO/DMA states. Dump request queue. */
4587 ataAsyncIODumpRequests(pCtl);
4588 }
4589 AssertReleaseMsg(ReqType == ATA_AIO_RESET_ASSERTED || ReqType == ATA_AIO_RESET_CLEARED || ReqType == ATA_AIO_ABORT || pCtl->uAsyncIOState == ReqType, ("I/O state inconsistent: state=%d request=%d\n", pCtl->uAsyncIOState, ReqType));
4590 }
4591
4592 /* Do our work. */
4593 {
4594 STAM_PROFILE_START(&pCtl->StatLockWait, a);
4595 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
4596 STAM_PROFILE_STOP(&pCtl->StatLockWait, a);
4597 }
4598
4599 if (pCtl->uAsyncIOState == ATA_AIO_NEW && !pCtl->fChainedTransfer)
4600 {
4601 u64TS = RTTimeNanoTS();
4602#if defined(DEBUG) || defined(VBOX_WITH_STATISTICS)
4603 STAM_PROFILE_ADV_START(&pCtl->StatAsyncTime, a);
4604#endif /* DEBUG || VBOX_WITH_STATISTICS */
4605 }
4606
4607 switch (ReqType)
4608 {
4609 case ATA_AIO_NEW:
4610
4611 pCtl->iAIOIf = pReq->u.t.iIf;
4612 s = &pCtl->aIfs[pCtl->iAIOIf];
4613 s->cbTotalTransfer = pReq->u.t.cbTotalTransfer;
4614 s->uTxDir = pReq->u.t.uTxDir;
4615 s->iBeginTransfer = pReq->u.t.iBeginTransfer;
4616 s->iSourceSink = pReq->u.t.iSourceSink;
4617 s->iIOBufferEnd = 0;
4618 s->u64CmdTS = u64TS;
4619
4620 if (s->fATAPI)
4621 {
4622 if (pCtl->fChainedTransfer)
4623 {
4624 /* Only count the actual transfers, not the PIO
4625 * transfer of the ATAPI command bytes. */
4626 if (s->fDMA)
4627 STAM_REL_COUNTER_INC(&s->StatATAPIDMA);
4628 else
4629 STAM_REL_COUNTER_INC(&s->StatATAPIPIO);
4630 }
4631 }
4632 else
4633 {
4634 if (s->fDMA)
4635 STAM_REL_COUNTER_INC(&s->StatATADMA);
4636 else
4637 STAM_REL_COUNTER_INC(&s->StatATAPIO);
4638 }
4639
4640 pCtl->fChainedTransfer = false;
4641
4642 if (s->iBeginTransfer != ATAFN_BT_NULL)
4643 {
4644 Log2(("%s: Ctl#%d: calling begin transfer function\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4645 g_apfnBeginTransFuncs[s->iBeginTransfer](s);
4646 s->iBeginTransfer = ATAFN_BT_NULL;
4647 if (s->uTxDir != PDMBLOCKTXDIR_FROM_DEVICE)
4648 s->iIOBufferEnd = s->cbElementaryTransfer;
4649 }
4650 else
4651 {
4652 s->cbElementaryTransfer = s->cbTotalTransfer;
4653 s->iIOBufferEnd = s->cbTotalTransfer;
4654 }
4655 s->iIOBufferCur = 0;
4656
4657 if (s->uTxDir != PDMBLOCKTXDIR_TO_DEVICE)
4658 {
4659 if (s->iSourceSink != ATAFN_SS_NULL)
4660 {
4661 bool fRedo;
4662 Log2(("%s: Ctl#%d: calling source/sink function\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4663 fRedo = g_apfnSourceSinkFuncs[s->iSourceSink](s);
4664 pCtl->fRedo = fRedo;
4665 if (RT_UNLIKELY(fRedo && !pCtl->fReset))
4666 {
4667 /* Operation failed at the initial transfer, restart
4668 * everything from scratch by resending the current
4669 * request. Occurs very rarely, not worth optimizing. */
4670 LogRel(("%s: Ctl#%d: redo entire operation\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4671 ataAsyncIOPutRequest(pCtl, pReq);
4672 break;
4673 }
4674 }
4675 else
4676 ataCmdOK(s, 0);
4677 s->iIOBufferEnd = s->cbElementaryTransfer;
4678
4679 }
4680
4681 /* Do not go into the transfer phase if RESET is asserted.
4682 * The CritSect is released while waiting for the host OS
4683 * to finish the I/O, thus RESET is possible here. Most
4684 * important: do not change uAsyncIOState. */
4685 if (pCtl->fReset)
4686 break;
4687
4688 if (s->fDMA)
4689 {
4690 if (s->cbTotalTransfer)
4691 {
4692 ataSetStatus(s, ATA_STAT_DRQ);
4693
4694 pCtl->uAsyncIOState = ATA_AIO_DMA;
4695 /* If BMDMA is already started, do the transfer now. */
4696 if (pCtl->BmDma.u8Cmd & BM_CMD_START)
4697 {
4698 Log2(("%s: Ctl#%d: message to async I/O thread, continuing DMA transfer immediately\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4699 ataAsyncIOPutRequest(pCtl, &g_ataDMARequest);
4700 }
4701 }
4702 else
4703 {
4704 Assert(s->uTxDir == PDMBLOCKTXDIR_NONE); /* Any transfer which has an initial transfer size of 0 must be marked as such. */
4705 /* Finish DMA transfer. */
4706 ataDMATransferStop(s);
4707 ataSetIRQ(s);
4708 pCtl->uAsyncIOState = ATA_AIO_NEW;
4709 }
4710 }
4711 else
4712 {
4713 if (s->cbTotalTransfer)
4714 {
4715 ataPIOTransfer(pCtl);
4716 Assert(!pCtl->fRedo);
4717 if (s->fATAPITransfer || s->uTxDir != PDMBLOCKTXDIR_TO_DEVICE)
4718 ataSetIRQ(s);
4719
4720 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE || s->iSourceSink != ATAFN_SS_NULL)
4721 {
4722 /* Write operations and not yet finished transfers
4723 * must be completed in the async I/O thread. */
4724 pCtl->uAsyncIOState = ATA_AIO_PIO;
4725 }
4726 else
4727 {
4728 /* Finished read operation can be handled inline
4729 * in the end of PIO transfer handling code. Linux
4730 * depends on this, as it waits only briefly for
4731 * devices to become ready after incoming data
4732 * transfer. Cannot find anything in the ATA spec
4733 * that backs this assumption, but as all kernels
4734 * are affected (though most of the time it does
4735 * not cause any harm) this must work. */
4736 pCtl->uAsyncIOState = ATA_AIO_NEW;
4737 }
4738 }
4739 else
4740 {
4741 Assert(s->uTxDir == PDMBLOCKTXDIR_NONE); /* Any transfer which has an initial transfer size of 0 must be marked as such. */
4742 /* Finish PIO transfer. */
4743 ataPIOTransfer(pCtl);
4744 Assert(!pCtl->fRedo);
4745 if (!s->fATAPITransfer)
4746 ataSetIRQ(s);
4747 pCtl->uAsyncIOState = ATA_AIO_NEW;
4748 }
4749 }
4750 break;
4751
4752 case ATA_AIO_DMA:
4753 {
4754 BMDMAState *bm = &pCtl->BmDma;
4755 s = &pCtl->aIfs[pCtl->iAIOIf]; /* Do not remove or there's an instant crash after loading the saved state */
4756 ATAFNSS iOriginalSourceSink = (ATAFNSS)s->iSourceSink; /* Used by the hack below, but gets reset by then. */
4757
4758 if (s->uTxDir == PDMBLOCKTXDIR_FROM_DEVICE)
4759 AssertRelease(bm->u8Cmd & BM_CMD_WRITE);
4760 else
4761 AssertRelease(!(bm->u8Cmd & BM_CMD_WRITE));
4762
4763 if (RT_LIKELY(!pCtl->fRedo))
4764 {
4765 /* The specs say that the descriptor table must not cross a
4766 * 4K boundary. */
4767 pCtl->pFirstDMADesc = bm->pvAddr;
4768 pCtl->pLastDMADesc = RT_ALIGN_32(bm->pvAddr + 1, _4K) - sizeof(BMDMADesc);
4769 }
4770 ataDMATransfer(pCtl);
4771
4772 if (RT_UNLIKELY(pCtl->fRedo && !pCtl->fReset))
4773 {
4774 LogRel(("PIIX3 ATA: Ctl#%d: redo DMA operation\n", ATACONTROLLER_IDX(pCtl)));
4775 ataAsyncIOPutRequest(pCtl, &g_ataDMARequest);
4776 break;
4777 }
4778
4779 /* The infamous delay IRQ hack. */
4780 if ( iOriginalSourceSink == ATAFN_SS_WRITE_SECTORS
4781 && s->cbTotalTransfer == 0
4782 && pCtl->DelayIRQMillies)
4783 {
4784 /* Delay IRQ for writing. Required to get the Win2K
4785 * installation work reliably (otherwise it crashes,
4786 * usually during component install). So far no better
4787 * solution has been found. */
4788 Log(("%s: delay IRQ hack\n", __FUNCTION__));
4789 PDMCritSectLeave(&pCtl->lock);
4790 RTThreadSleep(pCtl->DelayIRQMillies);
4791 PDMCritSectEnter(&pCtl->lock, VINF_SUCCESS);
4792 }
4793
4794 ataUnsetStatus(s, ATA_STAT_DRQ);
4795 Assert(!pCtl->fChainedTransfer);
4796 Assert(s->iSourceSink == ATAFN_SS_NULL);
4797 if (s->fATAPITransfer)
4798 {
4799 s->uATARegNSector = (s->uATARegNSector & ~7) | ATAPI_INT_REASON_IO | ATAPI_INT_REASON_CD;
4800 Log2(("%s: Ctl#%d: interrupt reason %#04x\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), s->uATARegNSector));
4801 s->fATAPITransfer = false;
4802 }
4803 ataSetIRQ(s);
4804 pCtl->uAsyncIOState = ATA_AIO_NEW;
4805 break;
4806 }
4807
4808 case ATA_AIO_PIO:
4809 s = &pCtl->aIfs[pCtl->iAIOIf]; /* Do not remove or there's an instant crash after loading the saved state */
4810
4811 if (s->iSourceSink != ATAFN_SS_NULL)
4812 {
4813 bool fRedo;
4814 Log2(("%s: Ctl#%d: calling source/sink function\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
4815 fRedo = g_apfnSourceSinkFuncs[s->iSourceSink](s);
4816 pCtl->fRedo = fRedo;
4817 if (RT_UNLIKELY(fRedo && !pCtl->fReset))
4818 {
4819 LogRel(("PIIX3 ATA: Ctl#%d: redo PIO operation\n", ATACONTROLLER_IDX(pCtl)));
4820 ataAsyncIOPutRequest(pCtl, &g_ataPIORequest);
4821 ataSuspendRedo(pCtl);
4822 break;
4823 }
4824 s->iIOBufferCur = 0;
4825 s->iIOBufferEnd = s->cbElementaryTransfer;
4826 }
4827 else
4828 {
4829 /* Continue a previously started transfer. */
4830 ataUnsetStatus(s, ATA_STAT_BUSY);
4831 ataSetStatus(s, ATA_STAT_READY);
4832 }
4833
4834 /* It is possible that the drives on this controller get RESET
4835 * during the above call to the source/sink function. If that's
4836 * the case, don't restart the transfer and don't finish it the
4837 * usual way. RESET handling took care of all that already.
4838 * Most important: do not change uAsyncIOState. */
4839 if (pCtl->fReset)
4840 break;
4841
4842 if (s->cbTotalTransfer)
4843 {
4844 ataPIOTransfer(pCtl);
4845 ataSetIRQ(s);
4846
4847 if (s->uTxDir == PDMBLOCKTXDIR_TO_DEVICE || s->iSourceSink != ATAFN_SS_NULL)
4848 {
4849 /* Write operations and not yet finished transfers
4850 * must be completed in the async I/O thread. */
4851 pCtl->uAsyncIOState = ATA_AIO_PIO;
4852 }
4853 else
4854 {
4855 /* Finished read operation can be handled inline
4856 * in the end of PIO transfer handling code. Linux
4857 * depends on this, as it waits only briefly for
4858 * devices to become ready after incoming data
4859 * transfer. Cannot find anything in the ATA spec
4860 * that backs this assumption, but as all kernels
4861 * are affected (though most of the time it does
4862 * not cause any harm) this must work. */
4863 pCtl->uAsyncIOState = ATA_AIO_NEW;
4864 }
4865 }
4866 else
4867 {
4868 /* Finish PIO transfer. */
4869 ataPIOTransfer(pCtl);
4870 if ( !pCtl->fChainedTransfer
4871 && !s->fATAPITransfer
4872 && s->uTxDir != PDMBLOCKTXDIR_FROM_DEVICE)
4873 {
4874 ataSetIRQ(s);
4875 }
4876 pCtl->uAsyncIOState = ATA_AIO_NEW;
4877 }
4878 break;
4879
4880 case ATA_AIO_RESET_ASSERTED:
4881 pCtl->uAsyncIOState = ATA_AIO_RESET_CLEARED;
4882 ataPIOTransferStop(&pCtl->aIfs[0]);
4883 ataPIOTransferStop(&pCtl->aIfs[1]);
4884 /* Do not change the DMA registers, they are not affected by the
4885 * ATA controller reset logic. It should be sufficient to issue a
4886 * new command, which is now possible as the state is cleared. */
4887 break;
4888
4889 case ATA_AIO_RESET_CLEARED:
4890 pCtl->uAsyncIOState = ATA_AIO_NEW;
4891 pCtl->fReset = false;
4892 /* Ensure that half-completed transfers are not redone. A reset
4893 * cancels the entire transfer, so continuing is wrong. */
4894 pCtl->fRedo = false;
4895 pCtl->fRedoDMALastDesc = false;
4896 LogRel(("PIIX3 ATA: Ctl#%d: finished processing RESET\n",
4897 ATACONTROLLER_IDX(pCtl)));
4898 for (uint32_t i = 0; i < RT_ELEMENTS(pCtl->aIfs); i++)
4899 {
4900 if (pCtl->aIfs[i].fATAPI)
4901 ataSetStatusValue(&pCtl->aIfs[i], 0); /* NOTE: READY is _not_ set */
4902 else
4903 ataSetStatusValue(&pCtl->aIfs[i], ATA_STAT_READY | ATA_STAT_SEEK);
4904 ataSetSignature(&pCtl->aIfs[i]);
4905 }
4906 break;
4907
4908 case ATA_AIO_ABORT:
4909 /* Abort the current command only if it operates on the same interface. */
4910 if (pCtl->iAIOIf == pReq->u.a.iIf)
4911 {
4912 s = &pCtl->aIfs[pCtl->iAIOIf];
4913
4914 pCtl->uAsyncIOState = ATA_AIO_NEW;
4915 /* Do not change the DMA registers, they are not affected by the
4916 * ATA controller reset logic. It should be sufficient to issue a
4917 * new command, which is now possible as the state is cleared. */
4918 if (pReq->u.a.fResetDrive)
4919 {
4920 ataResetDevice(s);
4921 ataExecuteDeviceDiagnosticSS(s);
4922 }
4923 else
4924 {
4925 /* Stop any pending DMA transfer. */
4926 s->fDMA = false;
4927 ataPIOTransferStop(s);
4928 ataUnsetStatus(s, ATA_STAT_BUSY | ATA_STAT_DRQ | ATA_STAT_SEEK | ATA_STAT_ERR);
4929 ataSetStatus(s, ATA_STAT_READY);
4930 ataSetIRQ(s);
4931 }
4932 }
4933 break;
4934
4935 default:
4936 AssertMsgFailed(("Undefined async I/O state %d\n", pCtl->uAsyncIOState));
4937 }
4938
4939 ataAsyncIORemoveCurrentRequest(pCtl, ReqType);
4940 pReq = ataAsyncIOGetCurrentRequest(pCtl);
4941
4942 if (pCtl->uAsyncIOState == ATA_AIO_NEW && !pCtl->fChainedTransfer)
4943 {
4944#if defined(DEBUG) || defined(VBOX_WITH_STATISTICS)
4945 STAM_PROFILE_ADV_STOP(&pCtl->StatAsyncTime, a);
4946#endif /* DEBUG || VBOX_WITH_STATISTICS */
4947
4948 u64TS = RTTimeNanoTS() - u64TS;
4949 uWait = u64TS / 1000;
4950 Log(("%s: Ctl#%d: LUN#%d finished I/O transaction in %d microseconds\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), pCtl->aIfs[pCtl->iAIOIf].iLUN, (uint32_t)(uWait)));
4951 /* Mark command as finished. */
4952 pCtl->aIfs[pCtl->iAIOIf].u64CmdTS = 0;
4953
4954 /*
4955 * Release logging of command execution times depends on the
4956 * command type. ATAPI commands often take longer (due to CD/DVD
4957 * spin up time etc.) so the threshold is different.
4958 */
4959 if (pCtl->aIfs[pCtl->iAIOIf].uATARegCommand != ATA_PACKET)
4960 {
4961 if (uWait > 8 * 1000 * 1000)
4962 {
4963 /*
4964 * Command took longer than 8 seconds. This is close
4965 * enough or over the guest's command timeout, so place
4966 * an entry in the release log to allow tracking such
4967 * timing errors (which are often caused by the host).
4968 */
4969 LogRel(("PIIX3 ATA: execution time for ATA command %#04x was %d seconds\n", pCtl->aIfs[pCtl->iAIOIf].uATARegCommand, uWait / (1000 * 1000)));
4970 }
4971 }
4972 else
4973 {
4974 if (uWait > 20 * 1000 * 1000)
4975 {
4976 /*
4977 * Command took longer than 20 seconds. This is close
4978 * enough or over the guest's command timeout, so place
4979 * an entry in the release log to allow tracking such
4980 * timing errors (which are often caused by the host).
4981 */
4982 LogRel(("PIIX3 ATA: execution time for ATAPI command %#04x was %d seconds\n", pCtl->aIfs[pCtl->iAIOIf].aATAPICmd[0], uWait / (1000 * 1000)));
4983 }
4984 }
4985
4986#if defined(DEBUG) || defined(VBOX_WITH_STATISTICS)
4987 if (uWait < pCtl->StatAsyncMinWait || !pCtl->StatAsyncMinWait)
4988 pCtl->StatAsyncMinWait = uWait;
4989 if (uWait > pCtl->StatAsyncMaxWait)
4990 pCtl->StatAsyncMaxWait = uWait;
4991
4992 STAM_COUNTER_ADD(&pCtl->StatAsyncTimeUS, uWait);
4993 STAM_COUNTER_INC(&pCtl->StatAsyncOps);
4994#endif /* DEBUG || VBOX_WITH_STATISTICS */
4995 }
4996
4997 PDMCritSectLeave(&pCtl->lock);
4998 }
4999
5000 /* Signal the ultimate idleness. */
5001 RTThreadUserSignal(pCtl->AsyncIOThread);
5002 if (pCtl->fSignalIdle)
5003 PDMDevHlpAsyncNotificationCompleted(pCtl->pDevInsR3);
5004
5005 /* Cleanup the state. */
5006 /* Do not destroy request mutex yet, still needed for proper shutdown. */
5007 pCtl->fShutdown = false;
5008
5009 Log2(("%s: Ctl#%d: return %Rrc\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl), rc));
5010 return rc;
5011}
5012
5013#endif /* IN_RING3 */
5014
5015static uint32_t ataBMDMACmdReadB(PATACONTROLLER pCtl, uint32_t addr)
5016{
5017 uint32_t val = pCtl->BmDma.u8Cmd;
5018 Log2(("%s: addr=%#06x val=%#04x\n", __FUNCTION__, addr, val));
5019 return val;
5020}
5021
5022
5023static void ataBMDMACmdWriteB(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
5024{
5025 Log2(("%s: addr=%#06x val=%#04x\n", __FUNCTION__, addr, val));
5026 if (!(val & BM_CMD_START))
5027 {
5028 pCtl->BmDma.u8Status &= ~BM_STATUS_DMAING;
5029 pCtl->BmDma.u8Cmd = val & (BM_CMD_START | BM_CMD_WRITE);
5030 }
5031 else
5032 {
5033#ifdef IN_RING3
5034 /* Check whether the guest OS wants to change DMA direction in
5035 * mid-flight. Not allowed, according to the PIIX3 specs. */
5036 Assert(!(pCtl->BmDma.u8Status & BM_STATUS_DMAING) || !((val ^ pCtl->BmDma.u8Cmd) & 0x04));
5037 pCtl->BmDma.u8Status |= BM_STATUS_DMAING;
5038 pCtl->BmDma.u8Cmd = val & (BM_CMD_START | BM_CMD_WRITE);
5039
5040 /* Do not continue DMA transfers while the RESET line is asserted. */
5041 if (pCtl->fReset)
5042 {
5043 Log2(("%s: Ctl#%d: suppressed continuing DMA transfer as RESET is active\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
5044 return;
5045 }
5046
5047 /* Do not start DMA transfers if there's a PIO transfer going on. */
5048 if (!pCtl->aIfs[pCtl->iSelectedIf].fDMA)
5049 return;
5050
5051 if (pCtl->aIfs[pCtl->iAIOIf].uATARegStatus & ATA_STAT_DRQ)
5052 {
5053 Log2(("%s: Ctl#%d: message to async I/O thread, continuing DMA transfer\n", __FUNCTION__, ATACONTROLLER_IDX(pCtl)));
5054 ataAsyncIOPutRequest(pCtl, &g_ataDMARequest);
5055 }
5056#else /* !IN_RING3 */
5057 AssertMsgFailed(("DMA START handling is too complicated for GC\n"));
5058#endif /* IN_RING3 */
5059 }
5060}
5061
5062static uint32_t ataBMDMAStatusReadB(PATACONTROLLER pCtl, uint32_t addr)
5063{
5064 uint32_t val = pCtl->BmDma.u8Status;
5065 Log2(("%s: addr=%#06x val=%#04x\n", __FUNCTION__, addr, val));
5066 return val;
5067}
5068
5069static void ataBMDMAStatusWriteB(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
5070{
5071 Log2(("%s: addr=%#06x val=%#04x\n", __FUNCTION__, addr, val));
5072 pCtl->BmDma.u8Status = (val & (BM_STATUS_D0DMA | BM_STATUS_D1DMA))
5073 | (pCtl->BmDma.u8Status & BM_STATUS_DMAING)
5074 | (pCtl->BmDma.u8Status & ~val & (BM_STATUS_ERROR | BM_STATUS_INT));
5075}
5076
5077static uint32_t ataBMDMAAddrReadL(PATACONTROLLER pCtl, uint32_t addr)
5078{
5079 uint32_t val = (uint32_t)pCtl->BmDma.pvAddr;
5080 Log2(("%s: addr=%#06x val=%#010x\n", __FUNCTION__, addr, val));
5081 return val;
5082}
5083
5084static void ataBMDMAAddrWriteL(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
5085{
5086 Log2(("%s: addr=%#06x val=%#010x\n", __FUNCTION__, addr, val));
5087 pCtl->BmDma.pvAddr = val & ~3;
5088}
5089
5090static void ataBMDMAAddrWriteLowWord(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
5091{
5092 Log2(("%s: addr=%#06x val=%#010x\n", __FUNCTION__, addr, val));
5093 pCtl->BmDma.pvAddr = (pCtl->BmDma.pvAddr & 0xFFFF0000) | RT_LOWORD(val & ~3);
5094
5095}
5096
5097static void ataBMDMAAddrWriteHighWord(PATACONTROLLER pCtl, uint32_t addr, uint32_t val)
5098{
5099 Log2(("%s: addr=%#06x val=%#010x\n", __FUNCTION__, addr, val));
5100 pCtl->BmDma.pvAddr = (RT_LOWORD(val) << 16) | RT_LOWORD(pCtl->BmDma.pvAddr);
5101}
5102
5103#define VAL(port, size) ( ((port) & 7) | ((size) << 3) )
5104
5105/**
5106 * Port I/O Handler for bus master DMA IN operations.
5107 * @see FNIOMIOPORTIN for details.
5108 */
5109PDMBOTHCBDECL(int) ataBMDMAIOPortRead(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *pu32, unsigned cb)
5110{
5111 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5112 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5113 PATACONTROLLER pCtl = &pThis->aCts[i];
5114 int rc;
5115
5116 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_READ);
5117 if (rc != VINF_SUCCESS)
5118 return rc;
5119 switch (VAL(Port, cb))
5120 {
5121 case VAL(0, 1): *pu32 = ataBMDMACmdReadB(pCtl, Port); break;
5122 case VAL(0, 2): *pu32 = ataBMDMACmdReadB(pCtl, Port); break;
5123 case VAL(2, 1): *pu32 = ataBMDMAStatusReadB(pCtl, Port); break;
5124 case VAL(2, 2): *pu32 = ataBMDMAStatusReadB(pCtl, Port); break;
5125 case VAL(4, 4): *pu32 = ataBMDMAAddrReadL(pCtl, Port); break;
5126 case VAL(0, 4):
5127 /* The SCO OpenServer tries to read 4 bytes starting from offset 0. */
5128 *pu32 = ataBMDMACmdReadB(pCtl, Port) | (ataBMDMAStatusReadB(pCtl, Port) << 16);
5129 break;
5130 default:
5131 AssertMsgFailed(("%s: Unsupported read from port %x size=%d\n", __FUNCTION__, Port, cb));
5132 PDMCritSectLeave(&pCtl->lock);
5133 return VERR_IOM_IOPORT_UNUSED;
5134 }
5135 PDMCritSectLeave(&pCtl->lock);
5136 return rc;
5137}
5138
5139/**
5140 * Port I/O Handler for bus master DMA OUT operations.
5141 * @see FNIOMIOPORTOUT for details.
5142 */
5143PDMBOTHCBDECL(int) ataBMDMAIOPortWrite(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb)
5144{
5145 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5146 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5147 PATACONTROLLER pCtl = &pThis->aCts[i];
5148 int rc;
5149
5150 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_WRITE);
5151 if (rc != VINF_SUCCESS)
5152 return rc;
5153 switch (VAL(Port, cb))
5154 {
5155 case VAL(0, 1):
5156#ifndef IN_RING3
5157 if (u32 & BM_CMD_START)
5158 {
5159 rc = VINF_IOM_HC_IOPORT_WRITE;
5160 break;
5161 }
5162#endif /* !IN_RING3 */
5163 ataBMDMACmdWriteB(pCtl, Port, u32);
5164 break;
5165 case VAL(2, 1): ataBMDMAStatusWriteB(pCtl, Port, u32); break;
5166 case VAL(4, 4): ataBMDMAAddrWriteL(pCtl, Port, u32); break;
5167 case VAL(4, 2): ataBMDMAAddrWriteLowWord(pCtl, Port, u32); break;
5168 case VAL(6, 2): ataBMDMAAddrWriteHighWord(pCtl, Port, u32); break;
5169 default: AssertMsgFailed(("%s: Unsupported write to port %x size=%d val=%x\n", __FUNCTION__, Port, cb, u32)); break;
5170 }
5171 PDMCritSectLeave(&pCtl->lock);
5172 return rc;
5173}
5174
5175#undef VAL
5176
5177#ifdef IN_RING3
5178
5179/**
5180 * Callback function for mapping an PCI I/O region.
5181 *
5182 * @return VBox status code.
5183 * @param pPciDev Pointer to PCI device. Use pPciDev->pDevIns to get the device instance.
5184 * @param iRegion The region number.
5185 * @param GCPhysAddress Physical address of the region. If iType is PCI_ADDRESS_SPACE_IO, this is an
5186 * I/O port, else it's a physical address.
5187 * This address is *NOT* relative to pci_mem_base like earlier!
5188 * @param enmType One of the PCI_ADDRESS_SPACE_* values.
5189 */
5190static DECLCALLBACK(int) ataBMDMAIORangeMap(PPCIDEVICE pPciDev, /*unsigned*/ int iRegion, RTGCPHYS GCPhysAddress, uint32_t cb, PCIADDRESSSPACE enmType)
5191{
5192 PCIATAState *pThis = PCIDEV_2_PCIATASTATE(pPciDev);
5193 int rc = VINF_SUCCESS;
5194 Assert(enmType == PCI_ADDRESS_SPACE_IO);
5195 Assert(iRegion == 4);
5196 AssertMsg(RT_ALIGN(GCPhysAddress, 8) == GCPhysAddress, ("Expected 8 byte alignment. GCPhysAddress=%#x\n", GCPhysAddress));
5197
5198 /* Register the port range. */
5199 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5200 {
5201 int rc2 = PDMDevHlpIOPortRegister(pPciDev->pDevIns, (RTIOPORT)GCPhysAddress + i * 8, 8,
5202 (RTHCPTR)i, ataBMDMAIOPortWrite, ataBMDMAIOPortRead, NULL, NULL, "ATA Bus Master DMA");
5203 AssertRC(rc2);
5204 if (rc2 < rc)
5205 rc = rc2;
5206
5207 if (pThis->fGCEnabled)
5208 {
5209 rc2 = PDMDevHlpIOPortRegisterGC(pPciDev->pDevIns, (RTIOPORT)GCPhysAddress + i * 8, 8,
5210 (RTGCPTR)i, "ataBMDMAIOPortWrite", "ataBMDMAIOPortRead", NULL, NULL, "ATA Bus Master DMA");
5211 AssertRC(rc2);
5212 if (rc2 < rc)
5213 rc = rc2;
5214 }
5215 if (pThis->fR0Enabled)
5216 {
5217 rc2 = PDMDevHlpIOPortRegisterR0(pPciDev->pDevIns, (RTIOPORT)GCPhysAddress + i * 8, 8,
5218 (RTR0PTR)i, "ataBMDMAIOPortWrite", "ataBMDMAIOPortRead", NULL, NULL, "ATA Bus Master DMA");
5219 AssertRC(rc2);
5220 if (rc2 < rc)
5221 rc = rc2;
5222 }
5223 }
5224 return rc;
5225}
5226
5227
5228/* -=-=-=-=-=- PCIATAState::IBase -=-=-=-=-=- */
5229
5230/**
5231 * @interface_method_impl{PDMIBASE,pfnQueryInterface}
5232 */
5233static DECLCALLBACK(void *) ataStatus_QueryInterface(PPDMIBASE pInterface, const char *pszIID)
5234{
5235 PCIATAState *pThis = PDMIBASE_2_PCIATASTATE(pInterface);
5236 PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pThis->IBase);
5237 PDMIBASE_RETURN_INTERFACE(pszIID, PDMILEDPORTS, &pThis->ILeds);
5238 return NULL;
5239}
5240
5241
5242/* -=-=-=-=-=- PCIATAState::ILeds -=-=-=-=-=- */
5243
5244/**
5245 * Gets the pointer to the status LED of a unit.
5246 *
5247 * @returns VBox status code.
5248 * @param pInterface Pointer to the interface structure containing the called function pointer.
5249 * @param iLUN The unit which status LED we desire.
5250 * @param ppLed Where to store the LED pointer.
5251 */
5252static DECLCALLBACK(int) ataStatus_QueryStatusLed(PPDMILEDPORTS pInterface, unsigned iLUN, PPDMLED *ppLed)
5253{
5254 PCIATAState *pThis = PDMILEDPORTS_2_PCIATASTATE(pInterface);
5255 if (iLUN < 4)
5256 {
5257 switch (iLUN)
5258 {
5259 case 0: *ppLed = &pThis->aCts[0].aIfs[0].Led; break;
5260 case 1: *ppLed = &pThis->aCts[0].aIfs[1].Led; break;
5261 case 2: *ppLed = &pThis->aCts[1].aIfs[0].Led; break;
5262 case 3: *ppLed = &pThis->aCts[1].aIfs[1].Led; break;
5263 }
5264 Assert((*ppLed)->u32Magic == PDMLED_MAGIC);
5265 return VINF_SUCCESS;
5266 }
5267 return VERR_PDM_LUN_NOT_FOUND;
5268}
5269
5270
5271/* -=-=-=-=-=- ATADevState::IBase -=-=-=-=-=- */
5272
5273/**
5274 * @interface_method_impl{PDMIBASE,pfnQueryInterface}
5275 */
5276static DECLCALLBACK(void *) ataQueryInterface(PPDMIBASE pInterface, const char *pszIID)
5277{
5278 ATADevState *pIf = PDMIBASE_2_ATASTATE(pInterface);
5279 PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pIf->IBase);
5280 PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBLOCKPORT, &pIf->IPort);
5281 PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMOUNTNOTIFY, &pIf->IMountNotify);
5282 return NULL;
5283}
5284
5285#endif /* IN_RING3 */
5286
5287
5288/* -=-=-=-=-=- Wrappers -=-=-=-=-=- */
5289
5290/**
5291 * Port I/O Handler for primary port range OUT operations.
5292 * @see FNIOMIOPORTOUT for details.
5293 */
5294PDMBOTHCBDECL(int) ataIOPortWrite1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb)
5295{
5296 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5297 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5298 PATACONTROLLER pCtl = &pThis->aCts[i];
5299 int rc = VINF_SUCCESS;
5300
5301 Assert(i < 2);
5302
5303 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_WRITE);
5304 if (rc != VINF_SUCCESS)
5305 return rc;
5306 if (cb == 1)
5307 rc = ataIOPortWriteU8(pCtl, Port, u32);
5308 else if (Port == pCtl->IOPortBase1)
5309 {
5310 Assert(cb == 2 || cb == 4);
5311 rc = ataDataWrite(pCtl, Port, cb, (const uint8_t *)&u32);
5312 }
5313 else
5314 AssertMsgFailed(("ataIOPortWrite1: unsupported write to port %x val=%x size=%d\n", Port, u32, cb));
5315 PDMCritSectLeave(&pCtl->lock);
5316 return rc;
5317}
5318
5319
5320/**
5321 * Port I/O Handler for primary port range IN operations.
5322 * @see FNIOMIOPORTIN for details.
5323 */
5324PDMBOTHCBDECL(int) ataIOPortRead1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *pu32, unsigned cb)
5325{
5326 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5327 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5328 PATACONTROLLER pCtl = &pThis->aCts[i];
5329 int rc = VINF_SUCCESS;
5330
5331 Assert(i < 2);
5332
5333 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_READ);
5334 if (rc != VINF_SUCCESS)
5335 return rc;
5336 if (cb == 1)
5337 {
5338 rc = ataIOPortReadU8(pCtl, Port, pu32);
5339 }
5340 else if (Port == pCtl->IOPortBase1)
5341 {
5342 Assert(cb == 2 || cb == 4);
5343 rc = ataDataRead(pCtl, Port, cb, (uint8_t *)pu32);
5344 if (cb == 2)
5345 *pu32 &= 0xffff;
5346 }
5347 else
5348 {
5349 AssertMsgFailed(("ataIOPortRead1: unsupported read from port %x size=%d\n", Port, cb));
5350 rc = VERR_IOM_IOPORT_UNUSED;
5351 }
5352 PDMCritSectLeave(&pCtl->lock);
5353 return rc;
5354}
5355
5356#ifndef IN_RING0 /** @todo do this in ring-0 as well. */
5357/**
5358 * Port I/O Handler for primary port range IN string operations.
5359 * @see FNIOMIOPORTINSTRING for details.
5360 */
5361PDMBOTHCBDECL(int) ataIOPortReadStr1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, RTGCPTR *pGCPtrDst, PRTGCUINTREG pcTransfer, unsigned cb)
5362{
5363 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5364 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5365 PATACONTROLLER pCtl = &pThis->aCts[i];
5366 int rc = VINF_SUCCESS;
5367
5368 Assert(i < 2);
5369
5370 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_READ);
5371 if (rc != VINF_SUCCESS)
5372 return rc;
5373 if (Port == pCtl->IOPortBase1)
5374 {
5375 uint32_t cTransAvailable, cTransfer = *pcTransfer, cbTransfer;
5376 RTGCPTR GCDst = *pGCPtrDst;
5377 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
5378 Assert(cb == 2 || cb == 4);
5379
5380 cTransAvailable = (s->iIOBufferPIODataEnd - s->iIOBufferPIODataStart) / cb;
5381#ifndef IN_RING3
5382 /* Deal with the unlikely case where no data (or not enough for the read length operation) is available; go back to ring 3. */
5383 if (!cTransAvailable)
5384 {
5385 PDMCritSectLeave(&pCtl->lock);
5386 return VINF_IOM_HC_IOPORT_READ;
5387 }
5388 /* The last transfer unit cannot be handled in GC, as it involves thread communication. */
5389 cTransAvailable--;
5390#endif /* !IN_RING3 */
5391 /* Do not handle the dummy transfer stuff here, leave it to the single-word transfers.
5392 * They are not performance-critical and generally shouldn't occur at all. */
5393 if (cTransAvailable > cTransfer)
5394 cTransAvailable = cTransfer;
5395 cbTransfer = cTransAvailable * cb;
5396
5397 rc = PGMPhysSimpleDirtyWriteGCPtr(PDMDevHlpGetVMCPU(pDevIns), GCDst, s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart, cbTransfer);
5398 Assert(rc == VINF_SUCCESS);
5399
5400 if (cbTransfer)
5401 Log3(("%s: addr=%#x val=%.*Rhxs\n", __FUNCTION__, Port, cbTransfer, s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart));
5402 s->iIOBufferPIODataStart += cbTransfer;
5403 *pGCPtrDst = (RTGCPTR)((RTGCUINTPTR)GCDst + cbTransfer);
5404 *pcTransfer = cTransfer - cTransAvailable;
5405#ifdef IN_RING3
5406 if (s->iIOBufferPIODataStart >= s->iIOBufferPIODataEnd)
5407 ataPIOTransferFinish(pCtl, s);
5408#endif /* IN_RING3 */
5409 }
5410 PDMCritSectLeave(&pCtl->lock);
5411 return rc;
5412}
5413
5414
5415/**
5416 * Port I/O Handler for primary port range OUT string operations.
5417 * @see FNIOMIOPORTOUTSTRING for details.
5418 */
5419PDMBOTHCBDECL(int) ataIOPortWriteStr1(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, RTGCPTR *pGCPtrSrc, PRTGCUINTREG pcTransfer, unsigned cb)
5420{
5421 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5422 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5423 PATACONTROLLER pCtl = &pThis->aCts[i];
5424 int rc;
5425
5426 Assert(i < 2);
5427
5428 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_WRITE);
5429 if (rc != VINF_SUCCESS)
5430 return rc;
5431 if (Port == pCtl->IOPortBase1)
5432 {
5433 uint32_t cTransAvailable, cTransfer = *pcTransfer, cbTransfer;
5434 RTGCPTR GCSrc = *pGCPtrSrc;
5435 ATADevState *s = &pCtl->aIfs[pCtl->iSelectedIf];
5436 Assert(cb == 2 || cb == 4);
5437
5438 cTransAvailable = (s->iIOBufferPIODataEnd - s->iIOBufferPIODataStart) / cb;
5439#ifndef IN_RING3
5440 /* Deal with the unlikely case where no data (or not enough for the read length operation) is available; go back to ring 3. */
5441 if (!cTransAvailable)
5442 {
5443 PDMCritSectLeave(&pCtl->lock);
5444 return VINF_IOM_HC_IOPORT_WRITE;
5445 }
5446 /* The last transfer unit cannot be handled in GC, as it involves thread communication. */
5447 cTransAvailable--;
5448#endif /* !IN_RING3 */
5449 /* Do not handle the dummy transfer stuff here, leave it to the single-word transfers.
5450 * They are not performance-critical and generally shouldn't occur at all. */
5451 if (cTransAvailable > cTransfer)
5452 cTransAvailable = cTransfer;
5453 cbTransfer = cTransAvailable * cb;
5454
5455 rc = PGMPhysSimpleReadGCPtr(PDMDevHlpGetVMCPU(pDevIns), s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart, GCSrc, cbTransfer);
5456 Assert(rc == VINF_SUCCESS);
5457
5458 if (cbTransfer)
5459 Log3(("%s: addr=%#x val=%.*Rhxs\n", __FUNCTION__, Port, cbTransfer, s->CTX_SUFF(pbIOBuffer) + s->iIOBufferPIODataStart));
5460 s->iIOBufferPIODataStart += cbTransfer;
5461 *pGCPtrSrc = (RTGCPTR)((RTGCUINTPTR)GCSrc + cbTransfer);
5462 *pcTransfer = cTransfer - cTransAvailable;
5463#ifdef IN_RING3
5464 if (s->iIOBufferPIODataStart >= s->iIOBufferPIODataEnd)
5465 ataPIOTransferFinish(pCtl, s);
5466#endif /* IN_RING3 */
5467 }
5468 PDMCritSectLeave(&pCtl->lock);
5469 return rc;
5470}
5471#endif /* !IN_RING0 */
5472
5473/**
5474 * Port I/O Handler for secondary port range OUT operations.
5475 * @see FNIOMIOPORTOUT for details.
5476 */
5477PDMBOTHCBDECL(int) ataIOPortWrite2(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t u32, unsigned cb)
5478{
5479 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5480 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5481 PATACONTROLLER pCtl = &pThis->aCts[i];
5482 int rc;
5483
5484 Assert(i < 2);
5485
5486 if (cb != 1)
5487 return VINF_SUCCESS;
5488 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_WRITE);
5489 if (rc != VINF_SUCCESS)
5490 return rc;
5491 rc = ataControlWrite(pCtl, Port, u32);
5492 PDMCritSectLeave(&pCtl->lock);
5493 return rc;
5494}
5495
5496
5497/**
5498 * Port I/O Handler for secondary port range IN operations.
5499 * @see FNIOMIOPORTIN for details.
5500 */
5501PDMBOTHCBDECL(int) ataIOPortRead2(PPDMDEVINS pDevIns, void *pvUser, RTIOPORT Port, uint32_t *pu32, unsigned cb)
5502{
5503 uint32_t i = (uint32_t)(uintptr_t)pvUser;
5504 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5505 PATACONTROLLER pCtl = &pThis->aCts[i];
5506 int rc;
5507
5508 Assert(i < 2);
5509
5510 if (cb != 1)
5511 return VERR_IOM_IOPORT_UNUSED;
5512
5513 rc = PDMCritSectEnter(&pCtl->lock, VINF_IOM_HC_IOPORT_READ);
5514 if (rc != VINF_SUCCESS)
5515 return rc;
5516 *pu32 = ataStatusRead(pCtl, Port);
5517 PDMCritSectLeave(&pCtl->lock);
5518 return VINF_SUCCESS;
5519}
5520
5521#ifdef IN_RING3
5522
5523
5524DECLINLINE(void) ataRelocBuffer(PPDMDEVINS pDevIns, ATADevState *s)
5525{
5526 if (s->pbIOBufferR3)
5527 s->pbIOBufferRC = MMHyperR3ToRC(PDMDevHlpGetVM(pDevIns), s->pbIOBufferR3);
5528}
5529
5530
5531/**
5532 * @copydoc FNPDMDEVRELOCATE
5533 */
5534static DECLCALLBACK(void) ataR3Relocate(PPDMDEVINS pDevIns, RTGCINTPTR offDelta)
5535{
5536 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5537
5538 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5539 {
5540 pThis->aCts[i].pDevInsRC += offDelta;
5541 pThis->aCts[i].aIfs[0].pDevInsRC += offDelta;
5542 pThis->aCts[i].aIfs[0].pControllerRC += offDelta;
5543 ataRelocBuffer(pDevIns, &pThis->aCts[i].aIfs[0]);
5544 pThis->aCts[i].aIfs[1].pDevInsRC += offDelta;
5545 pThis->aCts[i].aIfs[1].pControllerRC += offDelta;
5546 ataRelocBuffer(pDevIns, &pThis->aCts[i].aIfs[1]);
5547 }
5548}
5549
5550
5551/**
5552 * Destroy a driver instance.
5553 *
5554 * Most VM resources are freed by the VM. This callback is provided so that any non-VM
5555 * resources can be freed correctly.
5556 *
5557 * @param pDevIns The device instance data.
5558 */
5559static DECLCALLBACK(int) ataR3Destruct(PPDMDEVINS pDevIns)
5560{
5561 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5562 int rc;
5563
5564 Log(("ataR3Destruct\n"));
5565
5566 /*
5567 * Tell the async I/O threads to terminate.
5568 */
5569 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5570 {
5571 if (pThis->aCts[i].AsyncIOThread != NIL_RTTHREAD)
5572 {
5573 ASMAtomicWriteU32(&pThis->aCts[i].fShutdown, true);
5574 rc = RTSemEventSignal(pThis->aCts[i].AsyncIOSem);
5575 AssertRC(rc);
5576 }
5577 }
5578
5579 /*
5580 * Wait for the threads to terminate before destroying their resources.
5581 */
5582 for (unsigned i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5583 {
5584 if (pThis->aCts[i].AsyncIOThread != NIL_RTTHREAD)
5585 {
5586 rc = RTThreadWait(pThis->aCts[i].AsyncIOThread, 30000 /* 30 s*/, NULL);
5587 if (RT_SUCCESS(rc))
5588 pThis->aCts[i].AsyncIOThread = NIL_RTTHREAD;
5589 else
5590 LogRel(("PIIX3 ATA Dtor: Ctl#%u is still executing, DevSel=%d AIOIf=%d CmdIf0=%#04x CmdIf1=%#04x rc=%Rrc\n",
5591 i, pThis->aCts[i].iSelectedIf, pThis->aCts[i].iAIOIf,
5592 pThis->aCts[i].aIfs[0].uATARegCommand, pThis->aCts[i].aIfs[1].uATARegCommand, rc));
5593 }
5594 }
5595
5596 /*
5597 * Free resources.
5598 */
5599 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5600 {
5601 if (pThis->aCts[i].AsyncIORequestMutex != NIL_RTSEMMUTEX)
5602 {
5603 RTSemMutexDestroy(pThis->aCts[i].AsyncIORequestMutex);
5604 pThis->aCts[i].AsyncIORequestMutex = NIL_RTSEMMUTEX;
5605 }
5606 if (pThis->aCts[i].AsyncIOSem != NIL_RTSEMEVENT)
5607 {
5608 RTSemEventDestroy(pThis->aCts[i].AsyncIOSem);
5609 pThis->aCts[i].AsyncIOSem = NIL_RTSEMEVENT;
5610 }
5611 if (pThis->aCts[i].SuspendIOSem != NIL_RTSEMEVENT)
5612 {
5613 RTSemEventDestroy(pThis->aCts[i].SuspendIOSem);
5614 pThis->aCts[i].SuspendIOSem = NIL_RTSEMEVENT;
5615 }
5616
5617 /* try one final time */
5618 if (pThis->aCts[i].AsyncIOThread != NIL_RTTHREAD)
5619 {
5620 rc = RTThreadWait(pThis->aCts[i].AsyncIOThread, 1 /*ms*/, NULL);
5621 if (RT_SUCCESS(rc))
5622 {
5623 pThis->aCts[i].AsyncIOThread = NIL_RTTHREAD;
5624 LogRel(("PIIX3 ATA Dtor: Ctl#%u actually completed.\n", i));
5625 }
5626 }
5627 }
5628
5629 return VINF_SUCCESS;
5630}
5631
5632
5633/**
5634 * Detach notification.
5635 *
5636 * The DVD drive has been unplugged.
5637 *
5638 * @param pDevIns The device instance.
5639 * @param iLUN The logical unit which is being detached.
5640 * @param fFlags Flags, combination of the PDMDEVATT_FLAGS_* \#defines.
5641 */
5642static DECLCALLBACK(void) ataR3Detach(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags)
5643{
5644 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5645 PATACONTROLLER pCtl;
5646 ATADevState *pIf;
5647 unsigned iController;
5648 unsigned iInterface;
5649
5650 AssertMsg(fFlags & PDM_TACH_FLAGS_NOT_HOT_PLUG,
5651 ("PIIX3IDE: Device does not support hotplugging\n"));
5652
5653 /*
5654 * Locate the controller and stuff.
5655 */
5656 iController = iLUN / RT_ELEMENTS(pThis->aCts[0].aIfs);
5657 AssertReleaseMsg(iController < RT_ELEMENTS(pThis->aCts), ("iController=%d iLUN=%d\n", iController, iLUN));
5658 pCtl = &pThis->aCts[iController];
5659
5660 iInterface = iLUN % RT_ELEMENTS(pThis->aCts[0].aIfs);
5661 pIf = &pCtl->aIfs[iInterface];
5662
5663 /*
5664 * Zero some important members.
5665 */
5666 pIf->pDrvBase = NULL;
5667 pIf->pDrvBlock = NULL;
5668 pIf->pDrvBlockBios = NULL;
5669 pIf->pDrvMount = NULL;
5670
5671 /*
5672 * In case there was a medium inserted.
5673 */
5674 ataMediumRemoved(pIf);
5675}
5676
5677
5678/**
5679 * Configure a LUN.
5680 *
5681 * @returns VBox status code.
5682 * @param pDevIns The device instance.
5683 * @param pIf The ATA unit state.
5684 */
5685static int ataConfigLun(PPDMDEVINS pDevIns, ATADevState *pIf)
5686{
5687 int rc = VINF_SUCCESS;
5688 PDMBLOCKTYPE enmType;
5689
5690 /*
5691 * Query Block, Bios and Mount interfaces.
5692 */
5693 pIf->pDrvBlock = PDMIBASE_QUERY_INTERFACE(pIf->pDrvBase, PDMIBLOCK);
5694 if (!pIf->pDrvBlock)
5695 {
5696 AssertMsgFailed(("Configuration error: LUN#%d hasn't a block interface!\n", pIf->iLUN));
5697 return VERR_PDM_MISSING_INTERFACE;
5698 }
5699
5700 /** @todo implement the BIOS invisible code path. */
5701 pIf->pDrvBlockBios = PDMIBASE_QUERY_INTERFACE(pIf->pDrvBase, PDMIBLOCKBIOS);
5702 if (!pIf->pDrvBlockBios)
5703 {
5704 AssertMsgFailed(("Configuration error: LUN#%d hasn't a block BIOS interface!\n", pIf->iLUN));
5705 return VERR_PDM_MISSING_INTERFACE;
5706 }
5707 pIf->pDrvMount = PDMIBASE_QUERY_INTERFACE(pIf->pDrvBase, PDMIMOUNT);
5708
5709 /*
5710 * Validate type.
5711 */
5712 enmType = pIf->pDrvBlock->pfnGetType(pIf->pDrvBlock);
5713 if ( enmType != PDMBLOCKTYPE_CDROM
5714 && enmType != PDMBLOCKTYPE_DVD
5715 && enmType != PDMBLOCKTYPE_HARD_DISK)
5716 {
5717 AssertMsgFailed(("Configuration error: LUN#%d isn't a disk or cd/dvd-rom. enmType=%d\n", pIf->iLUN, enmType));
5718 return VERR_PDM_UNSUPPORTED_BLOCK_TYPE;
5719 }
5720 if ( ( enmType == PDMBLOCKTYPE_DVD
5721 || enmType == PDMBLOCKTYPE_CDROM)
5722 && !pIf->pDrvMount)
5723 {
5724 AssertMsgFailed(("Internal error: cdrom without a mountable interface, WTF???!\n"));
5725 return VERR_INTERNAL_ERROR;
5726 }
5727 pIf->fATAPI = enmType == PDMBLOCKTYPE_DVD || enmType == PDMBLOCKTYPE_CDROM;
5728 pIf->fATAPIPassthrough = pIf->fATAPI ? (pIf->pDrvBlock->pfnSendCmd != NULL) : false;
5729
5730 /*
5731 * Allocate I/O buffer.
5732 */
5733 PVM pVM = PDMDevHlpGetVM(pDevIns);
5734 if (pIf->cbIOBuffer)
5735 {
5736 /* Buffer is (probably) already allocated. Validate the fields,
5737 * because memory corruption can also overwrite pIf->cbIOBuffer. */
5738 if (pIf->fATAPI)
5739 AssertRelease(pIf->cbIOBuffer == _128K);
5740 else
5741 AssertRelease(pIf->cbIOBuffer == ATA_MAX_MULT_SECTORS * 512);
5742 Assert(pIf->pbIOBufferR3);
5743 Assert(pIf->pbIOBufferR0 == MMHyperR3ToR0(pVM, pIf->pbIOBufferR3));
5744 Assert(pIf->pbIOBufferRC == MMHyperR3ToRC(pVM, pIf->pbIOBufferR3));
5745 }
5746 else
5747 {
5748 if (pIf->fATAPI)
5749 pIf->cbIOBuffer = _128K;
5750 else
5751 pIf->cbIOBuffer = ATA_MAX_MULT_SECTORS * 512;
5752 Assert(!pIf->pbIOBufferR3);
5753 rc = MMR3HyperAllocOnceNoRel(pVM, pIf->cbIOBuffer, 0, MM_TAG_PDM_DEVICE_USER, (void **)&pIf->pbIOBufferR3);
5754 if (RT_FAILURE(rc))
5755 return VERR_NO_MEMORY;
5756 pIf->pbIOBufferR0 = MMHyperR3ToR0(pVM, pIf->pbIOBufferR3);
5757 pIf->pbIOBufferRC = MMHyperR3ToRC(pVM, pIf->pbIOBufferR3);
5758 }
5759
5760 /*
5761 * Init geometry (only for non-CD/DVD media).
5762 */
5763 if (pIf->fATAPI)
5764 {
5765 pIf->cTotalSectors = pIf->pDrvBlock->pfnGetSize(pIf->pDrvBlock) / 2048;
5766 pIf->PCHSGeometry.cCylinders = 0; /* dummy */
5767 pIf->PCHSGeometry.cHeads = 0; /* dummy */
5768 pIf->PCHSGeometry.cSectors = 0; /* dummy */
5769 LogRel(("PIIX3 ATA: LUN#%d: CD/DVD, total number of sectors %Ld, passthrough %s\n", pIf->iLUN, pIf->cTotalSectors, (pIf->fATAPIPassthrough ? "enabled" : "disabled")));
5770 }
5771 else
5772 {
5773 pIf->cTotalSectors = pIf->pDrvBlock->pfnGetSize(pIf->pDrvBlock) / 512;
5774 rc = pIf->pDrvBlockBios->pfnGetPCHSGeometry(pIf->pDrvBlockBios,
5775 &pIf->PCHSGeometry);
5776 if (rc == VERR_PDM_MEDIA_NOT_MOUNTED)
5777 {
5778 pIf->PCHSGeometry.cCylinders = 0;
5779 pIf->PCHSGeometry.cHeads = 16; /*??*/
5780 pIf->PCHSGeometry.cSectors = 63; /*??*/
5781 }
5782 else if (rc == VERR_PDM_GEOMETRY_NOT_SET)
5783 {
5784 pIf->PCHSGeometry.cCylinders = 0; /* autodetect marker */
5785 rc = VINF_SUCCESS;
5786 }
5787 AssertRC(rc);
5788
5789 if ( pIf->PCHSGeometry.cCylinders == 0
5790 || pIf->PCHSGeometry.cHeads == 0
5791 || pIf->PCHSGeometry.cSectors == 0
5792 )
5793 {
5794 uint64_t cCylinders = pIf->cTotalSectors / (16 * 63);
5795 pIf->PCHSGeometry.cCylinders = RT_MAX(RT_MIN(cCylinders, 16383), 1);
5796 pIf->PCHSGeometry.cHeads = 16;
5797 pIf->PCHSGeometry.cSectors = 63;
5798 /* Set the disk geometry information. Ignore errors. */
5799 pIf->pDrvBlockBios->pfnSetPCHSGeometry(pIf->pDrvBlockBios,
5800 &pIf->PCHSGeometry);
5801 rc = VINF_SUCCESS;
5802 }
5803 LogRel(("PIIX3 ATA: LUN#%d: disk, PCHS=%u/%u/%u, total number of sectors %Ld\n", pIf->iLUN, pIf->PCHSGeometry.cCylinders, pIf->PCHSGeometry.cHeads, pIf->PCHSGeometry.cSectors, pIf->cTotalSectors));
5804 }
5805 return rc;
5806}
5807
5808
5809/**
5810 * Attach command.
5811 *
5812 * This is called when we change block driver for the DVD drive.
5813 *
5814 * @returns VBox status code.
5815 * @param pDevIns The device instance.
5816 * @param iLUN The logical unit which is being detached.
5817 * @param fFlags Flags, combination of the PDMDEVATT_FLAGS_* \#defines.
5818 */
5819static DECLCALLBACK(int) ataR3Attach(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags)
5820{
5821 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5822 PATACONTROLLER pCtl;
5823 ATADevState *pIf;
5824 int rc;
5825 unsigned iController;
5826 unsigned iInterface;
5827
5828 AssertMsgReturn(fFlags & PDM_TACH_FLAGS_NOT_HOT_PLUG,
5829 ("PIIX3IDE: Device does not support hotplugging\n"),
5830 VERR_INVALID_PARAMETER);
5831
5832 /*
5833 * Locate the controller and stuff.
5834 */
5835 iController = iLUN / RT_ELEMENTS(pThis->aCts[0].aIfs);
5836 AssertReleaseMsg(iController < RT_ELEMENTS(pThis->aCts), ("iController=%d iLUN=%d\n", iController, iLUN));
5837 pCtl = &pThis->aCts[iController];
5838
5839 iInterface = iLUN % RT_ELEMENTS(pThis->aCts[0].aIfs);
5840 pIf = &pCtl->aIfs[iInterface];
5841
5842 /* the usual paranoia */
5843 AssertRelease(!pIf->pDrvBase);
5844 AssertRelease(!pIf->pDrvBlock);
5845 Assert(ATADEVSTATE_2_CONTROLLER(pIf) == pCtl);
5846 Assert(pIf->iLUN == iLUN);
5847
5848 /*
5849 * Try attach the block device and get the interfaces,
5850 * required as well as optional.
5851 */
5852 rc = PDMDevHlpDriverAttach(pDevIns, pIf->iLUN, &pIf->IBase, &pIf->pDrvBase, NULL);
5853 if (RT_SUCCESS(rc))
5854 {
5855 rc = ataConfigLun(pDevIns, pIf);
5856 /*
5857 * In case there is a medium inserted.
5858 */
5859 ataMediumInserted(pIf);
5860 }
5861 else
5862 AssertMsgFailed(("Failed to attach LUN#%d. rc=%Rrc\n", pIf->iLUN, rc));
5863
5864 if (RT_FAILURE(rc))
5865 {
5866 pIf->pDrvBase = NULL;
5867 pIf->pDrvBlock = NULL;
5868 }
5869 return rc;
5870}
5871
5872
5873/**
5874 * Resume notification.
5875 *
5876 * @returns VBox status.
5877 * @param pDevIns The device instance data.
5878 */
5879static DECLCALLBACK(void) ataR3Resume(PPDMDEVINS pDevIns)
5880{
5881 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5882 int rc;
5883
5884 Log(("%s:\n", __FUNCTION__));
5885 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5886 {
5887 if (pThis->aCts[i].fRedo && pThis->aCts[i].fRedoIdle)
5888 {
5889 rc = RTSemEventSignal(pThis->aCts[i].SuspendIOSem);
5890 AssertRC(rc);
5891 }
5892 }
5893 return;
5894}
5895
5896
5897/**
5898 * Checks if all (both) the async I/O threads have quiesced.
5899 *
5900 * @returns true on success.
5901 * @returns false when one or more threads is still processing.
5902 * @param pThis Pointer to the instance data.
5903 */
5904static bool ataR3AllAsyncIOIsIdle(PPDMDEVINS pDevIns)
5905{
5906 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5907
5908 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5909 if (pThis->aCts[i].AsyncIOThread != NIL_RTTHREAD)
5910 {
5911 bool fRc = ataAsyncIOIsIdle(&pThis->aCts[i], false /*fStrict*/);
5912 if (!fRc)
5913 {
5914 /* Make it signal PDM & itself when its done */
5915 RTSemMutexRequest(pThis->aCts[i].AsyncIORequestMutex, RT_INDEFINITE_WAIT);
5916 ASMAtomicWriteBool(&pThis->aCts[i].fSignalIdle, true);
5917 RTSemMutexRelease(pThis->aCts[i].AsyncIORequestMutex);
5918 fRc = ataAsyncIOIsIdle(&pThis->aCts[i], false /*fStrict*/);
5919 if (!fRc)
5920 {
5921#if 0 /** @todo Need to do some time tracking here... */
5922 LogRel(("PIIX3 ATA: Ctl#%u is still executing, DevSel=%d AIOIf=%d CmdIf0=%#04x CmdIf1=%#04x\n",
5923 i, pThis->aCts[i].iSelectedIf, pThis->aCts[i].iAIOIf,
5924 pThis->aCts[i].aIfs[0].uATARegCommand, pThis->aCts[i].aIfs[1].uATARegCommand));
5925#endif
5926 return false;
5927 }
5928 }
5929 ASMAtomicWriteBool(&pThis->aCts[i].fSignalIdle, false);
5930 }
5931 return true;
5932}
5933
5934
5935/**
5936 * Callback employed by ataSuspend and ataR3PowerOff.
5937 *
5938 * @returns true if we've quiesced, false if we're still working.
5939 * @param pDevIns The device instance.
5940 */
5941static DECLCALLBACK(bool) ataR3IsAsyncSuspendOrPowerOffDone(PPDMDEVINS pDevIns)
5942{
5943 return ataR3AllAsyncIOIsIdle(pDevIns);
5944}
5945
5946
5947/**
5948 * Common worker for ataSuspend and ataR3PowerOff.
5949 */
5950static void ataR3SuspendOrPowerOff(PPDMDEVINS pDevIns)
5951{
5952 if (!ataR3AllAsyncIOIsIdle(pDevIns))
5953 PDMDevHlpSetAsyncNotification(pDevIns, ataR3IsAsyncSuspendOrPowerOffDone);
5954}
5955
5956
5957/**
5958 * Power Off notification.
5959 *
5960 * @returns VBox status.
5961 * @param pDevIns The device instance data.
5962 */
5963static DECLCALLBACK(void) ataR3PowerOff(PPDMDEVINS pDevIns)
5964{
5965 Log(("%s:\n", __FUNCTION__));
5966 ataR3SuspendOrPowerOff(pDevIns);
5967}
5968
5969
5970/**
5971 * Suspend notification.
5972 *
5973 * @returns VBox status.
5974 * @param pDevIns The device instance data.
5975 */
5976static DECLCALLBACK(void) ataR3Suspend(PPDMDEVINS pDevIns)
5977{
5978 Log(("%s:\n", __FUNCTION__));
5979 ataR3SuspendOrPowerOff(pDevIns);
5980}
5981
5982
5983/**
5984 * Callback employed by ataR3Reset.
5985 *
5986 * @returns true if we've quiesced, false if we're still working.
5987 * @param pDevIns The device instance.
5988 */
5989static DECLCALLBACK(bool) ataR3IsAsyncResetDone(PPDMDEVINS pDevIns)
5990{
5991 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
5992
5993 if (!ataR3AllAsyncIOIsIdle(pDevIns))
5994 return false;
5995
5996 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
5997 {
5998 PDMCritSectEnter(&pThis->aCts[i].lock, VERR_INTERNAL_ERROR);
5999 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6000 ataResetDevice(&pThis->aCts[i].aIfs[j]);
6001 PDMCritSectLeave(&pThis->aCts[i].lock);
6002 }
6003 return true;
6004}
6005
6006
6007/**
6008 * Common reset worker for ataR3Reset and ataR3Construct.
6009 *
6010 * @returns VBox status.
6011 * @param pDevIns The device instance data.
6012 * @param fConstruct Indicates who is calling.
6013 */
6014static int ataR3ResetCommon(PPDMDEVINS pDevIns, bool fConstruct)
6015{
6016 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6017
6018 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6019 {
6020 PDMCritSectEnter(&pThis->aCts[i].lock, VERR_INTERNAL_ERROR);
6021
6022 pThis->aCts[i].iSelectedIf = 0;
6023 pThis->aCts[i].iAIOIf = 0;
6024 pThis->aCts[i].BmDma.u8Cmd = 0;
6025 /* Report that both drives present on the bus are in DMA mode. This
6026 * pretends that there is a BIOS that has set it up. Normal reset
6027 * default is 0x00. */
6028 pThis->aCts[i].BmDma.u8Status = (pThis->aCts[i].aIfs[0].pDrvBase != NULL ? BM_STATUS_D0DMA : 0)
6029 | (pThis->aCts[i].aIfs[1].pDrvBase != NULL ? BM_STATUS_D1DMA : 0);
6030 pThis->aCts[i].BmDma.pvAddr = 0;
6031
6032 pThis->aCts[i].fReset = true;
6033 pThis->aCts[i].fRedo = false;
6034 pThis->aCts[i].fRedoIdle = false;
6035 ataAsyncIOClearRequests(&pThis->aCts[i]);
6036 Log2(("%s: Ctl#%d: message to async I/O thread, reset controller\n", __FUNCTION__, i));
6037 ataAsyncIOPutRequest(&pThis->aCts[i], &g_ataResetARequest);
6038 ataAsyncIOPutRequest(&pThis->aCts[i], &g_ataResetCRequest);
6039
6040 PDMCritSectLeave(&pThis->aCts[i].lock);
6041 }
6042
6043 int rcRet = VINF_SUCCESS;
6044 if (!fConstruct)
6045 {
6046 /*
6047 * Setup asynchronous notification compmletion if the requests haven't
6048 * completed yet.
6049 */
6050 if (!ataR3IsAsyncResetDone(pDevIns))
6051 PDMDevHlpSetAsyncNotification(pDevIns, ataR3IsAsyncResetDone);
6052 }
6053 else
6054 {
6055 /*
6056 * Wait for the requests for complete.
6057 *
6058 * Would be real nice if we could do it all from EMT(0) and not
6059 * involve the worker threads, then we could dispense with all the
6060 * waiting and semaphore ping-pong here...
6061 */
6062 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6063 {
6064 if (pThis->aCts[i].AsyncIOThread != NIL_RTTHREAD)
6065 {
6066 int rc = RTSemMutexRequest(pThis->aCts[i].AsyncIORequestMutex, RT_INDEFINITE_WAIT);
6067 AssertRC(rc);
6068
6069 ASMAtomicWriteBool(&pThis->aCts[i].fSignalIdle, true);
6070 rc = RTThreadUserReset(pThis->aCts[i].AsyncIOThread);
6071 AssertRC(rc);
6072
6073 rc = RTSemMutexRelease(pThis->aCts[i].AsyncIORequestMutex);
6074 AssertRC(rc);
6075
6076 if (!ataAsyncIOIsIdle(&pThis->aCts[i], false /*fStrict*/))
6077 {
6078 rc = RTThreadUserWait(pThis->aCts[i].AsyncIOThread, 30*1000 /*ms*/);
6079 if (RT_FAILURE(rc))
6080 rc = RTThreadUserWait(pThis->aCts[i].AsyncIOThread, 1000 /*ms*/);
6081 if (RT_FAILURE(rc))
6082 {
6083 AssertRC(rc);
6084 rcRet = rc;
6085 }
6086 }
6087 }
6088 ASMAtomicWriteBool(&pThis->aCts[i].fSignalIdle, false);
6089 }
6090 if (RT_SUCCESS(rcRet))
6091 {
6092 rcRet = ataR3IsAsyncResetDone(pDevIns) ? VINF_SUCCESS : VERR_INTERNAL_ERROR;
6093 AssertRC(rcRet);
6094 }
6095 }
6096 return rcRet;
6097}
6098
6099
6100/**
6101 * Reset notification.
6102 *
6103 * @param pDevIns The device instance data.
6104 */
6105static DECLCALLBACK(void) ataR3Reset(PPDMDEVINS pDevIns)
6106{
6107 ataR3ResetCommon(pDevIns, false /*fConstruct*/);
6108}
6109
6110
6111/**
6112 * Prepare state save and load operation.
6113 *
6114 * @returns VBox status code.
6115 * @param pDevIns Device instance of the device which registered the data unit.
6116 * @param pSSM SSM operation handle.
6117 */
6118static DECLCALLBACK(int) ataSaveLoadPrep(PPDMDEVINS pDevIns, PSSMHANDLE pSSM)
6119{
6120 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6121
6122 /* sanity - the suspend notification will wait on the async stuff. */
6123 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6124 AssertLogRelMsgReturn(ataAsyncIOIsIdle(&pThis->aCts[i], false /*fStrict*/),
6125 ("i=%u\n", i),
6126 VERR_SSM_IDE_ASYNC_TIMEOUT);
6127 return VINF_SUCCESS;
6128}
6129
6130/**
6131 * @copydoc FNSSMDEVLIVEEXEC
6132 */
6133static DECLCALLBACK(int) ataLiveExec(PPDMDEVINS pDevIns, PSSMHANDLE pSSM, uint32_t uPass)
6134{
6135 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6136
6137 SSMR3PutU8(pSSM, pThis->u8Type);
6138 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6139 {
6140 SSMR3PutBool(pSSM, true); /* For controller enabled / disabled. */
6141 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6142 {
6143 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].pDrvBase != NULL);
6144 SSMR3PutStrZ(pSSM, pThis->aCts[i].aIfs[j].szSerialNumber);
6145 SSMR3PutStrZ(pSSM, pThis->aCts[i].aIfs[j].szFirmwareRevision);
6146 SSMR3PutStrZ(pSSM, pThis->aCts[i].aIfs[j].szModelNumber);
6147 }
6148 }
6149
6150 return VINF_SSM_DONT_CALL_AGAIN;
6151}
6152
6153
6154/**
6155 * @copydoc FNSSMDEVSAVEEXEC
6156 */
6157static DECLCALLBACK(int) ataSaveExec(PPDMDEVINS pDevIns, PSSMHANDLE pSSM)
6158{
6159 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6160
6161 ataLiveExec(pDevIns, pSSM, SSM_PASS_FINAL);
6162
6163 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6164 {
6165 SSMR3PutU8(pSSM, pThis->aCts[i].iSelectedIf);
6166 SSMR3PutU8(pSSM, pThis->aCts[i].iAIOIf);
6167 SSMR3PutU8(pSSM, pThis->aCts[i].uAsyncIOState);
6168 SSMR3PutBool(pSSM, pThis->aCts[i].fChainedTransfer);
6169 SSMR3PutBool(pSSM, pThis->aCts[i].fReset);
6170 SSMR3PutBool(pSSM, pThis->aCts[i].fRedo);
6171 SSMR3PutBool(pSSM, pThis->aCts[i].fRedoIdle);
6172 SSMR3PutBool(pSSM, pThis->aCts[i].fRedoDMALastDesc);
6173 SSMR3PutMem(pSSM, &pThis->aCts[i].BmDma, sizeof(pThis->aCts[i].BmDma));
6174 SSMR3PutGCPhys32(pSSM, pThis->aCts[i].pFirstDMADesc);
6175 SSMR3PutGCPhys32(pSSM, pThis->aCts[i].pLastDMADesc);
6176 SSMR3PutGCPhys32(pSSM, pThis->aCts[i].pRedoDMABuffer);
6177 SSMR3PutU32(pSSM, pThis->aCts[i].cbRedoDMABuffer);
6178
6179 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6180 {
6181 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].fLBA48);
6182 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].fATAPI);
6183 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].fIrqPending);
6184 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].cMultSectors);
6185 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].PCHSGeometry.cCylinders);
6186 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].PCHSGeometry.cHeads);
6187 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].PCHSGeometry.cSectors);
6188 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].cSectorsPerIRQ);
6189 SSMR3PutU64(pSSM, pThis->aCts[i].aIfs[j].cTotalSectors);
6190 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegFeature);
6191 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegFeatureHOB);
6192 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegError);
6193 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegNSector);
6194 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegNSectorHOB);
6195 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegSector);
6196 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegSectorHOB);
6197 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegLCyl);
6198 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegLCylHOB);
6199 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegHCyl);
6200 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegHCylHOB);
6201 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegSelect);
6202 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegStatus);
6203 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegCommand);
6204 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATARegDevCtl);
6205 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uATATransferMode);
6206 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].uTxDir);
6207 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].iBeginTransfer);
6208 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].iSourceSink);
6209 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].fDMA);
6210 SSMR3PutBool(pSSM, pThis->aCts[i].aIfs[j].fATAPITransfer);
6211 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].cbTotalTransfer);
6212 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].cbElementaryTransfer);
6213 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].iIOBufferCur);
6214 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].iIOBufferEnd);
6215 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].iIOBufferPIODataStart);
6216 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].iIOBufferPIODataEnd);
6217 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].iATAPILBA);
6218 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].cbATAPISector);
6219 SSMR3PutMem(pSSM, &pThis->aCts[i].aIfs[j].aATAPICmd, sizeof(pThis->aCts[i].aIfs[j].aATAPICmd));
6220 SSMR3PutMem(pSSM, &pThis->aCts[i].aIfs[j].abATAPISense, sizeof(pThis->aCts[i].aIfs[j].abATAPISense));
6221 SSMR3PutU8(pSSM, pThis->aCts[i].aIfs[j].cNotifiedMediaChange);
6222 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].MediaEventStatus);
6223 SSMR3PutMem(pSSM, &pThis->aCts[i].aIfs[j].Led, sizeof(pThis->aCts[i].aIfs[j].Led));
6224 SSMR3PutU32(pSSM, pThis->aCts[i].aIfs[j].cbIOBuffer);
6225 if (pThis->aCts[i].aIfs[j].cbIOBuffer)
6226 SSMR3PutMem(pSSM, pThis->aCts[i].aIfs[j].CTX_SUFF(pbIOBuffer), pThis->aCts[i].aIfs[j].cbIOBuffer);
6227 else
6228 Assert(pThis->aCts[i].aIfs[j].CTX_SUFF(pbIOBuffer) == NULL);
6229 }
6230 }
6231
6232 return SSMR3PutU32(pSSM, ~0); /* sanity/terminator */
6233}
6234
6235/**
6236 * Converts the LUN number into a message string.
6237 */
6238static const char *ataStringifyLun(unsigned iLun)
6239{
6240 switch (iLun)
6241 {
6242 case 0: return "primary master";
6243 case 1: return "primary slave";
6244 case 2: return "secondary master";
6245 case 3: return "secondary slave";
6246 default: AssertFailedReturn("unknown lun");
6247 }
6248}
6249
6250/**
6251 * FNSSMDEVLOADEXEC
6252 */
6253static DECLCALLBACK(int) ataLoadExec(PPDMDEVINS pDevIns, PSSMHANDLE pSSM, uint32_t uVersion, uint32_t uPass)
6254{
6255 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6256 int rc;
6257 uint32_t u32;
6258
6259 if ( uVersion != ATA_SAVED_STATE_VERSION
6260 && uVersion != ATA_SAVED_STATE_VERSION_VBOX_30
6261 && uVersion != ATA_SAVED_STATE_VERSION_WITHOUT_FULL_SENSE
6262 && uVersion != ATA_SAVED_STATE_VERSION_WITHOUT_EVENT_STATUS
6263 && uVersion != ATA_SAVED_STATE_VERSION_WITH_BOOL_TYPE)
6264 {
6265 AssertMsgFailed(("uVersion=%d\n", uVersion));
6266 return VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION;
6267 }
6268
6269 /*
6270 * Verify the configuration.
6271 */
6272 if (uVersion > ATA_SAVED_STATE_VERSION_VBOX_30)
6273 {
6274 uint8_t u8Type;
6275 rc = SSMR3GetU8(pSSM, &u8Type);
6276 AssertRCReturn(rc, rc);
6277 if (u8Type != pThis->u8Type)
6278 return SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("Config mismatch: u8Type - saved=%u config=%u"), u8Type, pThis->u8Type);
6279
6280 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6281 {
6282 bool fEnabled;
6283 rc = SSMR3GetBool(pSSM, &fEnabled);
6284 AssertRCReturn(rc, rc);
6285 if (!fEnabled)
6286 return SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("Ctr#%u onfig mismatch: fEnabled != true"), i);
6287
6288 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6289 {
6290 ATADevState const *pIf = &pThis->aCts[i].aIfs[j];
6291
6292 bool fInUse;
6293 rc = SSMR3GetBool(pSSM, &fInUse);
6294 AssertRCReturn(rc, rc);
6295 if (fInUse != (pIf->pDrvBase != NULL))
6296 return SSMR3SetCfgError(pSSM, RT_SRC_POS,
6297 N_("The %s VM is missing a %s device. Please make sure the source and target VMs have compatible storage configurations"),
6298 fInUse ? "target" : "source", ataStringifyLun(pIf->iLUN) );
6299
6300 char szSerialNumber[ATA_SERIAL_NUMBER_LENGTH+1];
6301 rc = SSMR3GetStrZ(pSSM, szSerialNumber, sizeof(szSerialNumber));
6302 AssertRCReturn(rc, rc);
6303 if (strcmp(szSerialNumber, pIf->szSerialNumber))
6304 LogRel(("PIIX3 ATA: LUN#%u config mismatch: Serial number - saved='%s' config='%s'\n",
6305 pIf->iLUN, szSerialNumber, pIf->szSerialNumber));
6306
6307 char szFirmwareRevision[ATA_FIRMWARE_REVISION_LENGTH+1];
6308 rc = SSMR3GetStrZ(pSSM, szFirmwareRevision, sizeof(szFirmwareRevision));
6309 AssertRCReturn(rc, rc);
6310 if (strcmp(szFirmwareRevision, pIf->szFirmwareRevision))
6311 LogRel(("PIIX3 ATA: LUN#%u config mismatch: Firmware revision - saved='%s' config='%s'\n",
6312 pIf->iLUN, szFirmwareRevision, pIf->szFirmwareRevision));
6313
6314 char szModelNumber[ATA_MODEL_NUMBER_LENGTH+1];
6315 rc = SSMR3GetStrZ(pSSM, szModelNumber, sizeof(szModelNumber));
6316 AssertRCReturn(rc, rc);
6317 if (strcmp(szModelNumber, pIf->szModelNumber))
6318 LogRel(("PIIX3 ATA: LUN#%u config mismatch: Model number - saved='%s' config='%s'\n",
6319 pIf->iLUN, szModelNumber, pIf->szModelNumber));
6320 }
6321 }
6322 }
6323 if (uPass != SSM_PASS_FINAL)
6324 return VINF_SUCCESS;
6325
6326 /*
6327 * Restore valid parts of the PCIATAState structure
6328 */
6329 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6330 {
6331 /* integrity check */
6332 if (!ataAsyncIOIsIdle(&pThis->aCts[i], false))
6333 {
6334 AssertMsgFailed(("Async I/O for controller %d is active\n", i));
6335 return VERR_INTERNAL_ERROR_4;
6336 }
6337
6338 SSMR3GetU8(pSSM, &pThis->aCts[i].iSelectedIf);
6339 SSMR3GetU8(pSSM, &pThis->aCts[i].iAIOIf);
6340 SSMR3GetU8(pSSM, &pThis->aCts[i].uAsyncIOState);
6341 SSMR3GetBool(pSSM, &pThis->aCts[i].fChainedTransfer);
6342 SSMR3GetBool(pSSM, (bool *)&pThis->aCts[i].fReset);
6343 SSMR3GetBool(pSSM, (bool *)&pThis->aCts[i].fRedo);
6344 SSMR3GetBool(pSSM, (bool *)&pThis->aCts[i].fRedoIdle);
6345 SSMR3GetBool(pSSM, (bool *)&pThis->aCts[i].fRedoDMALastDesc);
6346 SSMR3GetMem(pSSM, &pThis->aCts[i].BmDma, sizeof(pThis->aCts[i].BmDma));
6347 SSMR3GetGCPhys32(pSSM, &pThis->aCts[i].pFirstDMADesc);
6348 SSMR3GetGCPhys32(pSSM, &pThis->aCts[i].pLastDMADesc);
6349 SSMR3GetGCPhys32(pSSM, &pThis->aCts[i].pRedoDMABuffer);
6350 SSMR3GetU32(pSSM, &pThis->aCts[i].cbRedoDMABuffer);
6351
6352 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6353 {
6354 SSMR3GetBool(pSSM, &pThis->aCts[i].aIfs[j].fLBA48);
6355 SSMR3GetBool(pSSM, &pThis->aCts[i].aIfs[j].fATAPI);
6356 SSMR3GetBool(pSSM, &pThis->aCts[i].aIfs[j].fIrqPending);
6357 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].cMultSectors);
6358 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].PCHSGeometry.cCylinders);
6359 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].PCHSGeometry.cHeads);
6360 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].PCHSGeometry.cSectors);
6361 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].cSectorsPerIRQ);
6362 SSMR3GetU64(pSSM, &pThis->aCts[i].aIfs[j].cTotalSectors);
6363 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegFeature);
6364 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegFeatureHOB);
6365 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegError);
6366 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegNSector);
6367 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegNSectorHOB);
6368 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegSector);
6369 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegSectorHOB);
6370 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegLCyl);
6371 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegLCylHOB);
6372 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegHCyl);
6373 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegHCylHOB);
6374 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegSelect);
6375 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegStatus);
6376 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegCommand);
6377 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATARegDevCtl);
6378 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uATATransferMode);
6379 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].uTxDir);
6380 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].iBeginTransfer);
6381 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].iSourceSink);
6382 SSMR3GetBool(pSSM, &pThis->aCts[i].aIfs[j].fDMA);
6383 SSMR3GetBool(pSSM, &pThis->aCts[i].aIfs[j].fATAPITransfer);
6384 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].cbTotalTransfer);
6385 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].cbElementaryTransfer);
6386 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].iIOBufferCur);
6387 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].iIOBufferEnd);
6388 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].iIOBufferPIODataStart);
6389 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].iIOBufferPIODataEnd);
6390 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].iATAPILBA);
6391 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].cbATAPISector);
6392 SSMR3GetMem(pSSM, &pThis->aCts[i].aIfs[j].aATAPICmd, sizeof(pThis->aCts[i].aIfs[j].aATAPICmd));
6393 if (uVersion > ATA_SAVED_STATE_VERSION_WITHOUT_FULL_SENSE)
6394 {
6395 SSMR3GetMem(pSSM, pThis->aCts[i].aIfs[j].abATAPISense, sizeof(pThis->aCts[i].aIfs[j].abATAPISense));
6396 }
6397 else
6398 {
6399 uint8_t uATAPISenseKey, uATAPIASC;
6400 memset(pThis->aCts[i].aIfs[j].abATAPISense, '\0', sizeof(pThis->aCts[i].aIfs[j].abATAPISense));
6401 pThis->aCts[i].aIfs[j].abATAPISense[0] = 0x70 | (1 << 7);
6402 pThis->aCts[i].aIfs[j].abATAPISense[7] = 10;
6403 SSMR3GetU8(pSSM, &uATAPISenseKey);
6404 SSMR3GetU8(pSSM, &uATAPIASC);
6405 pThis->aCts[i].aIfs[j].abATAPISense[2] = uATAPISenseKey & 0x0f;
6406 pThis->aCts[i].aIfs[j].abATAPISense[12] = uATAPIASC;
6407 }
6408 /** @todo triple-check this hack after passthrough is working */
6409 SSMR3GetU8(pSSM, &pThis->aCts[i].aIfs[j].cNotifiedMediaChange);
6410 if (uVersion > ATA_SAVED_STATE_VERSION_WITHOUT_EVENT_STATUS)
6411 SSMR3GetU32(pSSM, (uint32_t*)&pThis->aCts[i].aIfs[j].MediaEventStatus);
6412 else
6413 pThis->aCts[i].aIfs[j].MediaEventStatus = ATA_EVENT_STATUS_UNCHANGED;
6414 SSMR3GetMem(pSSM, &pThis->aCts[i].aIfs[j].Led, sizeof(pThis->aCts[i].aIfs[j].Led));
6415 SSMR3GetU32(pSSM, &pThis->aCts[i].aIfs[j].cbIOBuffer);
6416 if (pThis->aCts[i].aIfs[j].cbIOBuffer)
6417 {
6418 if (pThis->aCts[i].aIfs[j].CTX_SUFF(pbIOBuffer))
6419 SSMR3GetMem(pSSM, pThis->aCts[i].aIfs[j].CTX_SUFF(pbIOBuffer), pThis->aCts[i].aIfs[j].cbIOBuffer);
6420 else
6421 {
6422 LogRel(("ATA: No buffer for %d/%d\n", i, j));
6423 if (SSMR3HandleGetAfter(pSSM) != SSMAFTER_DEBUG_IT)
6424 return SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("No buffer for %d/%d"), i, j);
6425
6426 /* skip the buffer if we're loading for the debugger / animator. */
6427 uint8_t u8Ignored;
6428 size_t cbLeft = pThis->aCts[i].aIfs[j].cbIOBuffer;
6429 while (cbLeft-- > 0)
6430 SSMR3GetU8(pSSM, &u8Ignored);
6431 }
6432 }
6433 else
6434 Assert(pThis->aCts[i].aIfs[j].CTX_SUFF(pbIOBuffer) == NULL);
6435 }
6436 }
6437 if (uVersion <= ATA_SAVED_STATE_VERSION_VBOX_30)
6438 SSMR3GetU8(pSSM, &pThis->u8Type);
6439
6440 rc = SSMR3GetU32(pSSM, &u32);
6441 if (RT_FAILURE(rc))
6442 return rc;
6443 if (u32 != ~0U)
6444 {
6445 AssertMsgFailed(("u32=%#x expected ~0\n", u32));
6446 rc = VERR_SSM_DATA_UNIT_FORMAT_CHANGED;
6447 return rc;
6448 }
6449
6450 return VINF_SUCCESS;
6451}
6452
6453/**
6454 * Convert config value to DEVPCBIOSBOOT.
6455 *
6456 * @returns VBox status code.
6457 * @param pDevIns The device instance data.
6458 * @param pCfgHandle Configuration handle.
6459 * @param penmChipset Where to store the chipset type.
6460 */
6461static int ataControllerFromCfg(PPDMDEVINS pDevIns, PCFGMNODE pCfgHandle, CHIPSET *penmChipset)
6462{
6463 char szType[20];
6464
6465 int rc = CFGMR3QueryStringDef(pCfgHandle, "Type", &szType[0], sizeof(szType), "PIIX4");
6466 if (RT_FAILURE(rc))
6467 return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
6468 N_("Configuration error: Querying \"Type\" as a string failed"));
6469 if (!strcmp(szType, "PIIX3"))
6470 *penmChipset = CHIPSET_PIIX3;
6471 else if (!strcmp(szType, "PIIX4"))
6472 *penmChipset = CHIPSET_PIIX4;
6473 else if (!strcmp(szType, "ICH6"))
6474 *penmChipset = CHIPSET_ICH6;
6475 else
6476 {
6477 PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
6478 N_("Configuration error: The \"Type\" value \"%s\" is unknown"),
6479 szType);
6480 rc = VERR_INTERNAL_ERROR;
6481 }
6482 return rc;
6483}
6484
6485
6486/**
6487 * Construct a device instance for a VM.
6488 *
6489 * @returns VBox status.
6490 * @param pDevIns The device instance data.
6491 * If the registration structure is needed, pDevIns->pDevReg points to it.
6492 * @param iInstance Instance number. Use this to figure out which registers and such to use.
6493 * The device number is also found in pDevIns->iInstance, but since it's
6494 * likely to be freqently used PDM passes it as parameter.
6495 * @param pCfgHandle Configuration node handle for the device. Use this to obtain the configuration
6496 * of the device instance. It's also found in pDevIns->pCfgHandle, but like
6497 * iInstance it's expected to be used a bit in this function.
6498 */
6499static DECLCALLBACK(int) ataR3Construct(PPDMDEVINS pDevIns, int iInstance, PCFGMNODE pCfgHandle)
6500{
6501 PCIATAState *pThis = PDMINS_2_DATA(pDevIns, PCIATAState *);
6502 PPDMIBASE pBase;
6503 int rc;
6504 bool fGCEnabled;
6505 bool fR0Enabled;
6506 uint32_t DelayIRQMillies;
6507
6508 Assert(iInstance == 0);
6509
6510 /*
6511 * Initialize NIL handle values (for the destructor).
6512 */
6513 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6514 {
6515 pThis->aCts[i].AsyncIOSem = NIL_RTSEMEVENT;
6516 pThis->aCts[i].SuspendIOSem = NIL_RTSEMEVENT;
6517 pThis->aCts[i].AsyncIORequestMutex = NIL_RTSEMMUTEX;
6518 pThis->aCts[i].AsyncIOThread = NIL_RTTHREAD;
6519 }
6520
6521 /*
6522 * Validate and read configuration.
6523 */
6524 if (!CFGMR3AreValuesValid(pCfgHandle,
6525 "GCEnabled\0"
6526 "R0Enabled\0"
6527 "IRQDelay\0"
6528 "Type\0")
6529 /** @todo || invalid keys */)
6530 return PDMDEV_SET_ERROR(pDevIns, VERR_PDM_DEVINS_UNKNOWN_CFG_VALUES,
6531 N_("PIIX3 configuration error: unknown option specified"));
6532
6533 rc = CFGMR3QueryBoolDef(pCfgHandle, "GCEnabled", &fGCEnabled, true);
6534 if (RT_FAILURE(rc))
6535 return PDMDEV_SET_ERROR(pDevIns, rc,
6536 N_("PIIX3 configuration error: failed to read GCEnabled as boolean"));
6537 Log(("%s: fGCEnabled=%d\n", __FUNCTION__, fGCEnabled));
6538
6539 rc = CFGMR3QueryBoolDef(pCfgHandle, "R0Enabled", &fR0Enabled, true);
6540 if (RT_FAILURE(rc))
6541 return PDMDEV_SET_ERROR(pDevIns, rc,
6542 N_("PIIX3 configuration error: failed to read R0Enabled as boolean"));
6543 Log(("%s: fR0Enabled=%d\n", __FUNCTION__, fR0Enabled));
6544
6545 rc = CFGMR3QueryU32Def(pCfgHandle, "IRQDelay", &DelayIRQMillies, 0);
6546 if (RT_FAILURE(rc))
6547 return PDMDEV_SET_ERROR(pDevIns, rc,
6548 N_("PIIX3 configuration error: failed to read IRQDelay as integer"));
6549 Log(("%s: DelayIRQMillies=%d\n", __FUNCTION__, DelayIRQMillies));
6550 Assert(DelayIRQMillies < 50);
6551
6552 CHIPSET enmChipset = CHIPSET_PIIX3;
6553 rc = ataControllerFromCfg(pDevIns, pCfgHandle, &enmChipset);
6554 if (RT_FAILURE(rc))
6555 return rc;
6556 pThis->u8Type = (uint8_t)enmChipset;
6557
6558 /*
6559 * Initialize data (most of it anyway).
6560 */
6561 /* Status LUN. */
6562 pThis->IBase.pfnQueryInterface = ataStatus_QueryInterface;
6563 pThis->ILeds.pfnQueryStatusLed = ataStatus_QueryStatusLed;
6564
6565 /* PCI configuration space. */
6566 PCIDevSetVendorId(&pThis->dev, 0x8086); /* Intel */
6567
6568 /*
6569 * When adding more IDE chipsets, don't forget to update pci_bios_init_device()
6570 * as it explicitly checks for PCI id for IDE controllers.
6571 */
6572 switch (pThis->u8Type)
6573 {
6574 case CHIPSET_ICH6:
6575 PCIDevSetDeviceId(&pThis->dev, 0x269e); /* ICH6 IDE */
6576 /** @todo: do we need it? Do we need anything else? */
6577 pThis->dev.config[0x48] = 0x00; /* UDMACTL */
6578 pThis->dev.config[0x4A] = 0x00; /* UDMATIM */
6579 pThis->dev.config[0x4B] = 0x00;
6580 {
6581 /*
6582 * See www.intel.com/Assets/PDF/manual/298600.pdf p. 30
6583 * Report
6584 * WR_Ping-Pong_EN: must be set
6585 * PCR0, PCR1: 80-pin primary cable reporting for both disks
6586 * SCR0, SCR1: 80-pin secondary cable reporting for both disks
6587 */
6588 uint16_t u16Config = (1<<10) | (1<<7) | (1<<6) | (1<<5) | (1<<4) ;
6589 pThis->dev.config[0x54] = u16Config & 0xff;
6590 pThis->dev.config[0x55] = u16Config >> 8;
6591 }
6592 break;
6593 case CHIPSET_PIIX4:
6594 PCIDevSetDeviceId(&pThis->dev, 0x7111); /* PIIX4 IDE */
6595 PCIDevSetRevisionId(&pThis->dev, 0x01); /* PIIX4E */
6596 pThis->dev.config[0x48] = 0x00; /* UDMACTL */
6597 pThis->dev.config[0x4A] = 0x00; /* UDMATIM */
6598 pThis->dev.config[0x4B] = 0x00;
6599 break;
6600 case CHIPSET_PIIX3:
6601 PCIDevSetDeviceId(&pThis->dev, 0x7010); /* PIIX3 IDE */
6602 break;
6603 default:
6604 AssertMsgFailed(("Unsupported IDE chipset type: %d\n", pThis->u8Type));
6605 }
6606
6607 PCIDevSetCommand( &pThis->dev, PCI_COMMAND_IOACCESS | PCI_COMMAND_MEMACCESS | PCI_COMMAND_BUSMASTER);
6608 PCIDevSetClassProg( &pThis->dev, 0x8a); /* programming interface = PCI_IDE bus master is supported */
6609 PCIDevSetClassSub( &pThis->dev, 0x01); /* class_sub = PCI_IDE */
6610 PCIDevSetClassBase( &pThis->dev, 0x01); /* class_base = PCI_mass_storage */
6611 PCIDevSetHeaderType(&pThis->dev, 0x00);
6612
6613 pThis->pDevIns = pDevIns;
6614 pThis->fGCEnabled = fGCEnabled;
6615 pThis->fR0Enabled = fR0Enabled;
6616 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6617 {
6618 pThis->aCts[i].pDevInsR3 = pDevIns;
6619 pThis->aCts[i].pDevInsR0 = PDMDEVINS_2_R0PTR(pDevIns);
6620 pThis->aCts[i].pDevInsRC = PDMDEVINS_2_RCPTR(pDevIns);
6621 pThis->aCts[i].DelayIRQMillies = (uint32_t)DelayIRQMillies;
6622 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6623 {
6624 ATADevState *pIf = &pThis->aCts[i].aIfs[j];
6625
6626 pIf->iLUN = i * RT_ELEMENTS(pThis->aCts) + j;
6627 pIf->pDevInsR3 = pDevIns;
6628 pIf->pDevInsR0 = PDMDEVINS_2_R0PTR(pDevIns);
6629 pIf->pDevInsRC = PDMDEVINS_2_RCPTR(pDevIns);
6630 pIf->pControllerR3 = &pThis->aCts[i];
6631 pIf->pControllerR0 = MMHyperR3ToR0(PDMDevHlpGetVM(pDevIns), &pThis->aCts[i]);
6632 pIf->pControllerRC = MMHyperR3ToRC(PDMDevHlpGetVM(pDevIns), &pThis->aCts[i]);
6633 pIf->IBase.pfnQueryInterface = ataQueryInterface;
6634 pIf->IMountNotify.pfnMountNotify = ataMountNotify;
6635 pIf->IMountNotify.pfnUnmountNotify = ataUnmountNotify;
6636 pIf->Led.u32Magic = PDMLED_MAGIC;
6637 }
6638 }
6639
6640 Assert(RT_ELEMENTS(pThis->aCts) == 2);
6641 pThis->aCts[0].irq = 14;
6642 pThis->aCts[0].IOPortBase1 = 0x1f0;
6643 pThis->aCts[0].IOPortBase2 = 0x3f6;
6644 pThis->aCts[1].irq = 15;
6645 pThis->aCts[1].IOPortBase1 = 0x170;
6646 pThis->aCts[1].IOPortBase2 = 0x376;
6647
6648 /*
6649 * Register the PCI device.
6650 * N.B. There's a hack in the PIIX3 PCI bridge device to assign this
6651 * device the slot next to itself.
6652 */
6653 rc = PDMDevHlpPCIRegister(pDevIns, &pThis->dev);
6654 if (RT_FAILURE(rc))
6655 return PDMDEV_SET_ERROR(pDevIns, rc,
6656 N_("PIIX3 cannot register PCI device"));
6657 AssertMsg(pThis->dev.devfn == 9 || iInstance != 0, ("pThis->dev.devfn=%d\n", pThis->dev.devfn));
6658 rc = PDMDevHlpPCIIORegionRegister(pDevIns, 4, 0x10, PCI_ADDRESS_SPACE_IO, ataBMDMAIORangeMap);
6659 if (RT_FAILURE(rc))
6660 return PDMDEV_SET_ERROR(pDevIns, rc,
6661 N_("PIIX3 cannot register PCI I/O region for BMDMA"));
6662
6663 /*
6664 * Register the I/O ports.
6665 * The ports are all hardcoded and enforced by the PIIX3 host bridge controller.
6666 */
6667 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6668 {
6669 rc = PDMDevHlpIOPortRegister(pDevIns, pThis->aCts[i].IOPortBase1, 8, (RTHCPTR)i,
6670 ataIOPortWrite1, ataIOPortRead1, ataIOPortWriteStr1, ataIOPortReadStr1, "ATA I/O Base 1");
6671 if (RT_FAILURE(rc))
6672 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register I/O handlers"));
6673
6674 if (fGCEnabled)
6675 {
6676 rc = PDMDevHlpIOPortRegisterGC(pDevIns, pThis->aCts[i].IOPortBase1, 8, (RTGCPTR)i,
6677 "ataIOPortWrite1", "ataIOPortRead1", "ataIOPortWriteStr1", "ataIOPortReadStr1", "ATA I/O Base 1");
6678 if (RT_FAILURE(rc))
6679 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register I/O handlers (GC)"));
6680 }
6681
6682 if (fR0Enabled)
6683 {
6684#if 1
6685 rc = PDMDevHlpIOPortRegisterR0(pDevIns, pThis->aCts[i].IOPortBase1, 8, (RTR0PTR)i,
6686 "ataIOPortWrite1", "ataIOPortRead1", NULL, NULL, "ATA I/O Base 1");
6687#else
6688 rc = PDMDevHlpIOPortRegisterR0(pDevIns, pThis->aCts[i].IOPortBase1, 8, (RTR0PTR)i,
6689 "ataIOPortWrite1", "ataIOPortRead1", "ataIOPortWriteStr1", "ataIOPortReadStr1", "ATA I/O Base 1");
6690#endif
6691 if (RT_FAILURE(rc))
6692 return PDMDEV_SET_ERROR(pDevIns, rc, "PIIX3 cannot register I/O handlers (R0).");
6693 }
6694
6695 rc = PDMDevHlpIOPortRegister(pDevIns, pThis->aCts[i].IOPortBase2, 1, (RTHCPTR)i,
6696 ataIOPortWrite2, ataIOPortRead2, NULL, NULL, "ATA I/O Base 2");
6697 if (RT_FAILURE(rc))
6698 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register base2 I/O handlers"));
6699
6700 if (fGCEnabled)
6701 {
6702 rc = PDMDevHlpIOPortRegisterGC(pDevIns, pThis->aCts[i].IOPortBase2, 1, (RTGCPTR)i,
6703 "ataIOPortWrite2", "ataIOPortRead2", NULL, NULL, "ATA I/O Base 2");
6704 if (RT_FAILURE(rc))
6705 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register base2 I/O handlers (GC)"));
6706 }
6707 if (fR0Enabled)
6708 {
6709 rc = PDMDevHlpIOPortRegisterR0(pDevIns, pThis->aCts[i].IOPortBase2, 1, (RTR0PTR)i,
6710 "ataIOPortWrite2", "ataIOPortRead2", NULL, NULL, "ATA I/O Base 2");
6711 if (RT_FAILURE(rc))
6712 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register base2 I/O handlers (R0)"));
6713 }
6714
6715 for (uint32_t j = 0; j < RT_ELEMENTS(pThis->aCts[i].aIfs); j++)
6716 {
6717 ATADevState *pIf = &pThis->aCts[i].aIfs[j];
6718 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatATADMA, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,
6719 "Number of ATA DMA transfers.", "/Devices/IDE%d/ATA%d/Unit%d/DMA", iInstance, i, j);
6720 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatATAPIO, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,
6721 "Number of ATA PIO transfers.", "/Devices/IDE%d/ATA%d/Unit%d/PIO", iInstance, i, j);
6722 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatATAPIDMA, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,
6723 "Number of ATAPI DMA transfers.", "/Devices/IDE%d/ATA%d/Unit%d/AtapiDMA", iInstance, i, j);
6724 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatATAPIPIO, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,
6725 "Number of ATAPI PIO transfers.", "/Devices/IDE%d/ATA%d/Unit%d/AtapiPIO", iInstance, i, j);
6726#ifdef VBOX_WITH_STATISTICS /** @todo release too. */
6727 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatReads, STAMTYPE_PROFILE_ADV, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6728 "Profiling of the read operations.", "/Devices/IDE%d/ATA%d/Unit%d/Reads", iInstance, i, j);
6729#endif
6730 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatBytesRead, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_BYTES,
6731 "Amount of data read.", "/Devices/IDE%d/ATA%d/Unit%d/ReadBytes", iInstance, i, j);
6732#ifdef VBOX_INSTRUMENT_DMA_WRITES
6733 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatInstrVDWrites,STAMTYPE_PROFILE_ADV, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6734 "Profiling of the VD DMA write operations.", "/Devices/IDE%d/ATA%d/Unit%d/InstrVDWrites", iInstance, i, j);
6735#endif
6736#ifdef VBOX_WITH_STATISTICS
6737 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatWrites, STAMTYPE_PROFILE_ADV, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6738 "Profiling of the write operations.", "/Devices/IDE%d/ATA%d/Unit%d/Writes", iInstance, i, j);
6739#endif
6740 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatBytesWritten, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_BYTES,
6741 "Amount of data written.", "/Devices/IDE%d/ATA%d/Unit%d/WrittenBytes", iInstance, i, j);
6742#ifdef VBOX_WITH_STATISTICS
6743 PDMDevHlpSTAMRegisterF(pDevIns, &pIf->StatFlushes, STAMTYPE_PROFILE, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6744 "Profiling of the flush operations.", "/Devices/IDE%d/ATA%d/Unit%d/Flushes", iInstance, i, j);
6745#endif
6746 }
6747#ifdef VBOX_WITH_STATISTICS /** @todo release too. */
6748 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatAsyncOps, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,
6749 "The number of async operations.", "/Devices/IDE%d/ATA%d/Async/Operations", iInstance, i);
6750 /** @todo STAMUNIT_MICROSECS */
6751 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatAsyncMinWait, STAMTYPE_U64_RESET, STAMVISIBILITY_ALWAYS, STAMUNIT_NONE,
6752 "Minimum wait in microseconds.", "/Devices/IDE%d/ATA%d/Async/MinWait", iInstance, i);
6753 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatAsyncMaxWait, STAMTYPE_U64_RESET, STAMVISIBILITY_ALWAYS, STAMUNIT_NONE,
6754 "Maximum wait in microseconds.", "/Devices/IDE%d/ATA%d/Async/MaxWait", iInstance, i);
6755 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatAsyncTimeUS, STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_NONE,
6756 "Total time spent in microseconds.", "/Devices/IDE%d/ATA%d/Async/TotalTimeUS", iInstance, i);
6757 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatAsyncTime, STAMTYPE_PROFILE_ADV, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6758 "Profiling of async operations.", "/Devices/IDE%d/ATA%d/Async/Time", iInstance, i);
6759 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aCts[i].StatLockWait, STAMTYPE_PROFILE, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL,
6760 "Profiling of locks.", "/Devices/IDE%d/ATA%d/Async/LockWait", iInstance, i);
6761#endif /* VBOX_WITH_STATISTICS */
6762
6763 /* Initialize per-controller critical section */
6764 rc = PDMDevHlpCritSectInit(pDevIns, &pThis->aCts[i].lock, RT_SRC_POS, "ATA%u", i);
6765 if (RT_FAILURE(rc))
6766 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot initialize critical section"));
6767 }
6768
6769 /*
6770 * Attach status driver (optional).
6771 */
6772 rc = PDMDevHlpDriverAttach(pDevIns, PDM_STATUS_LUN, &pThis->IBase, &pBase, "Status Port");
6773 if (RT_SUCCESS(rc))
6774 pThis->pLedsConnector = PDMIBASE_QUERY_INTERFACE(pBase, PDMILEDCONNECTORS);
6775 else if (rc != VERR_PDM_NO_ATTACHED_DRIVER)
6776 {
6777 AssertMsgFailed(("Failed to attach to status driver. rc=%Rrc\n", rc));
6778 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot attach to status driver"));
6779 }
6780
6781 /*
6782 * Attach the units.
6783 */
6784 uint32_t cbTotalBuffer = 0;
6785 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCts); i++)
6786 {
6787 PATACONTROLLER pCtl = &pThis->aCts[i];
6788
6789 /*
6790 * Start the worker thread.
6791 */
6792 pCtl->uAsyncIOState = ATA_AIO_NEW;
6793 rc = RTSemEventCreate(&pCtl->AsyncIOSem);
6794 AssertLogRelRCReturn(rc, rc);
6795 rc = RTSemEventCreate(&pCtl->SuspendIOSem);
6796 AssertLogRelRCReturn(rc, rc);
6797 rc = RTSemMutexCreate(&pCtl->AsyncIORequestMutex);
6798 AssertLogRelRCReturn(rc, rc);
6799 ataAsyncIOClearRequests(pCtl);
6800 rc = RTThreadCreateF(&pCtl->AsyncIOThread, ataAsyncIOLoop, (void *)pCtl, 128*1024 /*cbStack*/,
6801 RTTHREADTYPE_IO, RTTHREADFLAGS_WAITABLE, "ATA-%u", i);
6802 AssertLogRelRCReturn(rc, rc);
6803 Assert(pCtl->AsyncIOThread != NIL_RTTHREAD && pCtl->AsyncIOSem != NIL_RTSEMEVENT && pCtl->SuspendIOSem != NIL_RTSEMEVENT && pCtl->AsyncIORequestMutex != NIL_RTSEMMUTEX);
6804 Log(("%s: controller %d AIO thread id %#x; sem %p susp_sem %p mutex %p\n", __FUNCTION__, i, pCtl->AsyncIOThread, pCtl->AsyncIOSem, pCtl->SuspendIOSem, pCtl->AsyncIORequestMutex));
6805
6806 for (uint32_t j = 0; j < RT_ELEMENTS(pCtl->aIfs); j++)
6807 {
6808 static const char *s_apszDescs[RT_ELEMENTS(pThis->aCts)][RT_ELEMENTS(pCtl->aIfs)] =
6809 {
6810 { "Primary Master", "Primary Slave" },
6811 { "Secondary Master", "Secondary Slave" }
6812 };
6813
6814 /*
6815 * Try attach the block device and get the interfaces,
6816 * required as well as optional.
6817 */
6818 ATADevState *pIf = &pCtl->aIfs[j];
6819
6820 rc = PDMDevHlpDriverAttach(pDevIns, pIf->iLUN, &pIf->IBase, &pIf->pDrvBase, s_apszDescs[i][j]);
6821 if (RT_SUCCESS(rc))
6822 {
6823 rc = ataConfigLun(pDevIns, pIf);
6824 if (RT_SUCCESS(rc))
6825 {
6826 /*
6827 * Init vendor product data.
6828 */
6829 static const char *s_apszCFGMKeys[RT_ELEMENTS(pThis->aCts)][RT_ELEMENTS(pCtl->aIfs)] =
6830 {
6831 { "PrimaryMaster", "PrimarySlave" },
6832 { "SecondaryMaster", "SecondarySlave" }
6833 };
6834
6835 /* Generate a default serial number. */
6836 char szSerial[ATA_SERIAL_NUMBER_LENGTH+1];
6837 RTUUID Uuid;
6838 if (pIf->pDrvBlock)
6839 rc = pIf->pDrvBlock->pfnGetUuid(pIf->pDrvBlock, &Uuid);
6840 else
6841 RTUuidClear(&Uuid);
6842
6843 if (RT_FAILURE(rc) || RTUuidIsNull(&Uuid))
6844 {
6845 /* Generate a predictable serial for drives which don't have a UUID. */
6846 RTStrPrintf(szSerial, sizeof(szSerial), "VB%x-%04x%04x",
6847 pIf->iLUN + pDevIns->iInstance * 32,
6848 pThis->aCts[i].IOPortBase1, pThis->aCts[i].IOPortBase2);
6849 }
6850 else
6851 RTStrPrintf(szSerial, sizeof(szSerial), "VB%08x-%08x", Uuid.au32[0], Uuid.au32[3]);
6852
6853 /* Get user config if present using defaults otherwise. */
6854 PCFGMNODE pCfgNode = CFGMR3GetChild(pCfgHandle, s_apszCFGMKeys[i][j]);
6855 rc = CFGMR3QueryStringDef(pCfgNode, "SerialNumber", pIf->szSerialNumber, sizeof(pIf->szSerialNumber),
6856 szSerial);
6857 if (RT_FAILURE(rc))
6858 {
6859 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6860 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6861 N_("PIIX3 configuration error: \"SerialNumber\" is longer than 20 bytes"));
6862 return PDMDEV_SET_ERROR(pDevIns, rc,
6863 N_("PIIX3 configuration error: failed to read \"SerialNumber\" as string"));
6864 }
6865
6866 rc = CFGMR3QueryStringDef(pCfgNode, "FirmwareRevision", pIf->szFirmwareRevision, sizeof(pIf->szFirmwareRevision),
6867 "1.0");
6868 if (RT_FAILURE(rc))
6869 {
6870 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6871 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6872 N_("PIIX3 configuration error: \"FirmwareRevision\" is longer than 8 bytes"));
6873 return PDMDEV_SET_ERROR(pDevIns, rc,
6874 N_("PIIX3 configuration error: failed to read \"FirmwareRevision\" as string"));
6875 }
6876
6877 rc = CFGMR3QueryStringDef(pCfgNode, "ModelNumber", pIf->szModelNumber, sizeof(pIf->szModelNumber),
6878 pIf->fATAPI ? "VBOX CD-ROM" : "VBOX HARDDISK");
6879 if (RT_FAILURE(rc))
6880 {
6881 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6882 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6883 N_("PIIX3 configuration error: \"ModelNumber\" is longer than 40 bytes"));
6884 return PDMDEV_SET_ERROR(pDevIns, rc,
6885 N_("PIIX3 configuration error: failed to read \"ModelNumber\" as string"));
6886 }
6887
6888 /* There are three other identification strings for CD drives used for INQUIRY */
6889 if (pIf->fATAPI)
6890 {
6891 rc = CFGMR3QueryStringDef(pCfgNode, "ATAPIVendorId", pIf->szInquiryVendorId, sizeof(pIf->szInquiryVendorId),
6892 "VBOX");
6893 if (RT_FAILURE(rc))
6894 {
6895 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6896 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6897 N_("PIIX3 configuration error: \"ATAPIVendorId\" is longer than 16 bytes"));
6898 return PDMDEV_SET_ERROR(pDevIns, rc,
6899 N_("PIIX3 configuration error: failed to read \"ATAPIVendorId\" as string"));
6900 }
6901
6902 rc = CFGMR3QueryStringDef(pCfgNode, "ATAPIProductId", pIf->szInquiryProductId, sizeof(pIf->szInquiryProductId),
6903 "CD-ROM");
6904 if (RT_FAILURE(rc))
6905 {
6906 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6907 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6908 N_("PIIX3 configuration error: \"ATAPIProductId\" is longer than 16 bytes"));
6909 return PDMDEV_SET_ERROR(pDevIns, rc,
6910 N_("PIIX3 configuration error: failed to read \"ATAPIProductId\" as string"));
6911 }
6912
6913 rc = CFGMR3QueryStringDef(pCfgNode, "ATAPIRevision", pIf->szInquiryRevision, sizeof(pIf->szInquiryRevision),
6914 "1.0");
6915 if (RT_FAILURE(rc))
6916 {
6917 if (rc == VERR_CFGM_NOT_ENOUGH_SPACE)
6918 return PDMDEV_SET_ERROR(pDevIns, VERR_INVALID_PARAMETER,
6919 N_("PIIX3 configuration error: \"ATAPIRevision\" is longer than 4 bytes"));
6920 return PDMDEV_SET_ERROR(pDevIns, rc,
6921 N_("PIIX3 configuration error: failed to read \"ATAPIRevision\" as string"));
6922 }
6923 }
6924 }
6925
6926 }
6927 else if (rc == VERR_PDM_NO_ATTACHED_DRIVER)
6928 {
6929 pIf->pDrvBase = NULL;
6930 pIf->pDrvBlock = NULL;
6931 pIf->cbIOBuffer = 0;
6932 pIf->pbIOBufferR3 = NULL;
6933 pIf->pbIOBufferR0 = NIL_RTR0PTR;
6934 pIf->pbIOBufferRC = NIL_RTGCPTR;
6935 LogRel(("PIIX3 ATA: LUN#%d: no unit\n", pIf->iLUN));
6936 }
6937 else
6938 {
6939 switch (rc)
6940 {
6941 case VERR_ACCESS_DENIED:
6942 /* Error already catched by DrvHostBase */
6943 return rc;
6944 default:
6945 return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
6946 N_("PIIX3 cannot attach drive to the %s"),
6947 s_apszDescs[i][j]);
6948 }
6949 }
6950 cbTotalBuffer += pIf->cbIOBuffer;
6951 }
6952 }
6953
6954 rc = PDMDevHlpSSMRegisterEx(pDevIns, ATA_SAVED_STATE_VERSION, sizeof(*pThis) + cbTotalBuffer, NULL,
6955 NULL, ataLiveExec, NULL,
6956 ataSaveLoadPrep, ataSaveExec, NULL,
6957 ataSaveLoadPrep, ataLoadExec, NULL);
6958 if (RT_FAILURE(rc))
6959 return PDMDEV_SET_ERROR(pDevIns, rc, N_("PIIX3 cannot register save state handlers"));
6960
6961 /*
6962 * Initialize the device state.
6963 */
6964 return ataR3ResetCommon(pDevIns, true /*fConstruct*/);
6965}
6966
6967
6968/**
6969 * The device registration structure.
6970 */
6971const PDMDEVREG g_DevicePIIX3IDE =
6972{
6973 /* u32Version */
6974 PDM_DEVREG_VERSION,
6975 /* szDeviceName */
6976 "piix3ide",
6977 /* szRCMod */
6978 "VBoxDDGC.gc",
6979 /* szR0Mod */
6980 "VBoxDDR0.r0",
6981 /* pszDescription */
6982 "Intel PIIX3 ATA controller.\n"
6983 " LUN #0 is primary master.\n"
6984 " LUN #1 is primary slave.\n"
6985 " LUN #2 is secondary master.\n"
6986 " LUN #3 is secondary slave.\n"
6987 " LUN #999 is the LED/Status connector.",
6988 /* fFlags */
6989 PDM_DEVREG_FLAGS_DEFAULT_BITS | PDM_DEVREG_FLAGS_RC | PDM_DEVREG_FLAGS_R0 |
6990 PDM_DEVREG_FLAGS_FIRST_SUSPEND_NOTIFICATION | PDM_DEVREG_FLAGS_FIRST_POWEROFF_NOTIFICATION,
6991 /* fClass */
6992 PDM_DEVREG_CLASS_STORAGE,
6993 /* cMaxInstances */
6994 1,
6995 /* cbInstance */
6996 sizeof(PCIATAState),
6997 /* pfnConstruct */
6998 ataR3Construct,
6999 /* pfnDestruct */
7000 ataR3Destruct,
7001 /* pfnRelocate */
7002 ataR3Relocate,
7003 /* pfnIOCtl */
7004 NULL,
7005 /* pfnPowerOn */
7006 NULL,
7007 /* pfnReset */
7008 ataR3Reset,
7009 /* pfnSuspend */
7010 ataR3Suspend,
7011 /* pfnResume */
7012 ataR3Resume,
7013 /* pfnAttach */
7014 ataR3Attach,
7015 /* pfnDetach */
7016 ataR3Detach,
7017 /* pfnQueryInterface. */
7018 NULL,
7019 /* pfnInitComplete */
7020 NULL,
7021 /* pfnPowerOff */
7022 ataR3PowerOff,
7023 /* pfnSoftReset */
7024 NULL,
7025 /* u32VersionEnd */
7026 PDM_DEVREG_VERSION
7027};
7028#endif /* IN_RING3 */
7029#endif /* !VBOX_DEVICE_STRUCT_TESTCASE */
Note: See TracBrowser for help on using the repository browser.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette