3 Copyright (c) 2002-2005 Alexandr A. Telyatnikov (Alter)
9 This file contains IDE, ATA, ATAPI and SCSI Miniport definitions
10 and function prototypes.
13 Alexander A. Telyatnikov (Alter)
20 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
21 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
22 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
23 IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
24 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 Some definitions were taken from standard ATAPI.SYS sources from NT4 DDK by
36 Some definitions were taken from FreeBSD 4.3-4.6 ATA driver by
37 Søren Schmidt, Copyright (c) 1998,1999,2000,2001
39 Code was changed/updated by
40 Alter, Copyright (c) 2002-2004
68 #ifdef USE_DBGPRINT_LOGGER
69 #include "inc\PostDbgMesg.h"
70 #define DbgPrint DbgDump_Printf
71 #define Connect_DbgPrint() {DbgDump_SetAutoReconnect(TRUE); DbgDump_Reconnect();}
72 #else // USE_DBGPRINT_LOGGER
73 #define Connect_DbgPrint() {;}
74 #endif // USE_DBGPRINT_LOGGER
76 #ifdef SCSI_PORT_DBG_PRINT
82 ULONG DebugPrintLevel
,
87 #define PRINT_PREFIX 0,
89 #define KdPrint3(_x_) ScsiDebugPrint _x_ {;}
90 #define KdPrint2(_x_) {ScsiDebugPrint("%x: ", PsGetCurrentThread()) ; ScsiDebugPrint _x_ ; }
91 #define KdPrint(_x_) ScsiDebugPrint _x_ {;}
93 #else // SCSI_PORT_DBG_PRINT
95 //#ifndef USE_DBGPRINT_LOGGER
102 //#endif // USE_DBGPRINT_LOGGER
106 // Note, that using DbgPrint on raised IRQL will crash w2k
107 // tis will not happen immediately, so we shall see some logs
108 //#define LOG_ON_RAISED_IRQL_W2K TRUE
109 //#define LOG_ON_RAISED_IRQL_W2K FALSE
111 #define KdPrint3(_x_) {if(LOG_ON_RAISED_IRQL_W2K || MajorVersion < 0x05 || KeGetCurrentIrql() <= 2){/*DbgPrint("%x: ", PsGetCurrentThread()) ;*/ DbgPrint _x_ ; if(g_LogToDisplay){ PrintNtConsole _x_ ;} }}
112 #define KdPrint2(_x_) {if(LOG_ON_RAISED_IRQL_W2K || MajorVersion < 0x05 || KeGetCurrentIrql() <= 2){/*DbgPrint("%x: ", PsGetCurrentThread()) ;*/ DbgPrint _x_ ; if(g_LogToDisplay){ PrintNtConsole _x_ ;} }}
113 #define KdPrint(_x_) {if(LOG_ON_RAISED_IRQL_W2K || MajorVersion < 0x05 || KeGetCurrentIrql() <= 2){/*DbgPrint("%x: ", PsGetCurrentThread()) ;*/ DbgPrint _x_ ; if(g_LogToDisplay){ PrintNtConsole _x_ ;} }}
115 #define PRINT_PREFIX_PTR ((PCHAR)&__tmp__kdprint__buff__)
116 #define PRINT_UPREFIX_PTR ((PWCHAR)&__tmp__kdprint__ubuff__)
117 #define PRINT_PREFIX PRINT_PREFIX_PTR,
118 #define KdPrint2(_x_) \
120 WCHAR __tmp__kdprint__ubuff__[256]; \
121 CHAR __tmp__kdprint__buff__[256]; \
122 UNICODE_STRING __tmp__usrt__buff__; \
124 swprintf (PRINT_UPREFIX_PTR, L"%hs", PRINT_PREFIX_PTR); \
125 __tmp__usrt__buff__.Buffer = PRINT_UPREFIX_PTR; \
126 __tmp__usrt__buff__.Length = \
127 __tmp__usrt__buff__.MaximumLength = strlen(PRINT_PREFIX_PTR); \
128 NtDisplayString(&__tmp__usrt__buff__); \
130 #define KdPrint(_x_) DbgPrint _x_
132 #endif // SCSI_PORT_DBG_PRINT
134 //#define AtapiStallExecution(dt) { KdPrint2((" AtapiStallExecution(%d)\n", dt)); ScsiPortStallExecution(dt); }
135 #define AtapiStallExecution(dt) { ScsiPortStallExecution(dt); }
145 #define PRINT_PREFIX "UniATA: "
147 //#define KdPrint3(_x_) {if(LOG_ON_RAISED_IRQL_W2K || MajorVersion < 0x05 || KeGetCurrentIrql() <= 2){/*DbgPrint("%x: ", PsGetCurrentThread()) ;*/ DbgPrint _x_ ; if(g_LogToDisplay){ PrintNtConsole _x_ ;} }}
148 #define KdPrint3(_x_) {;}
149 #define KdPrint2(_x_) {;}
150 #define KdPrint(_x_) {;}
151 #define Connect_DbgPrint() {;}
153 #define AtapiStallExecution(dt) ScsiPortStallExecution(dt)
157 // IDE register definition
159 #pragma pack(push, 1)
161 typedef union _IDE_REGISTERS_1
{
184 } IDE_REGISTERS_1
, *PIDE_REGISTERS_1
;
187 #define IDX_IO1_SZ sizeof(IDE_REGISTERS_1)
190 #define IDX_IO1_SZ sizeof(IDE_REGISTERS_1)
191 #define IDX_IO1_i_Data (FIELD_OFFSET(IDE_REGISTERS_1, i.Data )+IDX_IO1)
192 #define IDX_IO1_i_Error (FIELD_OFFSET(IDE_REGISTERS_1, i.Error )+IDX_IO1)
193 #define IDX_IO1_i_BlockCount (FIELD_OFFSET(IDE_REGISTERS_1, i.BlockCount )+IDX_IO1)
194 #define IDX_IO1_i_BlockNumber (FIELD_OFFSET(IDE_REGISTERS_1, i.BlockNumber )+IDX_IO1)
195 #define IDX_IO1_i_CylinderLow (FIELD_OFFSET(IDE_REGISTERS_1, i.CylinderLow )+IDX_IO1)
196 #define IDX_IO1_i_CylinderHigh (FIELD_OFFSET(IDE_REGISTERS_1, i.CylinderHigh)+IDX_IO1)
197 #define IDX_IO1_i_DriveSelect (FIELD_OFFSET(IDE_REGISTERS_1, i.DriveSelect )+IDX_IO1)
198 #define IDX_IO1_i_Status (FIELD_OFFSET(IDE_REGISTERS_1, i.Status )+IDX_IO1)
200 #define IDX_IO1_o IDX_IO1_SZ
201 #define IDX_IO1_o_SZ sizeof(IDE_REGISTERS_1)
203 #define IDX_IO1_o_Data (FIELD_OFFSET(IDE_REGISTERS_1, o.Data )+IDX_IO1_o)
204 #define IDX_IO1_o_Feature (FIELD_OFFSET(IDE_REGISTERS_1, o.Feature )+IDX_IO1_o)
205 #define IDX_IO1_o_BlockCount (FIELD_OFFSET(IDE_REGISTERS_1, o.BlockCount )+IDX_IO1_o)
206 #define IDX_IO1_o_BlockNumber (FIELD_OFFSET(IDE_REGISTERS_1, o.BlockNumber )+IDX_IO1_o)
207 #define IDX_IO1_o_CylinderLow (FIELD_OFFSET(IDE_REGISTERS_1, o.CylinderLow )+IDX_IO1_o)
208 #define IDX_IO1_o_CylinderHigh (FIELD_OFFSET(IDE_REGISTERS_1, o.CylinderHigh)+IDX_IO1_o)
209 #define IDX_IO1_o_DriveSelect (FIELD_OFFSET(IDE_REGISTERS_1, o.DriveSelect )+IDX_IO1_o)
210 #define IDX_IO1_o_Command (FIELD_OFFSET(IDE_REGISTERS_1, o.Command )+IDX_IO1_o)
212 typedef struct _IDE_REGISTERS_2
{
215 } IDE_REGISTERS_2
, *PIDE_REGISTERS_2
;
217 #define IDX_IO2 (IDX_IO1_o+IDX_IO1_o_SZ)
218 #define IDX_IO2_SZ sizeof(IDE_REGISTERS_2)
220 #define IDX_IO2_AltStatus (FIELD_OFFSET(IDE_REGISTERS_2, AltStatus )+IDX_IO2)
221 #define IDX_IO2_DriveAddress (FIELD_OFFSET(IDE_REGISTERS_2, DriveAddress)+IDX_IO2)
223 #define IDX_IO2_o (IDX_IO2+IDX_IO2_SZ)
224 #define IDX_IO2_o_SZ sizeof(IDE_REGISTERS_2)
226 #define IDX_IO2_o_Control (FIELD_OFFSET(IDE_REGISTERS_2, AltStatus )+IDX_IO2_o)
228 // Device Extension Device Flags
231 #define DFLAGS_DEVICE_PRESENT 0x0001 // Indicates that some device is present.
232 #define DFLAGS_ATAPI_DEVICE 0x0002 // Indicates whether ATAPI commands can be used.
233 #define DFLAGS_TAPE_DEVICE 0x0004 // Indicates whether this is a tape device.
234 #define DFLAGS_INT_DRQ 0x0008 // Indicates whether device interrupts as DRQ is set after
235 // receiving ATAPI Packet Command
236 #define DFLAGS_REMOVABLE_DRIVE 0x0010 // Indicates that the drive has the 'removable' bit set in
237 // identify data (offset 128)
238 #define DFLAGS_MEDIA_STATUS_ENABLED 0x0020 // Media status notification enabled
239 #define DFLAGS_ATAPI_CHANGER 0x0040 // Indicates atapi 2.5 changer present.
240 #define DFLAGS_SANYO_ATAPI_CHANGER 0x0080 // Indicates multi-platter device, not conforming to the 2.5 spec.
241 #define DFLAGS_CHANGER_INITED 0x0100 // Indicates that the init path for changers has already been done.
242 #define DFLAGS_LBA_ENABLED 0x0200 // Indicates that we should use LBA addressing rather than CHS
243 #define DFLAGS_DWORDIO_ENABLED 0x0400 // Indicates that we should use 32-bit IO
244 #define DFLAGS_WCACHE_ENABLED 0x0800 // Indicates that we use write cache
245 #define DFLAGS_RCACHE_ENABLED 0x1000 // Indicates that we use read cache
246 #define DFLAGS_ORIG_GEOMETRY 0x2000 //
247 #define DFLAGS_REINIT_DMA 0x4000 //
248 #define DFLAGS_HIDDEN 0x8000 // Hidden device, available only with special IOCTLs
249 // via communication virtual device
250 //#define DFLAGS_ 0x10000 //
252 // Used to disable 'advanced' features.
258 // ATAPI command definitions
261 #define ATAPI_MODE_SENSE 0x5A
262 #define ATAPI_MODE_SELECT 0x55
263 #define ATAPI_FORMAT_UNIT 0x24
265 // ATAPI Command Descriptor Block
267 typedef struct _MODE_SENSE_10
{
273 UCHAR ParameterListLengthMsb
;
274 UCHAR ParameterListLengthLsb
;
276 } MODE_SENSE_10
, *PMODE_SENSE_10
;
278 typedef struct _MODE_SELECT_10
{
284 UCHAR ParameterListLengthMsb
;
285 UCHAR ParameterListLengthLsb
;
287 } MODE_SELECT_10
, *PMODE_SELECT_10
;
289 typedef struct _MODE_PARAMETER_HEADER_10
{
290 UCHAR ModeDataLengthMsb
;
291 UCHAR ModeDataLengthLsb
;
294 }MODE_PARAMETER_HEADER_10
, *PMODE_PARAMETER_HEADER_10
;
297 // IDE command definitions
300 #define IDE_COMMAND_ATAPI_RESET 0x08
301 #define IDE_COMMAND_RECALIBRATE 0x10
302 #define IDE_COMMAND_READ 0x20
303 #define IDE_COMMAND_READ_NO_RETR 0x21
304 #define IDE_COMMAND_READ48 0x24
305 #define IDE_COMMAND_READ_DMA48 0x25
306 #define IDE_COMMAND_READ_DMA_Q48 0x26
307 #define IDE_COMMAND_READ_NATIVE_SIZE48 0x27
308 #define IDE_COMMAND_READ_MUL48 0x29
309 #define IDE_COMMAND_READ_STREAM_DMA48 0x2A
310 #define IDE_COMMAND_READ_STREAM48 0x2B
311 #define IDE_COMMAND_READ_LOG48 0x2f
312 #define IDE_COMMAND_WRITE 0x30
313 #define IDE_COMMAND_WRITE_NO_RETR 0x31
314 #define IDE_COMMAND_WRITE48 0x34
315 #define IDE_COMMAND_WRITE_DMA48 0x35
316 #define IDE_COMMAND_WRITE_DMA_Q48 0x36
317 #define IDE_COMMAND_SET_NATIVE_SIZE48 0x37
318 #define IDE_COMMAND_WRITE_MUL48 0x39
319 #define IDE_COMMAND_WRITE_STREAM_DMA48 0x3a
320 #define IDE_COMMAND_WRITE_STREAM48 0x3b
321 #define IDE_COMMAND_WRITE_FUA_DMA48 0x3d
322 #define IDE_COMMAND_WRITE_FUA_DMA_Q48 0x3e
323 #define IDE_COMMAND_WRITE_LOG48 0x3f
324 #define IDE_COMMAND_VERIFY 0x40
325 #define IDE_COMMAND_VERIFY48 0x42
326 #define IDE_COMMAND_READ_LOG_DMA48 0x47
327 #define IDE_COMMAND_WRITE_LOG_DMA48 0x57
328 #define IDE_COMMAND_TRUSTED_RCV 0x5c
329 #define IDE_COMMAND_TRUSTED_RCV_DMA 0x5d
330 #define IDE_COMMAND_TRUSTED_SEND 0x5e
331 #define IDE_COMMAND_TRUSTED_SEND_DMA 0x5f
332 #define IDE_COMMAND_SEEK 0x70
333 #define IDE_COMMAND_SET_DRIVE_PARAMETERS 0x91
334 #define IDE_COMMAND_ATAPI_PACKET 0xA0
335 #define IDE_COMMAND_ATAPI_IDENTIFY 0xA1
336 #define IDE_COMMAND_READ_MULTIPLE 0xC4
337 #define IDE_COMMAND_WRITE_MULTIPLE 0xC5
338 #define IDE_COMMAND_SET_MULTIPLE 0xC6
339 #define IDE_COMMAND_READ_DMA_Q 0xC7
340 #define IDE_COMMAND_READ_DMA 0xC8
341 #define IDE_COMMAND_WRITE_DMA 0xCA
342 #define IDE_COMMAND_WRITE_DMA_Q 0xCC
343 #define IDE_COMMAND_WRITE_MUL_FUA48 0xCE
344 #define IDE_COMMAND_GET_MEDIA_STATUS 0xDA
345 #define IDE_COMMAND_DOOR_LOCK 0xDE
346 #define IDE_COMMAND_DOOR_UNLOCK 0xDF
347 #define IDE_COMMAND_STANDBY_IMMED 0xE0 // flush and spin down
348 #define IDE_COMMAND_STANDBY 0xE2 // flush and spin down and enable autopowerdown timer
349 #define IDE_COMMAND_SLEEP 0xE6 // flush, spin down and deactivate interface
350 #define IDE_COMMAND_FLUSH_CACHE 0xE7
351 #define IDE_COMMAND_IDENTIFY 0xEC
352 #define IDE_COMMAND_MEDIA_EJECT 0xED
353 #define IDE_COMMAND_FLUSH_CACHE48 0xEA
354 #define IDE_COMMAND_ENABLE_MEDIA_STATUS 0xEF
355 #define IDE_COMMAND_SET_FEATURES 0xEF /* features command,
356 IDE_COMMAND_ENABLE_MEDIA_STATUS */
357 #define IDE_COMMAND_READ_NATIVE_SIZE 0xF8
358 #define IDE_COMMAND_SET_NATIVE_SIZE 0xF9
360 #define SCSIOP_ATA_PASSTHROUGH 0xCC //
363 // IDE status definitions
366 #define IDE_STATUS_SUCCESS 0x00
367 #define IDE_STATUS_ERROR 0x01
368 #define IDE_STATUS_INDEX 0x02
369 #define IDE_STATUS_CORRECTED_ERROR 0x04
370 #define IDE_STATUS_DRQ 0x08
371 #define IDE_STATUS_DSC 0x10
372 //#define IDE_STATUS_DWF 0x10 /* drive write fault */
373 #define IDE_STATUS_DMA 0x20 /* DMA ready */
374 #define IDE_STATUS_DWF 0x20 /* drive write fault */
375 #define IDE_STATUS_DRDY 0x40
376 #define IDE_STATUS_IDLE 0x50
377 #define IDE_STATUS_BUSY 0x80
381 // IDE drive select/head definitions
384 #define IDE_DRIVE_SELECT 0xA0
385 #define IDE_DRIVE_1 0x00
386 #define IDE_DRIVE_2 0x10
387 #define IDE_DRIVE_SELECT_1 (IDE_DRIVE_SELECT | IDE_DRIVE_1)
388 #define IDE_DRIVE_SELECT_2 (IDE_DRIVE_SELECT | IDE_DRIVE_2)
390 #define IDE_USE_LBA 0x40
393 // IDE drive control definitions
396 #define IDE_DC_DISABLE_INTERRUPTS 0x02
397 #define IDE_DC_RESET_CONTROLLER 0x04
398 #define IDE_DC_A_4BIT 0x80
399 #define IDE_DC_USE_HOB 0x80 // use high-order byte(s)
400 #define IDE_DC_REENABLE_CONTROLLER 0x00
402 // IDE error definitions
405 #define IDE_ERROR_ICRC 0x80
406 #define IDE_ERROR_BAD_BLOCK 0x80
407 #define IDE_ERROR_DATA_ERROR 0x40
408 #define IDE_ERROR_MEDIA_CHANGE 0x20
409 #define IDE_ERROR_ID_NOT_FOUND 0x10
410 #define IDE_ERROR_MEDIA_CHANGE_REQ 0x08
411 #define IDE_ERROR_COMMAND_ABORTED 0x04
412 #define IDE_ERROR_END_OF_MEDIA 0x02
413 #define IDE_ERROR_NO_MEDIA 0x02
414 #define IDE_ERROR_ILLEGAL_LENGTH 0x01
417 // ATAPI register definition
420 typedef union _ATAPI_REGISTERS_1
{
435 UCHAR InterruptReason
;
443 //IDE_REGISTERS_1 ide;
445 } ATAPI_REGISTERS_1
, *PATAPI_REGISTERS_1
;
447 #define IDX_ATAPI_IO1 IDX_IO1
448 #define IDX_ATAPI_IO1_SZ sizeof(ATAPI_REGISTERS_1)
450 #define IDX_ATAPI_IO1_i_Data (FIELD_OFFSET(ATAPI_REGISTERS_1, i.Data )+IDX_ATAPI_IO1)
451 #define IDX_ATAPI_IO1_i_Error (FIELD_OFFSET(ATAPI_REGISTERS_1, i.Error )+IDX_ATAPI_IO1)
452 #define IDX_ATAPI_IO1_i_InterruptReason (FIELD_OFFSET(ATAPI_REGISTERS_1, i.InterruptReason)+IDX_ATAPI_IO1)
453 #define IDX_ATAPI_IO1_i_Unused1 (FIELD_OFFSET(ATAPI_REGISTERS_1, i.Unused1 )+IDX_ATAPI_IO1)
454 #define IDX_ATAPI_IO1_i_ByteCountLow (FIELD_OFFSET(ATAPI_REGISTERS_1, i.ByteCountLow )+IDX_ATAPI_IO1)
455 #define IDX_ATAPI_IO1_i_ByteCountHigh (FIELD_OFFSET(ATAPI_REGISTERS_1, i.ByteCountHigh )+IDX_ATAPI_IO1)
456 #define IDX_ATAPI_IO1_i_DriveSelect (FIELD_OFFSET(ATAPI_REGISTERS_1, i.DriveSelect )+IDX_ATAPI_IO1)
457 #define IDX_ATAPI_IO1_i_Status (FIELD_OFFSET(ATAPI_REGISTERS_1, i.Status )+IDX_ATAPI_IO1)
459 #define IDX_ATAPI_IO1_o_Data (FIELD_OFFSET(ATAPI_REGISTERS_1, o.Data )+IDX_ATAPI_IO1)
460 #define IDX_ATAPI_IO1_o_Feature (FIELD_OFFSET(ATAPI_REGISTERS_1, o.Feature )+IDX_ATAPI_IO1)
461 #define IDX_ATAPI_IO1_o_Unused0 (FIELD_OFFSET(ATAPI_REGISTERS_1, o.Unused0 )+IDX_ATAPI_IO1)
462 #define IDX_ATAPI_IO1_o_Unused1 (FIELD_OFFSET(ATAPI_REGISTERS_1, o.Unused1 )+IDX_ATAPI_IO1)
463 #define IDX_ATAPI_IO1_o_ByteCountLow (FIELD_OFFSET(ATAPI_REGISTERS_1, o.ByteCountLow )+IDX_ATAPI_IO1)
464 #define IDX_ATAPI_IO1_o_ByteCountHigh (FIELD_OFFSET(ATAPI_REGISTERS_1, o.ByteCountHigh)+IDX_ATAPI_IO1)
465 #define IDX_ATAPI_IO1_o_DriveSelect (FIELD_OFFSET(ATAPI_REGISTERS_1, o.DriveSelect )+IDX_ATAPI_IO1)
466 #define IDX_ATAPI_IO1_o_Command (FIELD_OFFSET(ATAPI_REGISTERS_1, o.Command )+IDX_ATAPI_IO1)
469 typedef union _ATAPI_REGISTERS_2 {
475 //IDE_REGISTERS_2 ide;
477 } ATAPI_REGISTERS_2, *PATAPI_REGISTERS_2;
479 #define IDX_ATAPI_IO2 IDX_ATAPI_IO2_SZ
480 #define IDX_ATAPI_IO2_SZ sizeof(ATAPI_REGISTERS_2)
484 // ATAPI interrupt reasons
487 #define ATAPI_IR_COD 0x01
488 #define ATAPI_IR_IO 0x02
494 #define ATA_F_DMA 0x01 /* enable DMA */
495 #define ATA_F_OVL 0x02 /* enable overlap */
497 #define ATA_C_F_SETXFER 0x03 /* set transfer mode */
499 #define ATA_C_F_ENAB_WCACHE 0x02 /* enable write cache */
500 #define ATA_C_F_DIS_WCACHE 0x82 /* disable write cache */
502 #define ATA_C_F_ENAB_RCACHE 0xaa /* enable readahead cache */
503 #define ATA_C_F_DIS_RCACHE 0x55 /* disable readahead cache */
505 #define ATA_C_F_ENAB_RELIRQ 0x5d /* enable release interrupt */
506 #define ATA_C_F_DIS_RELIRQ 0xdd /* disable release interrupt */
508 #define ATA_C_F_ENAB_SRVIRQ 0x5e /* enable service interrupt */
509 #define ATA_C_F_DIS_SRVIRQ 0xde /* disable service interrupt */
511 #define ATA_C_F_ENAB_MEDIASTAT 0x95 /* enable media status */
512 #define ATA_C_F_DIS_MEDIASTAT 0x31 /* disable media status */
515 // ATAPI interrupt reasons
518 #define ATA_I_CMD 0x01 /* cmd (1) | data (0) */
519 #define ATA_I_IN 0x02 /* read (1) | write (0) */
520 #define ATA_I_RELEASE 0x04 /* released bus (1) */
521 #define ATA_I_TAGMASK 0xf8 /* tag mask */
526 typedef struct _IDENTIFY_DATA
{
527 UCHAR AtapiCmdSize
:2; // 00 00
528 #define ATAPI_PSIZE_12 0 /* 12 bytes */
529 #define ATAPI_PSIZE_16 1 /* 16 bytes */
531 UCHAR DrqType
:2; // 00 00
532 #define ATAPI_DRQT_MPROC 0 /* cpu 3 ms delay */
533 #define ATAPI_DRQT_INTR 1 /* intr 10 ms delay */
534 #define ATAPI_DRQT_ACCEL 2 /* accel 50 us delay */
538 #define ATAPI_TYPE_DIRECT 0 /* disk/floppy */
539 #define ATAPI_TYPE_TAPE 1 /* streaming tape */
540 #define ATAPI_TYPE_CDROM 5 /* CD-ROM device */
541 #define ATAPI_TYPE_OPTICAL 7 /* optical disk */
543 UCHAR CmdProtocol
:2; // 00 00
544 #define ATAPI_PROTO_ATAPI 2
545 // USHORT GeneralConfiguration; // 00 00
547 USHORT NumberOfCylinders
; // 02 1
548 USHORT Reserved1
; // 04 2
549 USHORT NumberOfHeads
; // 06 3
550 USHORT UnformattedBytesPerTrack
; // 08 4 // Now obsolete
551 USHORT UnformattedBytesPerSector
; // 0A 5 // Now obsolete
552 USHORT SectorsPerTrack
; // 0C 6
554 USHORT VendorUnique1
[3]; // 0E 7-9
555 UCHAR SerialNumber
[20]; // 14 10-19
557 USHORT BufferType
; // 28 20
558 #define ATA_BT_SINGLEPORTSECTOR 1 /* 1 port, 1 sector buffer */
559 #define ATA_BT_DUALPORTMULTI 2 /* 2 port, mult sector buffer */
560 #define ATA_BT_DUALPORTMULTICACHE 3 /* above plus track cache */
562 USHORT BufferSectorSize
; // 2A 21
563 USHORT NumberOfEccBytes
; // 2C 22
564 USHORT FirmwareRevision
[4]; // 2E 23-26
565 USHORT ModelNumber
[20]; // 36 27-46
566 UCHAR MaximumBlockTransfer
; // 5E 47
567 UCHAR VendorUnique2
; // 5F
569 USHORT DoubleWordIo
; // 60 48
571 USHORT Reserved62_0
:8; // 62 49
574 USHORT DisableIordy
:1;
575 USHORT SupportIordy
:1;
577 USHORT StandbyOverlap
:1;
578 USHORT SupportQTag
:1; /* supports queuing overlap */
579 USHORT SupportIDma
:1; /* interleaved DMA supported */
580 /* USHORT Capabilities; // 62 49
581 #define IDENTIFY_CAPABILITIES_SUPPORT_DMA 0x0100
582 #define IDENTIFY_CAPABILITIES_SUPPORT_LBA 0x0200
583 #define IDENTIFY_CAPABILITIES_DISABLE_IORDY 0x0400
584 #define IDENTIFY_CAPABILITIES_SUPPORT_IORDY 0x0800
585 #define IDENTIFY_CAPABILITIES_SOFT_RESET 0x1000
586 #define IDENTIFY_CAPABILITIES_STDBY_OVLP 0x2000
587 #define IDENTIFY_CAPABILITIES_SUPPORT_QTAG 0x4000
588 #define IDENTIFY_CAPABILITIES_SUPPORT_IDMA 0x8000*/
590 USHORT DeviceStandbyMin
:1; // 64 50
591 USHORT Reserved50_1
:13;
592 USHORT DeviceCapability1
:1;
593 USHORT DeviceCapability0
:1;
596 UCHAR Vendor51
; // 66 51
597 UCHAR PioCycleTimingMode
; // 67
599 UCHAR Vendor52
; // 68 52
600 UCHAR DmaCycleTimingMode
; // 69
602 USHORT TranslationFieldsValid
:1; // 6A 53 /* 54-58 */
603 USHORT PioTimingsValid
:1; /* 64-70 */
604 USHORT UdmaModesValid
:1; /* 88 */
607 USHORT NumberOfCurrentCylinders
; // 6C 54 \-
608 USHORT NumberOfCurrentHeads
; // 6E 55 \-
609 USHORT CurrentSectorsPerTrack
; // 70 56 /- obsolete USHORT[5]
610 ULONG CurrentSectorCapacity
; // 72 57-58 /-
612 USHORT CurrentMultiSector
:8; // 59
613 USHORT CurrentMultiSectorValid
:1;
614 USHORT Reserved59_9
:7;
616 ULONG UserAddressableSectors
; // 60-61
618 USHORT SingleWordDMASupport
: 8; // 62 \- obsolete
619 USHORT SingleWordDMAActive
: 8; // /-
621 USHORT MultiWordDMASupport
: 8; // 63
622 USHORT MultiWordDMAActive
: 8;
624 USHORT AdvancedPIOModes
: 8; // 64
625 USHORT Reserved4
: 8;
627 #define AdvancedPIOModes_3 1
628 #define AdvancedPIOModes_4 2
629 #define AdvancedPIOModes_5 4 // non-standard
631 USHORT MinimumMWXferCycleTime
; // 65
632 USHORT RecommendedMWXferCycleTime
; // 66
633 USHORT MinimumPIOCycleTime
; // 67
634 USHORT MinimumPIOCycleTimeIORDY
; // 68
636 USHORT Reserved69_70
[2]; // 69-70
637 USHORT ReleaseTimeOverlapped
; // 71
638 USHORT ReleaseTimeServiceCommand
; // 72
639 USHORT Reserved73_74
[2]; // 73-74
641 USHORT QueueLength
: 5; // 75
642 USHORT Reserved75_6
: 11;
644 USHORT SataCapabilities
; // 76
645 #define ATA_SATA_GEN1 0x0002
646 #define ATA_SATA_GEN2 0x0004
647 #define ATA_SUPPORT_NCQ 0x0100
648 #define ATA_SUPPORT_IFPWRMNGTRCV 0x0200
650 USHORT Reserved77
; // 77
652 USHORT SataSupport
; // 78
653 #define ATA_SUPPORT_NONZERO 0x0002
654 #define ATA_SUPPORT_AUTOACTIVATE 0x0004
655 #define ATA_SUPPORT_IFPWRMNGT 0x0008
656 #define ATA_SUPPORT_INORDERDATA 0x0010
658 USHORT SataEnable
; // 79
659 USHORT MajorRevision
; // 80
660 USHORT MinorRevision
; // 81
663 USHORT Smart
:1; // 82/85
674 USHORT Reserved_82_11
:1;
675 USHORT WriteBuffer
:1;
678 USHORT Reserved_82_15
:1;
680 USHORT Microcode
:1; // 83/86
687 USHORT Reserver_83_7
:1;
688 USHORT MaxSecurity
:1; //
689 USHORT AutoAcoustic
:1; //
690 USHORT Address48
:1; //
691 USHORT ConfigOverlay
:1; //
692 USHORT FlushCache
:1; //
693 USHORT FlushCache48
:1; //
694 USHORT SupportOne
:1; //
695 USHORT SupportZero
:1; //
697 USHORT SmartErrorLog
:1; // 84/87
698 USHORT SmartSelfTest
:1;
699 USHORT MediaSerialNo
:1;
700 USHORT MediaCardPass
:1;
703 USHORT Reserver_84_6
:8;
704 USHORT ExtendedOne
:1; //
705 USHORT ExtendedZero
:1; //
706 } FeaturesSupport
, FeaturesEnabled
;
708 USHORT UltraDMASupport
: 8; // 88
709 USHORT UltraDMAActive
: 8;
711 USHORT EraseTime
; // 89
712 USHORT EnhancedEraseTime
; // 90
713 USHORT CurentAPMLevel
; // 91
715 USHORT MasterPasswdRevision
; // 92
717 USHORT HwResMaster
: 8; // 93
718 USHORT HwResSlave
: 5;
719 USHORT HwResCableId
: 1;
720 USHORT HwResValid
: 2;
722 USHORT CurrentAcoustic
: 8; // 94
723 USHORT VendorAcoustic
: 8;
725 USHORT StreamMinReqSize
; // 95
726 USHORT StreamTransferTime
; // 96
727 USHORT StreamAccessLatency
; // 97
728 ULONG StreamGranularity
; // 98-99
730 ULONGLONG UserAddressableSectors48
; // 100-103
732 USHORT Reserved104
[2]; // 104-105
734 USHORT PhysLogSectorSize
; // 106
737 USHORT PLSS_Reserved
:8;
738 USHORT PLSS_LargeL
:1; // =1 if 117-118 are valid
739 USHORT PLSS_LargeP
:1;
740 USHORT PLSS_Signature
:2; // = 0x01 = 01b
743 USHORT Reserved107
[10]; // 107-116
745 ULONG LargeSectorSize
; // 117-118
747 USHORT Reserved117
[8]; // 119-126
749 USHORT RemovableStatus
; // 127
750 USHORT SecurityStatus
; // 128
752 USHORT FeaturesSupport4
; // 129
753 USHORT Reserved130
[30]; // 130-159
754 USHORT CfAdvPowerMode
; // 160
755 USHORT Reserved161
[14]; // 161-175
756 USHORT MediaSerial
[30]; // 176-205
757 USHORT Reserved206
[49]; // 205-254
758 USHORT Integrity
; // 255
759 } IDENTIFY_DATA
, *PIDENTIFY_DATA
;
762 // Identify data without the Reserved4.
765 #define IDENTIFY_DATA2 IDENTIFY_DATA
766 #define PIDENTIFY_DATA2 PIDENTIFY_DATA
768 /*typedef struct _IDENTIFY_DATA2 {
769 UCHAR AtapiCmdSize:2; // 00 00
771 UCHAR DrqType:2; // 00 00
776 UCHAR CmdProtocol:2; // 00 00
777 // USHORT GeneralConfiguration; // 00
779 USHORT NumberOfCylinders; // 02
780 USHORT Reserved1; // 04
781 USHORT NumberOfHeads; // 06
782 USHORT UnformattedBytesPerTrack; // 08
783 USHORT UnformattedBytesPerSector; // 0A
784 USHORT SectorsPerTrack; // 0C
785 USHORT VendorUnique1[3]; // 0E
786 UCHAR SerialNumber[20]; // 14
787 USHORT BufferType; // 28
788 USHORT BufferSectorSize; // 2A
789 USHORT NumberOfEccBytes; // 2C
790 USHORT FirmwareRevision[4]; // 2E
791 USHORT ModelNumber[20]; // 36
792 UCHAR MaximumBlockTransfer; // 5E
793 UCHAR VendorUnique2; // 5F
794 USHORT DoubleWordIo; // 60
795 USHORT Capabilities; // 62
796 USHORT Reserved2; // 64
797 UCHAR VendorUnique3; // 66
798 UCHAR PioCycleTimingMode; // 67
799 UCHAR VendorUnique4; // 68
800 UCHAR DmaCycleTimingMode; // 69
801 USHORT TranslationFieldsValid:1; // 6A
803 USHORT NumberOfCurrentCylinders; // 6C
804 USHORT NumberOfCurrentHeads; // 6E
805 USHORT CurrentSectorsPerTrack; // 70
806 ULONG CurrentSectorCapacity; // 72
807 } IDENTIFY_DATA2, *PIDENTIFY_DATA2;*/
809 #define IDENTIFY_DATA_SIZE sizeof(IDENTIFY_DATA)
811 // IDENTIFY DMA timing cycle modes.
812 #define IDENTIFY_DMA_CYCLES_MODE_0 0x00
813 #define IDENTIFY_DMA_CYCLES_MODE_1 0x01
814 #define IDENTIFY_DMA_CYCLES_MODE_2 0x02
816 #define PCI_DEV_HW_SPEC(idhi, idlo) \
817 { #idlo, 4, #idhi, 4}
819 typedef struct _BROKEN_CONTROLLER_INFORMATION {
821 ULONG VendorIdLength;
823 ULONG DeviceIdLength;
824 }BROKEN_CONTROLLER_INFORMATION, *PBROKEN_CONTROLLER_INFORMATION;
826 BROKEN_CONTROLLER_INFORMATION const BrokenAdapters[] = {
827 // CMD 640 ATA controller !WARNING! buggy chip data loss possible
828 PCI_DEV_HW_SPEC( 0640, 1095 ), //{ "1095", 4, "0640", 4},
830 PCI_DEV_HW_SPEC( 0601, 1039 ), //{ "1039", 4, "0601", 4}
831 // RZ 100? ATA controller !WARNING! buggy chip data loss possible
832 PCI_DEV_HW_SPEC( 1000, 1042 ),
833 PCI_DEV_HW_SPEC( 1001, 1042 )
836 #define BROKEN_ADAPTERS (sizeof(BrokenAdapters) / sizeof(BROKEN_CONTROLLER_INFORMATION))
838 typedef struct _NATIVE_MODE_CONTROLLER_INFORMATION {
840 ULONG VendorIdLength;
842 ULONG DeviceIdLength;
843 }NATIVE_MODE_CONTROLLER_INFORMATION, *PNATIVE_MODE_CONTROLLER_INFORMATION;
845 NATIVE_MODE_CONTROLLER_INFORMATION const NativeModeAdapters[] = {
846 PCI_DEV_HW_SPEC( 0105, 10ad ) //{ "10ad", 4, "0105", 4}
849 #define NUM_NATIVE_MODE_ADAPTERS (sizeof(NativeModeAdapters) / sizeof(NATIVE_MODE_CONTROLLER_INFORMATION))
852 // Beautification macros
857 #define GetStatus(chan, Status) \
858 Status = AtapiReadPort1(chan, IDX_IO2_AltStatus);
860 #define GetBaseStatus(chan, pStatus) \
861 pStatus = AtapiReadPort1(chan, IDX_IO1_i_Status);
863 #define WriteCommand(chan, _Command) \
864 AtapiWritePort1(chan, IDX_IO1_o_Command, _Command);
867 #define SelectDrive(chan, unit) { \
868 if(chan && chan->lun[unit] && chan->lun[unit]->DeviceFlags & DFLAGS_ATAPI_CHANGER) KdPrint3((" Select %d\n", unit)); \
869 AtapiWritePort1(chan, IDX_IO1_o_DriveSelect, (unit) ? IDE_DRIVE_SELECT_2 : IDE_DRIVE_SELECT_1); \
873 #define ReadBuffer(chan, Buffer, Count, timing) \
874 AtapiReadBuffer2(chan, IDX_IO1_i_Data, \
879 #define WriteBuffer(chan, Buffer, Count, timing) \
880 AtapiWriteBuffer2(chan, IDX_IO1_o_Data, \
885 #define ReadBuffer2(chan, Buffer, Count, timing) \
886 AtapiReadBuffer4(chan, IDX_IO1_i_Data, \
891 #define WriteBuffer2(chan, Buffer, Count, timing) \
892 AtapiWriteBuffer4(chan, IDX_IO1_o_Data, \
900 IN
struct _HW_CHANNEL
* chan
/*,
901 PIDE_REGISTERS_2 BaseIoAddress*/
907 IN
struct _HW_CHANNEL
* chan
/*,
908 PIDE_REGISTERS_2 BaseIoAddress*/
914 IN
struct _HW_CHANNEL
* chan
/*,
915 PIDE_REGISTERS_1 BaseIoAddress*/
921 IN
struct _HW_CHANNEL
* chan
/*,
922 PIDE_REGISTERS_1 BaseIoAddress*/
928 IN
struct _HW_CHANNEL
* chan
/*,
929 PIDE_REGISTERS_2 BaseIoAddress*/
935 IN
struct _HW_CHANNEL
* chan
/*,
936 PIDE_REGISTERS_2 BaseIoAddress*/
942 IN
struct _HW_CHANNEL
* chan
,/*
943 PIDE_REGISTERS_1 BaseIoAddress*/
947 /*#define IdeHardReset(BaseIoAddress,result) \
951 SelectDrive(BaseIoAddress,DeviceNumber); \
952 AtapiWritePort1(&BaseIoAddress->AltStatus,IDE_DC_DISABLE_INTERRUPTS | IDE_DC_RESET_CONTROLLER );\
953 ScsiPortStallExecution(50 * 1000);\
954 AtapiWritePort1(&BaseIoAddress->AltStatus,IDE_DC_REENABLE_CONTROLLER);\
955 5 seconds for reset \
956 for (i = 0; i < 1000 * (1+11); i++) {\
957 statusByte = AtapiReadPort1(&BaseIoAddress->AltStatus);\
958 if (statusByte != IDE_STATUS_IDLE && statusByte != IDE_STATUS_SUCCESS) {\
959 ScsiPortStallExecution((i<1000) ? 5 : 500);\
964 KdPrint2((PRINT_PREFIX "IdeHardReset: Status %x\n", statusByte)); \
965 if (i == 1000*1000) {\
973 #define IS_RDP(OperationCode)\
974 ((OperationCode == SCSIOP_ERASE)||\
975 (OperationCode == SCSIOP_LOAD_UNLOAD)||\
976 (OperationCode == SCSIOP_LOCATE)||\
977 (OperationCode == SCSIOP_REWIND) ||\
978 (OperationCode == SCSIOP_SPACE)||\
979 (OperationCode == SCSIOP_SEEK)||\
980 /* (OperationCode == SCSIOP_FORMAT_UNIT)||\
981 (OperationCode == SCSIOP_BLANK)||*/ \
982 (OperationCode == SCSIOP_WRITE_FILEMARKS))
988 BuildMechanismStatusSrb (
989 IN PVOID HwDeviceExtension
,
990 IN PSCSI_REQUEST_BLOCK Srb
995 BuildRequestSenseSrb (
996 IN PVOID HwDeviceExtension
,
997 IN PSCSI_REQUEST_BLOCK Srb
1002 AtapiHwInitializeChanger (
1003 IN PVOID HwDeviceExtension
,
1005 IN PMECHANICAL_STATUS_INFORMATION_HEADER MechanismStatus
1011 IN PVOID HwDeviceExtension
,
1012 IN PSCSI_REQUEST_BLOCK Srb
,
1019 IN PVOID HwDeviceExtension
,
1020 IN PSCSI_REQUEST_BLOCK Srb
,
1024 #define AtapiCopyMemory RtlCopyMemory
1033 #define AtapiStringCmp(s1, s2, n) _strnicmp(s1, s2, n)
1038 IN PVOID HwDeviceExtension
1044 IN PVOID HwDeviceExtension
,
1051 IN PVOID HwDeviceExtension
1056 IdeBuildSenseBuffer(
1057 IN PVOID HwDeviceExtension
,
1058 IN PSCSI_REQUEST_BLOCK Srb
1064 IN BOOLEAN EnableMSN
,
1065 IN PVOID HwDeviceExtension
,
1070 AtapiFindController(
1071 IN PVOID HwDeviceExtension
,
1073 IN PVOID BusInformation
,
1074 IN PCHAR ArgumentString
,
1075 IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo
,
1081 AtapiParseArgumentString(
1089 IN PVOID HwDeviceExtension
,
1090 IN ULONG DeviceNumber
,
1099 IN PVOID HwDeviceExtension
,
1100 IN ULONG DeviceNumber
,
1107 IN PVOID HwDeviceExtension
,
1109 IN ULONG deviceNumber
,
1113 #define UNIATA_FIND_DEV_UNHIDE 0x01
1118 IN PVOID HwDeviceExtension
,
1127 #endif //__cplusplus
1133 AtapiResetController(
1134 IN PVOID HwDeviceExtension
,
1141 IN PVOID HwDeviceExtension
,
1142 IN PSCSI_REQUEST_BLOCK Srb
1148 IN PVOID HwDeviceExtension
,
1149 IN PSCSI_REQUEST_BLOCK Srb
,
1156 // IN PVOID HwDeviceExtension,
1157 IN
struct _HW_DEVICE_EXTENSION
* deviceExtension
,
1158 IN ULONG DeviceNumber
,
1170 // IN PVOID HwDeviceExtension,
1171 IN
struct _HW_DEVICE_EXTENSION
* deviceExtension
,
1172 IN ULONG DeviceNumber
,
1185 AtaPioMode(PIDENTIFY_DATA2 ident
);
1189 AtaWmode(PIDENTIFY_DATA2 ident
);
1193 AtaUmode(PIDENTIFY_DATA2 ident
);
1199 IN PVOID DeferredContext
,
1200 IN PVOID SystemArgument1
,
1201 IN PVOID SystemArgument2
1204 //#define AtaCommand(de, devn, chan, cmd, cyl, hd, sec, cnt, feat, flg)
1208 AtaPio2Mode(LONG pio
);
1212 AtaPioMode(PIDENTIFY_DATA2 ident
);
1216 AtapiEnableInterrupts(
1217 IN PVOID HwDeviceExtension
,
1223 AtapiDisableInterrupts(
1224 IN PVOID HwDeviceExtension
,
1228 #define CHAN_NOT_SPECIFIED (0xffffffffL)
1229 #define CHAN_NOT_SPECIFIED_CHECK_CABLE (0xfffffffeL)
1230 #define DEVNUM_NOT_SPECIFIED (0xffffffffL)
1231 #define IOMODE_NOT_SPECIFIED (0xffffffffL)
1235 AtapiRegCheckDevValue(
1236 IN PVOID HwDeviceExtension
,
1245 AtapiRegCheckParameterValue(
1246 IN PVOID HwDeviceExtension
,
1247 IN PCWSTR PathSuffix
,
1252 extern ULONG g_LogToDisplay
;
1265 IN
struct _HW_DEVICE_EXTENSION
* deviceExtension
,
1266 IN
struct _IDE_BUSMASTER_REGISTERS
* BaseIoAddressBM_0
,
1273 IN
struct _HW_CHANNEL
* chan
,
1274 IN PIDE_REGISTERS_1 BaseIoAddress1
,
1275 IN PIDE_REGISTERS_2 BaseIoAddress2
1280 UniataInitSyncBaseIO(
1281 IN
struct _HW_CHANNEL
* chan
1287 IN
struct _HW_DEVICE_EXTENSION
* deviceExtension
,
1294 IN
struct _HW_CHANNEL
* chan
1307 UniAtaCalculateLBARegsBack(
1308 struct _HW_LU_EXTENSION
* LunExt
,
1315 IN PVOID HwDeviceExtension
,
1317 IN ULONG deviceNumber
1320 #define ATA_CMD_FLAG_LBAIOsupp 0x01
1321 #define ATA_CMD_FLAG_48supp 0x02
1322 #define ATA_CMD_FLAG_48 0x04
1323 #define ATA_CMD_FLAG_DMA 0x08
1325 extern UCHAR AtaCommands48
[256];
1326 extern UCHAR AtaCommandFlags
[256];
1329 #define PrintNtConsole _PrintNtConsole
1331 #define PrintNtConsole(x) {;}
1338 #endif // __GLOBAL_H__