1/* 2 3 Linux Driver for Mylex DAC960/AcceleRAID/eXtremeRAID PCI RAID Controllers 4 5 Copyright 1998-2001 by Leonard N. Zubkoff <lnz@dandelion.com> 6 7 This program is free software; you may redistribute and/or modify it under 8 the terms of the GNU General Public License Version 2 as published by the 9 Free Software Foundation. 10 11 This program is distributed in the hope that it will be useful, but 12 WITHOUT ANY WARRANTY, without even the implied warranty of MERCHANTABILITY 13 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 for complete details. 15 16 The author respectfully requests that any modifications to this software be 17 sent directly to him for evaluation and testing. 18 19*/ 20 21 22/* 23 Define the maximum number of DAC960 Controllers supported by this driver. 24*/ 25 26#define DAC960_MaxControllers 8 27 28 29/* 30 Define the maximum number of Controller Channels supported by DAC960 31 V1 and V2 Firmware Controllers. 32*/ 33 34#define DAC960_V1_MaxChannels 3 35#define DAC960_V2_MaxChannels 4 36 37 38/* 39 Define the maximum number of Targets per Channel supported by DAC960 40 V1 and V2 Firmware Controllers. 41*/ 42 43#define DAC960_V1_MaxTargets 16 44#define DAC960_V2_MaxTargets 128 45 46 47/* 48 Define the maximum number of Logical Drives supported by DAC960 49 V1 and V2 Firmware Controllers. 50*/ 51 52#define DAC960_MaxLogicalDrives 32 53 54 55/* 56 Define the maximum number of Physical Devices supported by DAC960 57 V1 and V2 Firmware Controllers. 58*/ 59 60#define DAC960_V1_MaxPhysicalDevices 45 61#define DAC960_V2_MaxPhysicalDevices 272 62 63/* 64 Define the pci dma mask supported by DAC960 V1 and V2 Firmware Controlers 65 */ 66 67#define DAC690_V1_PciDmaMask 0xffffffff 68#define DAC690_V2_PciDmaMask 0xffffffffffffffffULL 69 70/* 71 Define a 32/64 bit I/O Address data type. 72*/ 73 74typedef unsigned long DAC960_IO_Address_T; 75 76 77/* 78 Define a 32/64 bit PCI Bus Address data type. 79*/ 80 81typedef unsigned long DAC960_PCI_Address_T; 82 83 84/* 85 Define a 32 bit Bus Address data type. 86*/ 87 88typedef unsigned int DAC960_BusAddress32_T; 89 90 91/* 92 Define a 64 bit Bus Address data type. 93*/ 94 95typedef unsigned long long DAC960_BusAddress64_T; 96 97 98/* 99 Define a 32 bit Byte Count data type. 100*/ 101 102typedef unsigned int DAC960_ByteCount32_T; 103 104 105/* 106 Define a 64 bit Byte Count data type. 107*/ 108 109typedef unsigned long long DAC960_ByteCount64_T; 110 111 112/* 113 dma_loaf is used by helper routines to divide a region of 114 dma mapped memory into smaller pieces, where those pieces 115 are not of uniform size. 116 */ 117 118struct dma_loaf { 119 void *cpu_base; 120 dma_addr_t dma_base; 121 size_t length; 122 void *cpu_free; 123 dma_addr_t dma_free; 124}; 125 126/* 127 Define the SCSI INQUIRY Standard Data structure. 128*/ 129 130typedef struct DAC960_SCSI_Inquiry 131{ 132 unsigned char PeripheralDeviceType:5; /* Byte 0 Bits 0-4 */ 133 unsigned char PeripheralQualifier:3; /* Byte 0 Bits 5-7 */ 134 unsigned char DeviceTypeModifier:7; /* Byte 1 Bits 0-6 */ 135 bool RMB:1; /* Byte 1 Bit 7 */ 136 unsigned char ANSI_ApprovedVersion:3; /* Byte 2 Bits 0-2 */ 137 unsigned char ECMA_Version:3; /* Byte 2 Bits 3-5 */ 138 unsigned char ISO_Version:2; /* Byte 2 Bits 6-7 */ 139 unsigned char ResponseDataFormat:4; /* Byte 3 Bits 0-3 */ 140 unsigned char :2; /* Byte 3 Bits 4-5 */ 141 bool TrmIOP:1; /* Byte 3 Bit 6 */ 142 bool AENC:1; /* Byte 3 Bit 7 */ 143 unsigned char AdditionalLength; /* Byte 4 */ 144 unsigned char :8; /* Byte 5 */ 145 unsigned char :8; /* Byte 6 */ 146 bool SftRe:1; /* Byte 7 Bit 0 */ 147 bool CmdQue:1; /* Byte 7 Bit 1 */ 148 bool :1; /* Byte 7 Bit 2 */ 149 bool Linked:1; /* Byte 7 Bit 3 */ 150 bool Sync:1; /* Byte 7 Bit 4 */ 151 bool WBus16:1; /* Byte 7 Bit 5 */ 152 bool WBus32:1; /* Byte 7 Bit 6 */ 153 bool RelAdr:1; /* Byte 7 Bit 7 */ 154 unsigned char VendorIdentification[8]; /* Bytes 8-15 */ 155 unsigned char ProductIdentification[16]; /* Bytes 16-31 */ 156 unsigned char ProductRevisionLevel[4]; /* Bytes 32-35 */ 157} 158DAC960_SCSI_Inquiry_T; 159 160 161/* 162 Define the SCSI INQUIRY Unit Serial Number structure. 163*/ 164 165typedef struct DAC960_SCSI_Inquiry_UnitSerialNumber 166{ 167 unsigned char PeripheralDeviceType:5; /* Byte 0 Bits 0-4 */ 168 unsigned char PeripheralQualifier:3; /* Byte 0 Bits 5-7 */ 169 unsigned char PageCode; /* Byte 1 */ 170 unsigned char :8; /* Byte 2 */ 171 unsigned char PageLength; /* Byte 3 */ 172 unsigned char ProductSerialNumber[28]; /* Bytes 4-31 */ 173} 174DAC960_SCSI_Inquiry_UnitSerialNumber_T; 175 176 177/* 178 Define the SCSI REQUEST SENSE Sense Key type. 179*/ 180 181typedef enum 182{ 183 DAC960_SenseKey_NoSense = 0x0, 184 DAC960_SenseKey_RecoveredError = 0x1, 185 DAC960_SenseKey_NotReady = 0x2, 186 DAC960_SenseKey_MediumError = 0x3, 187 DAC960_SenseKey_HardwareError = 0x4, 188 DAC960_SenseKey_IllegalRequest = 0x5, 189 DAC960_SenseKey_UnitAttention = 0x6, 190 DAC960_SenseKey_DataProtect = 0x7, 191 DAC960_SenseKey_BlankCheck = 0x8, 192 DAC960_SenseKey_VendorSpecific = 0x9, 193 DAC960_SenseKey_CopyAborted = 0xA, 194 DAC960_SenseKey_AbortedCommand = 0xB, 195 DAC960_SenseKey_Equal = 0xC, 196 DAC960_SenseKey_VolumeOverflow = 0xD, 197 DAC960_SenseKey_Miscompare = 0xE, 198 DAC960_SenseKey_Reserved = 0xF 199} 200__attribute__ ((packed)) 201DAC960_SCSI_RequestSenseKey_T; 202 203 204/* 205 Define the SCSI REQUEST SENSE structure. 206*/ 207 208typedef struct DAC960_SCSI_RequestSense 209{ 210 unsigned char ErrorCode:7; /* Byte 0 Bits 0-6 */ 211 bool Valid:1; /* Byte 0 Bit 7 */ 212 unsigned char SegmentNumber; /* Byte 1 */ 213 DAC960_SCSI_RequestSenseKey_T SenseKey:4; /* Byte 2 Bits 0-3 */ 214 unsigned char :1; /* Byte 2 Bit 4 */ 215 bool ILI:1; /* Byte 2 Bit 5 */ 216 bool EOM:1; /* Byte 2 Bit 6 */ 217 bool Filemark:1; /* Byte 2 Bit 7 */ 218 unsigned char Information[4]; /* Bytes 3-6 */ 219 unsigned char AdditionalSenseLength; /* Byte 7 */ 220 unsigned char CommandSpecificInformation[4]; /* Bytes 8-11 */ 221 unsigned char AdditionalSenseCode; /* Byte 12 */ 222 unsigned char AdditionalSenseCodeQualifier; /* Byte 13 */ 223} 224DAC960_SCSI_RequestSense_T; 225 226 227/* 228 Define the DAC960 V1 Firmware Command Opcodes. 229*/ 230 231typedef enum 232{ 233 /* I/O Commands */ 234 DAC960_V1_ReadExtended = 0x33, 235 DAC960_V1_WriteExtended = 0x34, 236 DAC960_V1_ReadAheadExtended = 0x35, 237 DAC960_V1_ReadExtendedWithScatterGather = 0xB3, 238 DAC960_V1_WriteExtendedWithScatterGather = 0xB4, 239 DAC960_V1_Read = 0x36, 240 DAC960_V1_ReadWithScatterGather = 0xB6, 241 DAC960_V1_Write = 0x37, 242 DAC960_V1_WriteWithScatterGather = 0xB7, 243 DAC960_V1_DCDB = 0x04, 244 DAC960_V1_DCDBWithScatterGather = 0x84, 245 DAC960_V1_Flush = 0x0A, 246 /* Controller Status Related Commands */ 247 DAC960_V1_Enquiry = 0x53, 248 DAC960_V1_Enquiry2 = 0x1C, 249 DAC960_V1_GetLogicalDriveElement = 0x55, 250 DAC960_V1_GetLogicalDriveInformation = 0x19, 251 DAC960_V1_IOPortRead = 0x39, 252 DAC960_V1_IOPortWrite = 0x3A, 253 DAC960_V1_GetSDStats = 0x3E, 254 DAC960_V1_GetPDStats = 0x3F, 255 DAC960_V1_PerformEventLogOperation = 0x72, 256 /* Device Related Commands */ 257 DAC960_V1_StartDevice = 0x10, 258 DAC960_V1_GetDeviceState = 0x50, 259 DAC960_V1_StopChannel = 0x13, 260 DAC960_V1_StartChannel = 0x12, 261 DAC960_V1_ResetChannel = 0x1A, 262 /* Commands Associated with Data Consistency and Errors */ 263 DAC960_V1_Rebuild = 0x09, 264 DAC960_V1_RebuildAsync = 0x16, 265 DAC960_V1_CheckConsistency = 0x0F, 266 DAC960_V1_CheckConsistencyAsync = 0x1E, 267 DAC960_V1_RebuildStat = 0x0C, 268 DAC960_V1_GetRebuildProgress = 0x27, 269 DAC960_V1_RebuildControl = 0x1F, 270 DAC960_V1_ReadBadBlockTable = 0x0B, 271 DAC960_V1_ReadBadDataTable = 0x25, 272 DAC960_V1_ClearBadDataTable = 0x26, 273 DAC960_V1_GetErrorTable = 0x17, 274 DAC960_V1_AddCapacityAsync = 0x2A, 275 DAC960_V1_BackgroundInitializationControl = 0x2B, 276 /* Configuration Related Commands */ 277 DAC960_V1_ReadConfig2 = 0x3D, 278 DAC960_V1_WriteConfig2 = 0x3C, 279 DAC960_V1_ReadConfigurationOnDisk = 0x4A, 280 DAC960_V1_WriteConfigurationOnDisk = 0x4B, 281 DAC960_V1_ReadConfiguration = 0x4E, 282 DAC960_V1_ReadBackupConfiguration = 0x4D, 283 DAC960_V1_WriteConfiguration = 0x4F, 284 DAC960_V1_AddConfiguration = 0x4C, 285 DAC960_V1_ReadConfigurationLabel = 0x48, 286 DAC960_V1_WriteConfigurationLabel = 0x49, 287 /* Firmware Upgrade Related Commands */ 288 DAC960_V1_LoadImage = 0x20, 289 DAC960_V1_StoreImage = 0x21, 290 DAC960_V1_ProgramImage = 0x22, 291 /* Diagnostic Commands */ 292 DAC960_V1_SetDiagnosticMode = 0x31, 293 DAC960_V1_RunDiagnostic = 0x32, 294 /* Subsystem Service Commands */ 295 DAC960_V1_GetSubsystemData = 0x70, 296 DAC960_V1_SetSubsystemParameters = 0x71, 297 /* Version 2.xx Firmware Commands */ 298 DAC960_V1_Enquiry_Old = 0x05, 299 DAC960_V1_GetDeviceState_Old = 0x14, 300 DAC960_V1_Read_Old = 0x02, 301 DAC960_V1_Write_Old = 0x03, 302 DAC960_V1_ReadWithScatterGather_Old = 0x82, 303 DAC960_V1_WriteWithScatterGather_Old = 0x83 304} 305__attribute__ ((packed)) 306DAC960_V1_CommandOpcode_T; 307 308 309/* 310 Define the DAC960 V1 Firmware Command Identifier type. 311*/ 312 313typedef unsigned char DAC960_V1_CommandIdentifier_T; 314 315 316/* 317 Define the DAC960 V1 Firmware Command Status Codes. 318*/ 319 320#define DAC960_V1_NormalCompletion 0x0000 /* Common */ 321#define DAC960_V1_CheckConditionReceived 0x0002 /* Common */ 322#define DAC960_V1_NoDeviceAtAddress 0x0102 /* Common */ 323#define DAC960_V1_InvalidDeviceAddress 0x0105 /* Common */ 324#define DAC960_V1_InvalidParameter 0x0105 /* Common */ 325#define DAC960_V1_IrrecoverableDataError 0x0001 /* I/O */ 326#define DAC960_V1_LogicalDriveNonexistentOrOffline 0x0002 /* I/O */ 327#define DAC960_V1_AccessBeyondEndOfLogicalDrive 0x0105 /* I/O */ 328#define DAC960_V1_BadDataEncountered 0x010C /* I/O */ 329#define DAC960_V1_DeviceBusy 0x0008 /* DCDB */ 330#define DAC960_V1_DeviceNonresponsive 0x000E /* DCDB */ 331#define DAC960_V1_CommandTerminatedAbnormally 0x000F /* DCDB */ 332#define DAC960_V1_UnableToStartDevice 0x0002 /* Device */ 333#define DAC960_V1_InvalidChannelOrTargetOrModifier 0x0105 /* Device */ 334#define DAC960_V1_ChannelBusy 0x0106 /* Device */ 335#define DAC960_V1_ChannelNotStopped 0x0002 /* Device */ 336#define DAC960_V1_AttemptToRebuildOnlineDrive 0x0002 /* Consistency */ 337#define DAC960_V1_RebuildBadBlocksEncountered 0x0003 /* Consistency */ 338#define DAC960_V1_NewDiskFailedDuringRebuild 0x0004 /* Consistency */ 339#define DAC960_V1_RebuildOrCheckAlreadyInProgress 0x0106 /* Consistency */ 340#define DAC960_V1_DependentDiskIsDead 0x0002 /* Consistency */ 341#define DAC960_V1_InconsistentBlocksFound 0x0003 /* Consistency */ 342#define DAC960_V1_InvalidOrNonredundantLogicalDrive 0x0105 /* Consistency */ 343#define DAC960_V1_NoRebuildOrCheckInProgress 0x0105 /* Consistency */ 344#define DAC960_V1_RebuildInProgress_DataValid 0x0000 /* Consistency */ 345#define DAC960_V1_RebuildFailed_LogicalDriveFailure 0x0002 /* Consistency */ 346#define DAC960_V1_RebuildFailed_BadBlocksOnOther 0x0003 /* Consistency */ 347#define DAC960_V1_RebuildFailed_NewDriveFailed 0x0004 /* Consistency */ 348#define DAC960_V1_RebuildSuccessful 0x0100 /* Consistency */ 349#define DAC960_V1_RebuildSuccessfullyTerminated 0x0107 /* Consistency */ 350#define DAC960_V1_BackgroundInitSuccessful 0x0100 /* Consistency */ 351#define DAC960_V1_BackgroundInitAborted 0x0005 /* Consistency */ 352#define DAC960_V1_NoBackgroundInitInProgress 0x0105 /* Consistency */ 353#define DAC960_V1_AddCapacityInProgress 0x0004 /* Consistency */ 354#define DAC960_V1_AddCapacityFailedOrSuspended 0x00F4 /* Consistency */ 355#define DAC960_V1_Config2ChecksumError 0x0002 /* Configuration */ 356#define DAC960_V1_ConfigurationSuspended 0x0106 /* Configuration */ 357#define DAC960_V1_FailedToConfigureNVRAM 0x0105 /* Configuration */ 358#define DAC960_V1_ConfigurationNotSavedStateChange 0x0106 /* Configuration */ 359#define DAC960_V1_SubsystemNotInstalled 0x0001 /* Subsystem */ 360#define DAC960_V1_SubsystemFailed 0x0002 /* Subsystem */ 361#define DAC960_V1_SubsystemBusy 0x0106 /* Subsystem */ 362 363typedef unsigned short DAC960_V1_CommandStatus_T; 364 365 366/* 367 Define the DAC960 V1 Firmware Enquiry Command reply structure. 368*/ 369 370typedef struct DAC960_V1_Enquiry 371{ 372 unsigned char NumberOfLogicalDrives; /* Byte 0 */ 373 unsigned int :24; /* Bytes 1-3 */ 374 unsigned int LogicalDriveSizes[32]; /* Bytes 4-131 */ 375 unsigned short FlashAge; /* Bytes 132-133 */ 376 struct { 377 bool DeferredWriteError:1; /* Byte 134 Bit 0 */ 378 bool BatteryLow:1; /* Byte 134 Bit 1 */ 379 unsigned char :6; /* Byte 134 Bits 2-7 */ 380 } StatusFlags; 381 unsigned char :8; /* Byte 135 */ 382 unsigned char MinorFirmwareVersion; /* Byte 136 */ 383 unsigned char MajorFirmwareVersion; /* Byte 137 */ 384 enum { 385 DAC960_V1_NoStandbyRebuildOrCheckInProgress = 0x00, 386 DAC960_V1_StandbyRebuildInProgress = 0x01, 387 DAC960_V1_BackgroundRebuildInProgress = 0x02, 388 DAC960_V1_BackgroundCheckInProgress = 0x03, 389 DAC960_V1_StandbyRebuildCompletedWithError = 0xFF, 390 DAC960_V1_BackgroundRebuildOrCheckFailed_DriveFailed = 0xF0, 391 DAC960_V1_BackgroundRebuildOrCheckFailed_LogicalDriveFailed = 0xF1, 392 DAC960_V1_BackgroundRebuildOrCheckFailed_OtherCauses = 0xF2, 393 DAC960_V1_BackgroundRebuildOrCheckSuccessfullyTerminated = 0xF3 394 } __attribute__ ((packed)) RebuildFlag; /* Byte 138 */ 395 unsigned char MaxCommands; /* Byte 139 */ 396 unsigned char OfflineLogicalDriveCount; /* Byte 140 */ 397 unsigned char :8; /* Byte 141 */ 398 unsigned short EventLogSequenceNumber; /* Bytes 142-143 */ 399 unsigned char CriticalLogicalDriveCount; /* Byte 144 */ 400 unsigned int :24; /* Bytes 145-147 */ 401 unsigned char DeadDriveCount; /* Byte 148 */ 402 unsigned char :8; /* Byte 149 */ 403 unsigned char RebuildCount; /* Byte 150 */ 404 struct { 405 unsigned char :3; /* Byte 151 Bits 0-2 */ 406 bool BatteryBackupUnitPresent:1; /* Byte 151 Bit 3 */ 407 unsigned char :3; /* Byte 151 Bits 4-6 */ 408 unsigned char :1; /* Byte 151 Bit 7 */ 409 } MiscFlags; 410 struct { 411 unsigned char TargetID; 412 unsigned char Channel; 413 } DeadDrives[21]; /* Bytes 152-194 */ 414 unsigned char Reserved[62]; /* Bytes 195-255 */ 415} 416__attribute__ ((packed)) 417DAC960_V1_Enquiry_T; 418 419 420/* 421 Define the DAC960 V1 Firmware Enquiry2 Command reply structure. 422*/ 423 424typedef struct DAC960_V1_Enquiry2 425{ 426 struct { 427 enum { 428 DAC960_V1_P_PD_PU = 0x01, 429 DAC960_V1_PL = 0x02, 430 DAC960_V1_PG = 0x10, 431 DAC960_V1_PJ = 0x11, 432 DAC960_V1_PR = 0x12, 433 DAC960_V1_PT = 0x13, 434 DAC960_V1_PTL0 = 0x14, 435 DAC960_V1_PRL = 0x15, 436 DAC960_V1_PTL1 = 0x16, 437 DAC960_V1_1164P = 0x20 438 } __attribute__ ((packed)) SubModel; /* Byte 0 */ 439 unsigned char ActualChannels; /* Byte 1 */ 440 enum { 441 DAC960_V1_FiveChannelBoard = 0x01, 442 DAC960_V1_ThreeChannelBoard = 0x02, 443 DAC960_V1_TwoChannelBoard = 0x03, 444 DAC960_V1_ThreeChannelASIC_DAC = 0x04 445 } __attribute__ ((packed)) Model; /* Byte 2 */ 446 enum { 447 DAC960_V1_EISA_Controller = 0x01, 448 DAC960_V1_MicroChannel_Controller = 0x02, 449 DAC960_V1_PCI_Controller = 0x03, 450 DAC960_V1_SCSItoSCSI_Controller = 0x08 451 } __attribute__ ((packed)) ProductFamily; /* Byte 3 */ 452 } HardwareID; /* Bytes 0-3 */ 453 /* MajorVersion.MinorVersion-FirmwareType-TurnID */ 454 struct { 455 unsigned char MajorVersion; /* Byte 4 */ 456 unsigned char MinorVersion; /* Byte 5 */ 457 unsigned char TurnID; /* Byte 6 */ 458 char FirmwareType; /* Byte 7 */ 459 } FirmwareID; /* Bytes 4-7 */ 460 unsigned char :8; /* Byte 8 */ 461 unsigned int :24; /* Bytes 9-11 */ 462 unsigned char ConfiguredChannels; /* Byte 12 */ 463 unsigned char ActualChannels; /* Byte 13 */ 464 unsigned char MaxTargets; /* Byte 14 */ 465 unsigned char MaxTags; /* Byte 15 */ 466 unsigned char MaxLogicalDrives; /* Byte 16 */ 467 unsigned char MaxArms; /* Byte 17 */ 468 unsigned char MaxSpans; /* Byte 18 */ 469 unsigned char :8; /* Byte 19 */ 470 unsigned int :32; /* Bytes 20-23 */ 471 unsigned int MemorySize; /* Bytes 24-27 */ 472 unsigned int CacheSize; /* Bytes 28-31 */ 473 unsigned int FlashMemorySize; /* Bytes 32-35 */ 474 unsigned int NonVolatileMemorySize; /* Bytes 36-39 */ 475 struct { 476 enum { 477 DAC960_V1_RamType_DRAM = 0x0, 478 DAC960_V1_RamType_EDO = 0x1, 479 DAC960_V1_RamType_SDRAM = 0x2, 480 DAC960_V1_RamType_Last = 0x7 481 } __attribute__ ((packed)) RamType:3; /* Byte 40 Bits 0-2 */ 482 enum { 483 DAC960_V1_ErrorCorrection_None = 0x0, 484 DAC960_V1_ErrorCorrection_Parity = 0x1, 485 DAC960_V1_ErrorCorrection_ECC = 0x2, 486 DAC960_V1_ErrorCorrection_Last = 0x7 487 } __attribute__ ((packed)) ErrorCorrection:3; /* Byte 40 Bits 3-5 */ 488 bool FastPageMode:1; /* Byte 40 Bit 6 */ 489 bool LowPowerMemory:1; /* Byte 40 Bit 7 */ 490 unsigned char :8; /* Bytes 41 */ 491 } MemoryType; 492 unsigned short ClockSpeed; /* Bytes 42-43 */ 493 unsigned short MemorySpeed; /* Bytes 44-45 */ 494 unsigned short HardwareSpeed; /* Bytes 46-47 */ 495 unsigned int :32; /* Bytes 48-51 */ 496 unsigned int :32; /* Bytes 52-55 */ 497 unsigned char :8; /* Byte 56 */ 498 unsigned char :8; /* Byte 57 */ 499 unsigned short :16; /* Bytes 58-59 */ 500 unsigned short MaxCommands; /* Bytes 60-61 */ 501 unsigned short MaxScatterGatherEntries; /* Bytes 62-63 */ 502 unsigned short MaxDriveCommands; /* Bytes 64-65 */ 503 unsigned short MaxIODescriptors; /* Bytes 66-67 */ 504 unsigned short MaxCombinedSectors; /* Bytes 68-69 */ 505 unsigned char Latency; /* Byte 70 */ 506 unsigned char :8; /* Byte 71 */ 507 unsigned char SCSITimeout; /* Byte 72 */ 508 unsigned char :8; /* Byte 73 */ 509 unsigned short MinFreeLines; /* Bytes 74-75 */ 510 unsigned int :32; /* Bytes 76-79 */ 511 unsigned int :32; /* Bytes 80-83 */ 512 unsigned char RebuildRateConstant; /* Byte 84 */ 513 unsigned char :8; /* Byte 85 */ 514 unsigned char :8; /* Byte 86 */ 515 unsigned char :8; /* Byte 87 */ 516 unsigned int :32; /* Bytes 88-91 */ 517 unsigned int :32; /* Bytes 92-95 */ 518 unsigned short PhysicalDriveBlockSize; /* Bytes 96-97 */ 519 unsigned short LogicalDriveBlockSize; /* Bytes 98-99 */ 520 unsigned short MaxBlocksPerCommand; /* Bytes 100-101 */ 521 unsigned short BlockFactor; /* Bytes 102-103 */ 522 unsigned short CacheLineSize; /* Bytes 104-105 */ 523 struct { 524 enum { 525 DAC960_V1_Narrow_8bit = 0x0, 526 DAC960_V1_Wide_16bit = 0x1, 527 DAC960_V1_Wide_32bit = 0x2 528 } __attribute__ ((packed)) BusWidth:2; /* Byte 106 Bits 0-1 */ 529 enum { 530 DAC960_V1_Fast = 0x0, 531 DAC960_V1_Ultra = 0x1, 532 DAC960_V1_Ultra2 = 0x2 533 } __attribute__ ((packed)) BusSpeed:2; /* Byte 106 Bits 2-3 */ 534 bool Differential:1; /* Byte 106 Bit 4 */ 535 unsigned char :3; /* Byte 106 Bits 5-7 */ 536 } SCSICapability; 537 unsigned char :8; /* Byte 107 */ 538 unsigned int :32; /* Bytes 108-111 */ 539 unsigned short FirmwareBuildNumber; /* Bytes 112-113 */ 540 enum { 541 DAC960_V1_AEMI = 0x01, 542 DAC960_V1_OEM1 = 0x02, 543 DAC960_V1_OEM2 = 0x04, 544 DAC960_V1_OEM3 = 0x08, 545 DAC960_V1_Conner = 0x10, 546 DAC960_V1_SAFTE = 0x20 547 } __attribute__ ((packed)) FaultManagementType; /* Byte 114 */ 548 unsigned char :8; /* Byte 115 */ 549 struct { 550 bool Clustering:1; /* Byte 116 Bit 0 */ 551 bool MylexOnlineRAIDExpansion:1; /* Byte 116 Bit 1 */ 552 bool ReadAhead:1; /* Byte 116 Bit 2 */ 553 bool BackgroundInitialization:1; /* Byte 116 Bit 3 */ 554 unsigned int :28; /* Bytes 116-119 */ 555 } FirmwareFeatures; 556 unsigned int :32; /* Bytes 120-123 */ 557 unsigned int :32; /* Bytes 124-127 */ 558} 559DAC960_V1_Enquiry2_T; 560 561 562/* 563 Define the DAC960 V1 Firmware Logical Drive State type. 564*/ 565 566typedef enum 567{ 568 DAC960_V1_LogicalDrive_Online = 0x03, 569 DAC960_V1_LogicalDrive_Critical = 0x04, 570 DAC960_V1_LogicalDrive_Offline = 0xFF 571} 572__attribute__ ((packed)) 573DAC960_V1_LogicalDriveState_T; 574 575 576/* 577 Define the DAC960 V1 Firmware Logical Drive Information structure. 578*/ 579 580typedef struct DAC960_V1_LogicalDriveInformation 581{ 582 unsigned int LogicalDriveSize; /* Bytes 0-3 */ 583 DAC960_V1_LogicalDriveState_T LogicalDriveState; /* Byte 4 */ 584 unsigned char RAIDLevel:7; /* Byte 5 Bits 0-6 */ 585 bool WriteBack:1; /* Byte 5 Bit 7 */ 586 unsigned short :16; /* Bytes 6-7 */ 587} 588DAC960_V1_LogicalDriveInformation_T; 589 590 591/* 592 Define the DAC960 V1 Firmware Get Logical Drive Information Command 593 reply structure. 594*/ 595 596typedef DAC960_V1_LogicalDriveInformation_T 597 DAC960_V1_LogicalDriveInformationArray_T[DAC960_MaxLogicalDrives]; 598 599 600/* 601 Define the DAC960 V1 Firmware Perform Event Log Operation Types. 602*/ 603 604typedef enum 605{ 606 DAC960_V1_GetEventLogEntry = 0x00 607} 608__attribute__ ((packed)) 609DAC960_V1_PerformEventLogOpType_T; 610 611 612/* 613 Define the DAC960 V1 Firmware Get Event Log Entry Command reply structure. 614*/ 615 616typedef struct DAC960_V1_EventLogEntry 617{ 618 unsigned char MessageType; /* Byte 0 */ 619 unsigned char MessageLength; /* Byte 1 */ 620 unsigned char TargetID:5; /* Byte 2 Bits 0-4 */ 621 unsigned char Channel:3; /* Byte 2 Bits 5-7 */ 622 unsigned char LogicalUnit:6; /* Byte 3 Bits 0-5 */ 623 unsigned char :2; /* Byte 3 Bits 6-7 */ 624 unsigned short SequenceNumber; /* Bytes 4-5 */ 625 unsigned char ErrorCode:7; /* Byte 6 Bits 0-6 */ 626 bool Valid:1; /* Byte 6 Bit 7 */ 627 unsigned char SegmentNumber; /* Byte 7 */ 628 DAC960_SCSI_RequestSenseKey_T SenseKey:4; /* Byte 8 Bits 0-3 */ 629 unsigned char :1; /* Byte 8 Bit 4 */ 630 bool ILI:1; /* Byte 8 Bit 5 */ 631 bool EOM:1; /* Byte 8 Bit 6 */ 632 bool Filemark:1; /* Byte 8 Bit 7 */ 633 unsigned char Information[4]; /* Bytes 9-12 */ 634 unsigned char AdditionalSenseLength; /* Byte 13 */ 635 unsigned char CommandSpecificInformation[4]; /* Bytes 14-17 */ 636 unsigned char AdditionalSenseCode; /* Byte 18 */ 637 unsigned char AdditionalSenseCodeQualifier; /* Byte 19 */ 638 unsigned char Dummy[12]; /* Bytes 20-31 */ 639} 640DAC960_V1_EventLogEntry_T; 641 642 643/* 644 Define the DAC960 V1 Firmware Physical Device State type. 645*/ 646 647typedef enum 648{ 649 DAC960_V1_Device_Dead = 0x00, 650 DAC960_V1_Device_WriteOnly = 0x02, 651 DAC960_V1_Device_Online = 0x03, 652 DAC960_V1_Device_Standby = 0x10 653} 654__attribute__ ((packed)) 655DAC960_V1_PhysicalDeviceState_T; 656 657 658/* 659 Define the DAC960 V1 Firmware Get Device State Command reply structure. 660 The structure is padded by 2 bytes for compatibility with Version 2.xx 661 Firmware. 662*/ 663 664typedef struct DAC960_V1_DeviceState 665{ 666 bool Present:1; /* Byte 0 Bit 0 */ 667 unsigned char :7; /* Byte 0 Bits 1-7 */ 668 enum { 669 DAC960_V1_OtherType = 0x0, 670 DAC960_V1_DiskType = 0x1, 671 DAC960_V1_SequentialType = 0x2, 672 DAC960_V1_CDROM_or_WORM_Type = 0x3 673 } __attribute__ ((packed)) DeviceType:2; /* Byte 1 Bits 0-1 */ 674 bool :1; /* Byte 1 Bit 2 */ 675 bool Fast20:1; /* Byte 1 Bit 3 */ 676 bool Sync:1; /* Byte 1 Bit 4 */ 677 bool Fast:1; /* Byte 1 Bit 5 */ 678 bool Wide:1; /* Byte 1 Bit 6 */ 679 bool TaggedQueuingSupported:1; /* Byte 1 Bit 7 */ 680 DAC960_V1_PhysicalDeviceState_T DeviceState; /* Byte 2 */ 681 unsigned char :8; /* Byte 3 */ 682 unsigned char SynchronousMultiplier; /* Byte 4 */ 683 unsigned char SynchronousOffset:5; /* Byte 5 Bits 0-4 */ 684 unsigned char :3; /* Byte 5 Bits 5-7 */ 685 unsigned int DiskSize __attribute__ ((packed)); /* Bytes 6-9 */ 686 unsigned short :16; /* Bytes 10-11 */ 687} 688DAC960_V1_DeviceState_T; 689 690 691/* 692 Define the DAC960 V1 Firmware Get Rebuild Progress Command reply structure. 693*/ 694 695typedef struct DAC960_V1_RebuildProgress 696{ 697 unsigned int LogicalDriveNumber; /* Bytes 0-3 */ 698 unsigned int LogicalDriveSize; /* Bytes 4-7 */ 699 unsigned int RemainingBlocks; /* Bytes 8-11 */ 700} 701DAC960_V1_RebuildProgress_T; 702 703 704/* 705 Define the DAC960 V1 Firmware Background Initialization Status Command 706 reply structure. 707*/ 708 709typedef struct DAC960_V1_BackgroundInitializationStatus 710{ 711 unsigned int LogicalDriveSize; /* Bytes 0-3 */ 712 unsigned int BlocksCompleted; /* Bytes 4-7 */ 713 unsigned char Reserved1[12]; /* Bytes 8-19 */ 714 unsigned int LogicalDriveNumber; /* Bytes 20-23 */ 715 unsigned char RAIDLevel; /* Byte 24 */ 716 enum { 717 DAC960_V1_BackgroundInitializationInvalid = 0x00, 718 DAC960_V1_BackgroundInitializationStarted = 0x02, 719 DAC960_V1_BackgroundInitializationInProgress = 0x04, 720 DAC960_V1_BackgroundInitializationSuspended = 0x05, 721 DAC960_V1_BackgroundInitializationCancelled = 0x06 722 } __attribute__ ((packed)) Status; /* Byte 25 */ 723 unsigned char Reserved2[6]; /* Bytes 26-31 */ 724} 725DAC960_V1_BackgroundInitializationStatus_T; 726 727 728/* 729 Define the DAC960 V1 Firmware Error Table Entry structure. 730*/ 731 732typedef struct DAC960_V1_ErrorTableEntry 733{ 734 unsigned char ParityErrorCount; /* Byte 0 */ 735 unsigned char SoftErrorCount; /* Byte 1 */ 736 unsigned char HardErrorCount; /* Byte 2 */ 737 unsigned char MiscErrorCount; /* Byte 3 */ 738} 739DAC960_V1_ErrorTableEntry_T; 740 741 742/* 743 Define the DAC960 V1 Firmware Get Error Table Command reply structure. 744*/ 745 746typedef struct DAC960_V1_ErrorTable 747{ 748 DAC960_V1_ErrorTableEntry_T 749 ErrorTableEntries[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 750} 751DAC960_V1_ErrorTable_T; 752 753 754/* 755 Define the DAC960 V1 Firmware Read Config2 Command reply structure. 756*/ 757 758typedef struct DAC960_V1_Config2 759{ 760 unsigned char :1; /* Byte 0 Bit 0 */ 761 bool ActiveNegationEnabled:1; /* Byte 0 Bit 1 */ 762 unsigned char :5; /* Byte 0 Bits 2-6 */ 763 bool NoRescanIfResetReceivedDuringScan:1; /* Byte 0 Bit 7 */ 764 bool StorageWorksSupportEnabled:1; /* Byte 1 Bit 0 */ 765 bool HewlettPackardSupportEnabled:1; /* Byte 1 Bit 1 */ 766 bool NoDisconnectOnFirstCommand:1; /* Byte 1 Bit 2 */ 767 unsigned char :2; /* Byte 1 Bits 3-4 */ 768 bool AEMI_ARM:1; /* Byte 1 Bit 5 */ 769 bool AEMI_OFM:1; /* Byte 1 Bit 6 */ 770 unsigned char :1; /* Byte 1 Bit 7 */ 771 enum { 772 DAC960_V1_OEMID_Mylex = 0x00, 773 DAC960_V1_OEMID_IBM = 0x08, 774 DAC960_V1_OEMID_HP = 0x0A, 775 DAC960_V1_OEMID_DEC = 0x0C, 776 DAC960_V1_OEMID_Siemens = 0x10, 777 DAC960_V1_OEMID_Intel = 0x12 778 } __attribute__ ((packed)) OEMID; /* Byte 2 */ 779 unsigned char OEMModelNumber; /* Byte 3 */ 780 unsigned char PhysicalSector; /* Byte 4 */ 781 unsigned char LogicalSector; /* Byte 5 */ 782 unsigned char BlockFactor; /* Byte 6 */ 783 bool ReadAheadEnabled:1; /* Byte 7 Bit 0 */ 784 bool LowBIOSDelay:1; /* Byte 7 Bit 1 */ 785 unsigned char :2; /* Byte 7 Bits 2-3 */ 786 bool ReassignRestrictedToOneSector:1; /* Byte 7 Bit 4 */ 787 unsigned char :1; /* Byte 7 Bit 5 */ 788 bool ForceUnitAccessDuringWriteRecovery:1; /* Byte 7 Bit 6 */ 789 bool EnableLeftSymmetricRAID5Algorithm:1; /* Byte 7 Bit 7 */ 790 unsigned char DefaultRebuildRate; /* Byte 8 */ 791 unsigned char :8; /* Byte 9 */ 792 unsigned char BlocksPerCacheLine; /* Byte 10 */ 793 unsigned char BlocksPerStripe; /* Byte 11 */ 794 struct { 795 enum { 796 DAC960_V1_Async = 0x0, 797 DAC960_V1_Sync_8MHz = 0x1, 798 DAC960_V1_Sync_5MHz = 0x2, 799 DAC960_V1_Sync_10or20MHz = 0x3 /* Byte 11 Bits 0-1 */ 800 } __attribute__ ((packed)) Speed:2; 801 bool Force8Bit:1; /* Byte 11 Bit 2 */ 802 bool DisableFast20:1; /* Byte 11 Bit 3 */ 803 unsigned char :3; /* Byte 11 Bits 4-6 */ 804 bool EnableTaggedQueuing:1; /* Byte 11 Bit 7 */ 805 } __attribute__ ((packed)) ChannelParameters[6]; /* Bytes 12-17 */ 806 unsigned char SCSIInitiatorID; /* Byte 18 */ 807 unsigned char :8; /* Byte 19 */ 808 enum { 809 DAC960_V1_StartupMode_ControllerSpinUp = 0x00, 810 DAC960_V1_StartupMode_PowerOnSpinUp = 0x01 811 } __attribute__ ((packed)) StartupMode; /* Byte 20 */ 812 unsigned char SimultaneousDeviceSpinUpCount; /* Byte 21 */ 813 unsigned char SecondsDelayBetweenSpinUps; /* Byte 22 */ 814 unsigned char Reserved1[29]; /* Bytes 23-51 */ 815 bool BIOSDisabled:1; /* Byte 52 Bit 0 */ 816 bool CDROMBootEnabled:1; /* Byte 52 Bit 1 */ 817 unsigned char :3; /* Byte 52 Bits 2-4 */ 818 enum { 819 DAC960_V1_Geometry_128_32 = 0x0, 820 DAC960_V1_Geometry_255_63 = 0x1, 821 DAC960_V1_Geometry_Reserved1 = 0x2, 822 DAC960_V1_Geometry_Reserved2 = 0x3 823 } __attribute__ ((packed)) DriveGeometry:2; /* Byte 52 Bits 5-6 */ 824 unsigned char :1; /* Byte 52 Bit 7 */ 825 unsigned char Reserved2[9]; /* Bytes 53-61 */ 826 unsigned short Checksum; /* Bytes 62-63 */ 827} 828DAC960_V1_Config2_T; 829 830 831/* 832 Define the DAC960 V1 Firmware DCDB request structure. 833*/ 834 835typedef struct DAC960_V1_DCDB 836{ 837 unsigned char TargetID:4; /* Byte 0 Bits 0-3 */ 838 unsigned char Channel:4; /* Byte 0 Bits 4-7 */ 839 enum { 840 DAC960_V1_DCDB_NoDataTransfer = 0, 841 DAC960_V1_DCDB_DataTransferDeviceToSystem = 1, 842 DAC960_V1_DCDB_DataTransferSystemToDevice = 2, 843 DAC960_V1_DCDB_IllegalDataTransfer = 3 844 } __attribute__ ((packed)) Direction:2; /* Byte 1 Bits 0-1 */ 845 bool EarlyStatus:1; /* Byte 1 Bit 2 */ 846 unsigned char :1; /* Byte 1 Bit 3 */ 847 enum { 848 DAC960_V1_DCDB_Timeout_24_hours = 0, 849 DAC960_V1_DCDB_Timeout_10_seconds = 1, 850 DAC960_V1_DCDB_Timeout_60_seconds = 2, 851 DAC960_V1_DCDB_Timeout_10_minutes = 3 852 } __attribute__ ((packed)) Timeout:2; /* Byte 1 Bits 4-5 */ 853 bool NoAutomaticRequestSense:1; /* Byte 1 Bit 6 */ 854 bool DisconnectPermitted:1; /* Byte 1 Bit 7 */ 855 unsigned short TransferLength; /* Bytes 2-3 */ 856 DAC960_BusAddress32_T BusAddress; /* Bytes 4-7 */ 857 unsigned char CDBLength:4; /* Byte 8 Bits 0-3 */ 858 unsigned char TransferLengthHigh4:4; /* Byte 8 Bits 4-7 */ 859 unsigned char SenseLength; /* Byte 9 */ 860 unsigned char CDB[12]; /* Bytes 10-21 */ 861 unsigned char SenseData[64]; /* Bytes 22-85 */ 862 unsigned char Status; /* Byte 86 */ 863 unsigned char :8; /* Byte 87 */ 864} 865DAC960_V1_DCDB_T; 866 867 868/* 869 Define the DAC960 V1 Firmware Scatter/Gather List Type 1 32 Bit Address 870 32 Bit Byte Count structure. 871*/ 872 873typedef struct DAC960_V1_ScatterGatherSegment 874{ 875 DAC960_BusAddress32_T SegmentDataPointer; /* Bytes 0-3 */ 876 DAC960_ByteCount32_T SegmentByteCount; /* Bytes 4-7 */ 877} 878DAC960_V1_ScatterGatherSegment_T; 879 880 881/* 882 Define the 13 Byte DAC960 V1 Firmware Command Mailbox structure. Bytes 13-15 883 are not used. The Command Mailbox structure is padded to 16 bytes for 884 efficient access. 885*/ 886 887typedef union DAC960_V1_CommandMailbox 888{ 889 unsigned int Words[4]; /* Words 0-3 */ 890 unsigned char Bytes[16]; /* Bytes 0-15 */ 891 struct { 892 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 893 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 894 unsigned char Dummy[14]; /* Bytes 2-15 */ 895 } __attribute__ ((packed)) Common; 896 struct { 897 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 898 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 899 unsigned char Dummy1[6]; /* Bytes 2-7 */ 900 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 901 unsigned char Dummy2[4]; /* Bytes 12-15 */ 902 } __attribute__ ((packed)) Type3; 903 struct { 904 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 905 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 906 unsigned char CommandOpcode2; /* Byte 2 */ 907 unsigned char Dummy1[5]; /* Bytes 3-7 */ 908 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 909 unsigned char Dummy2[4]; /* Bytes 12-15 */ 910 } __attribute__ ((packed)) Type3B; 911 struct { 912 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 913 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 914 unsigned char Dummy1[5]; /* Bytes 2-6 */ 915 unsigned char LogicalDriveNumber:6; /* Byte 7 Bits 0-6 */ 916 bool AutoRestore:1; /* Byte 7 Bit 7 */ 917 unsigned char Dummy2[8]; /* Bytes 8-15 */ 918 } __attribute__ ((packed)) Type3C; 919 struct { 920 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 921 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 922 unsigned char Channel; /* Byte 2 */ 923 unsigned char TargetID; /* Byte 3 */ 924 DAC960_V1_PhysicalDeviceState_T DeviceState:5; /* Byte 4 Bits 0-4 */ 925 unsigned char Modifier:3; /* Byte 4 Bits 5-7 */ 926 unsigned char Dummy1[3]; /* Bytes 5-7 */ 927 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 928 unsigned char Dummy2[4]; /* Bytes 12-15 */ 929 } __attribute__ ((packed)) Type3D; 930 struct { 931 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 932 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 933 DAC960_V1_PerformEventLogOpType_T OperationType; /* Byte 2 */ 934 unsigned char OperationQualifier; /* Byte 3 */ 935 unsigned short SequenceNumber; /* Bytes 4-5 */ 936 unsigned char Dummy1[2]; /* Bytes 6-7 */ 937 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 938 unsigned char Dummy2[4]; /* Bytes 12-15 */ 939 } __attribute__ ((packed)) Type3E; 940 struct { 941 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 942 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 943 unsigned char Dummy1[2]; /* Bytes 2-3 */ 944 unsigned char RebuildRateConstant; /* Byte 4 */ 945 unsigned char Dummy2[3]; /* Bytes 5-7 */ 946 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 947 unsigned char Dummy3[4]; /* Bytes 12-15 */ 948 } __attribute__ ((packed)) Type3R; 949 struct { 950 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 951 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 952 unsigned short TransferLength; /* Bytes 2-3 */ 953 unsigned int LogicalBlockAddress; /* Bytes 4-7 */ 954 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 955 unsigned char LogicalDriveNumber; /* Byte 12 */ 956 unsigned char Dummy[3]; /* Bytes 13-15 */ 957 } __attribute__ ((packed)) Type4; 958 struct { 959 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 960 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 961 struct { 962 unsigned short TransferLength:11; /* Bytes 2-3 */ 963 unsigned char LogicalDriveNumber:5; /* Byte 3 Bits 3-7 */ 964 } __attribute__ ((packed)) LD; 965 unsigned int LogicalBlockAddress; /* Bytes 4-7 */ 966 DAC960_BusAddress32_T BusAddress; /* Bytes 8-11 */ 967 unsigned char ScatterGatherCount:6; /* Byte 12 Bits 0-5 */ 968 enum { 969 DAC960_V1_ScatterGather_32BitAddress_32BitByteCount = 0x0, 970 DAC960_V1_ScatterGather_32BitAddress_16BitByteCount = 0x1, 971 DAC960_V1_ScatterGather_32BitByteCount_32BitAddress = 0x2, 972 DAC960_V1_ScatterGather_16BitByteCount_32BitAddress = 0x3 973 } __attribute__ ((packed)) ScatterGatherType:2; /* Byte 12 Bits 6-7 */ 974 unsigned char Dummy[3]; /* Bytes 13-15 */ 975 } __attribute__ ((packed)) Type5; 976 struct { 977 DAC960_V1_CommandOpcode_T CommandOpcode; /* Byte 0 */ 978 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 1 */ 979 unsigned char CommandOpcode2; /* Byte 2 */ 980 unsigned char :8; /* Byte 3 */ 981 DAC960_BusAddress32_T CommandMailboxesBusAddress; /* Bytes 4-7 */ 982 DAC960_BusAddress32_T StatusMailboxesBusAddress; /* Bytes 8-11 */ 983 unsigned char Dummy[4]; /* Bytes 12-15 */ 984 } __attribute__ ((packed)) TypeX; 985} 986DAC960_V1_CommandMailbox_T; 987 988 989/* 990 Define the DAC960 V2 Firmware Command Opcodes. 991*/ 992 993typedef enum 994{ 995 DAC960_V2_MemCopy = 0x01, 996 DAC960_V2_SCSI_10_Passthru = 0x02, 997 DAC960_V2_SCSI_255_Passthru = 0x03, 998 DAC960_V2_SCSI_10 = 0x04, 999 DAC960_V2_SCSI_256 = 0x05, 1000 DAC960_V2_IOCTL = 0x20 1001} 1002__attribute__ ((packed)) 1003DAC960_V2_CommandOpcode_T; 1004 1005 1006/* 1007 Define the DAC960 V2 Firmware IOCTL Opcodes. 1008*/ 1009 1010typedef enum 1011{ 1012 DAC960_V2_GetControllerInfo = 0x01, 1013 DAC960_V2_GetLogicalDeviceInfoValid = 0x03, 1014 DAC960_V2_GetPhysicalDeviceInfoValid = 0x05, 1015 DAC960_V2_GetHealthStatus = 0x11, 1016 DAC960_V2_GetEvent = 0x15, 1017 DAC960_V2_StartDiscovery = 0x81, 1018 DAC960_V2_SetDeviceState = 0x82, 1019 DAC960_V2_RebuildDeviceStart = 0x88, 1020 DAC960_V2_RebuildDeviceStop = 0x89, 1021 DAC960_V2_ConsistencyCheckStart = 0x8C, 1022 DAC960_V2_ConsistencyCheckStop = 0x8D, 1023 DAC960_V2_SetMemoryMailbox = 0x8E, 1024 DAC960_V2_PauseDevice = 0x92, 1025 DAC960_V2_TranslatePhysicalToLogicalDevice = 0xC5 1026} 1027__attribute__ ((packed)) 1028DAC960_V2_IOCTL_Opcode_T; 1029 1030 1031/* 1032 Define the DAC960 V2 Firmware Command Identifier type. 1033*/ 1034 1035typedef unsigned short DAC960_V2_CommandIdentifier_T; 1036 1037 1038/* 1039 Define the DAC960 V2 Firmware Command Status Codes. 1040*/ 1041 1042#define DAC960_V2_NormalCompletion 0x00 1043#define DAC960_V2_AbormalCompletion 0x02 1044#define DAC960_V2_DeviceBusy 0x08 1045#define DAC960_V2_DeviceNonresponsive 0x0E 1046#define DAC960_V2_DeviceNonresponsive2 0x0F 1047#define DAC960_V2_DeviceRevervationConflict 0x18 1048 1049typedef unsigned char DAC960_V2_CommandStatus_T; 1050 1051 1052/* 1053 Define the DAC960 V2 Firmware Memory Type structure. 1054*/ 1055 1056typedef struct DAC960_V2_MemoryType 1057{ 1058 enum { 1059 DAC960_V2_MemoryType_Reserved = 0x00, 1060 DAC960_V2_MemoryType_DRAM = 0x01, 1061 DAC960_V2_MemoryType_EDRAM = 0x02, 1062 DAC960_V2_MemoryType_EDO = 0x03, 1063 DAC960_V2_MemoryType_SDRAM = 0x04, 1064 DAC960_V2_MemoryType_Last = 0x1F 1065 } __attribute__ ((packed)) MemoryType:5; /* Byte 0 Bits 0-4 */ 1066 bool :1; /* Byte 0 Bit 5 */ 1067 bool MemoryParity:1; /* Byte 0 Bit 6 */ 1068 bool MemoryECC:1; /* Byte 0 Bit 7 */ 1069} 1070DAC960_V2_MemoryType_T; 1071 1072 1073/* 1074 Define the DAC960 V2 Firmware Processor Type structure. 1075*/ 1076 1077typedef enum 1078{ 1079 DAC960_V2_ProcessorType_i960CA = 0x01, 1080 DAC960_V2_ProcessorType_i960RD = 0x02, 1081 DAC960_V2_ProcessorType_i960RN = 0x03, 1082 DAC960_V2_ProcessorType_i960RP = 0x04, 1083 DAC960_V2_ProcessorType_NorthBay = 0x05, 1084 DAC960_V2_ProcessorType_StrongArm = 0x06, 1085 DAC960_V2_ProcessorType_i960RM = 0x07 1086} 1087__attribute__ ((packed)) 1088DAC960_V2_ProcessorType_T; 1089 1090 1091/* 1092 Define the DAC960 V2 Firmware Get Controller Info reply structure. 1093*/ 1094 1095typedef struct DAC960_V2_ControllerInfo 1096{ 1097 unsigned char :8; /* Byte 0 */ 1098 enum { 1099 DAC960_V2_SCSI_Bus = 0x00, 1100 DAC960_V2_Fibre_Bus = 0x01, 1101 DAC960_V2_PCI_Bus = 0x03 1102 } __attribute__ ((packed)) BusInterfaceType; /* Byte 1 */ 1103 enum { 1104 DAC960_V2_DAC960E = 0x01, 1105 DAC960_V2_DAC960M = 0x08, 1106 DAC960_V2_DAC960PD = 0x10, 1107 DAC960_V2_DAC960PL = 0x11, 1108 DAC960_V2_DAC960PU = 0x12, 1109 DAC960_V2_DAC960PE = 0x13, 1110 DAC960_V2_DAC960PG = 0x14, 1111 DAC960_V2_DAC960PJ = 0x15, 1112 DAC960_V2_DAC960PTL0 = 0x16, 1113 DAC960_V2_DAC960PR = 0x17, 1114 DAC960_V2_DAC960PRL = 0x18, 1115 DAC960_V2_DAC960PT = 0x19, 1116 DAC960_V2_DAC1164P = 0x1A, 1117 DAC960_V2_DAC960PTL1 = 0x1B, 1118 DAC960_V2_EXR2000P = 0x1C, 1119 DAC960_V2_EXR3000P = 0x1D, 1120 DAC960_V2_AcceleRAID352 = 0x1E, 1121 DAC960_V2_AcceleRAID170 = 0x1F, 1122 DAC960_V2_AcceleRAID160 = 0x20, 1123 DAC960_V2_DAC960S = 0x60, 1124 DAC960_V2_DAC960SU = 0x61, 1125 DAC960_V2_DAC960SX = 0x62, 1126 DAC960_V2_DAC960SF = 0x63, 1127 DAC960_V2_DAC960SS = 0x64, 1128 DAC960_V2_DAC960FL = 0x65, 1129 DAC960_V2_DAC960LL = 0x66, 1130 DAC960_V2_DAC960FF = 0x67, 1131 DAC960_V2_DAC960HP = 0x68, 1132 DAC960_V2_RAIDBRICK = 0x69, 1133 DAC960_V2_METEOR_FL = 0x6A, 1134 DAC960_V2_METEOR_FF = 0x6B 1135 } __attribute__ ((packed)) ControllerType; /* Byte 2 */ 1136 unsigned char :8; /* Byte 3 */ 1137 unsigned short BusInterfaceSpeedMHz; /* Bytes 4-5 */ 1138 unsigned char BusWidthBits; /* Byte 6 */ 1139 unsigned char FlashCodeTypeOrProductID; /* Byte 7 */ 1140 unsigned char NumberOfHostPortsPresent; /* Byte 8 */ 1141 unsigned char Reserved1[7]; /* Bytes 9-15 */ 1142 unsigned char BusInterfaceName[16]; /* Bytes 16-31 */ 1143 unsigned char ControllerName[16]; /* Bytes 32-47 */ 1144 unsigned char Reserved2[16]; /* Bytes 48-63 */ 1145 /* Firmware Release Information */ 1146 unsigned char FirmwareMajorVersion; /* Byte 64 */ 1147 unsigned char FirmwareMinorVersion; /* Byte 65 */ 1148 unsigned char FirmwareTurnNumber; /* Byte 66 */ 1149 unsigned char FirmwareBuildNumber; /* Byte 67 */ 1150 unsigned char FirmwareReleaseDay; /* Byte 68 */ 1151 unsigned char FirmwareReleaseMonth; /* Byte 69 */ 1152 unsigned char FirmwareReleaseYearHigh2Digits; /* Byte 70 */ 1153 unsigned char FirmwareReleaseYearLow2Digits; /* Byte 71 */ 1154 /* Hardware Release Information */ 1155 unsigned char HardwareRevision; /* Byte 72 */ 1156 unsigned int :24; /* Bytes 73-75 */ 1157 unsigned char HardwareReleaseDay; /* Byte 76 */ 1158 unsigned char HardwareReleaseMonth; /* Byte 77 */ 1159 unsigned char HardwareReleaseYearHigh2Digits; /* Byte 78 */ 1160 unsigned char HardwareReleaseYearLow2Digits; /* Byte 79 */ 1161 /* Hardware Manufacturing Information */ 1162 unsigned char ManufacturingBatchNumber; /* Byte 80 */ 1163 unsigned char :8; /* Byte 81 */ 1164 unsigned char ManufacturingPlantNumber; /* Byte 82 */ 1165 unsigned char :8; /* Byte 83 */ 1166 unsigned char HardwareManufacturingDay; /* Byte 84 */ 1167 unsigned char HardwareManufacturingMonth; /* Byte 85 */ 1168 unsigned char HardwareManufacturingYearHigh2Digits; /* Byte 86 */ 1169 unsigned char HardwareManufacturingYearLow2Digits; /* Byte 87 */ 1170 unsigned char MaximumNumberOfPDDperXLD; /* Byte 88 */ 1171 unsigned char MaximumNumberOfILDperXLD; /* Byte 89 */ 1172 unsigned short NonvolatileMemorySizeKB; /* Bytes 90-91 */ 1173 unsigned char MaximumNumberOfXLD; /* Byte 92 */ 1174 unsigned int :24; /* Bytes 93-95 */ 1175 /* Unique Information per Controller */ 1176 unsigned char ControllerSerialNumber[16]; /* Bytes 96-111 */ 1177 unsigned char Reserved3[16]; /* Bytes 112-127 */ 1178 /* Vendor Information */ 1179 unsigned int :24; /* Bytes 128-130 */ 1180 unsigned char OEM_Code; /* Byte 131 */ 1181 unsigned char VendorName[16]; /* Bytes 132-147 */ 1182 /* Other Physical/Controller/Operation Information */ 1183 bool BBU_Present:1; /* Byte 148 Bit 0 */ 1184 bool ActiveActiveClusteringMode:1; /* Byte 148 Bit 1 */ 1185 unsigned char :6; /* Byte 148 Bits 2-7 */ 1186 unsigned char :8; /* Byte 149 */ 1187 unsigned short :16; /* Bytes 150-151 */ 1188 /* Physical Device Scan Information */ 1189 bool PhysicalScanActive:1; /* Byte 152 Bit 0 */ 1190 unsigned char :7; /* Byte 152 Bits 1-7 */ 1191 unsigned char PhysicalDeviceChannelNumber; /* Byte 153 */ 1192 unsigned char PhysicalDeviceTargetID; /* Byte 154 */ 1193 unsigned char PhysicalDeviceLogicalUnit; /* Byte 155 */ 1194 /* Maximum Command Data Transfer Sizes */ 1195 unsigned short MaximumDataTransferSizeInBlocks; /* Bytes 156-157 */ 1196 unsigned short MaximumScatterGatherEntries; /* Bytes 158-159 */ 1197 /* Logical/Physical Device Counts */ 1198 unsigned short LogicalDevicesPresent; /* Bytes 160-161 */ 1199 unsigned short LogicalDevicesCritical; /* Bytes 162-163 */ 1200 unsigned short LogicalDevicesOffline; /* Bytes 164-165 */ 1201 unsigned short PhysicalDevicesPresent; /* Bytes 166-167 */ 1202 unsigned short PhysicalDisksPresent; /* Bytes 168-169 */ 1203 unsigned short PhysicalDisksCritical; /* Bytes 170-171 */ 1204 unsigned short PhysicalDisksOffline; /* Bytes 172-173 */ 1205 unsigned short MaximumParallelCommands; /* Bytes 174-175 */ 1206 /* Channel and Target ID Information */ 1207 unsigned char NumberOfPhysicalChannelsPresent; /* Byte 176 */ 1208 unsigned char NumberOfVirtualChannelsPresent; /* Byte 177 */ 1209 unsigned char NumberOfPhysicalChannelsPossible; /* Byte 178 */ 1210 unsigned char NumberOfVirtualChannelsPossible; /* Byte 179 */ 1211 unsigned char MaximumTargetsPerChannel[16]; /* Bytes 180-195 */ 1212 unsigned char Reserved4[12]; /* Bytes 196-207 */ 1213 /* Memory/Cache Information */ 1214 unsigned short MemorySizeMB; /* Bytes 208-209 */ 1215 unsigned short CacheSizeMB; /* Bytes 210-211 */ 1216 unsigned int ValidCacheSizeInBytes; /* Bytes 212-215 */ 1217 unsigned int DirtyCacheSizeInBytes; /* Bytes 216-219 */ 1218 unsigned short MemorySpeedMHz; /* Bytes 220-221 */ 1219 unsigned char MemoryDataWidthBits; /* Byte 222 */ 1220 DAC960_V2_MemoryType_T MemoryType; /* Byte 223 */ 1221 unsigned char CacheMemoryTypeName[16]; /* Bytes 224-239 */ 1222 /* Execution Memory Information */ 1223 unsigned short ExecutionMemorySizeMB; /* Bytes 240-241 */ 1224 unsigned short ExecutionL2CacheSizeMB; /* Bytes 242-243 */ 1225 unsigned char Reserved5[8]; /* Bytes 244-251 */ 1226 unsigned short ExecutionMemorySpeedMHz; /* Bytes 252-253 */ 1227 unsigned char ExecutionMemoryDataWidthBits; /* Byte 254 */ 1228 DAC960_V2_MemoryType_T ExecutionMemoryType; /* Byte 255 */ 1229 unsigned char ExecutionMemoryTypeName[16]; /* Bytes 256-271 */ 1230 /* First CPU Type Information */ 1231 unsigned short FirstProcessorSpeedMHz; /* Bytes 272-273 */ 1232 DAC960_V2_ProcessorType_T FirstProcessorType; /* Byte 274 */ 1233 unsigned char FirstProcessorCount; /* Byte 275 */ 1234 unsigned char Reserved6[12]; /* Bytes 276-287 */ 1235 unsigned char FirstProcessorName[16]; /* Bytes 288-303 */ 1236 /* Second CPU Type Information */ 1237 unsigned short SecondProcessorSpeedMHz; /* Bytes 304-305 */ 1238 DAC960_V2_ProcessorType_T SecondProcessorType; /* Byte 306 */ 1239 unsigned char SecondProcessorCount; /* Byte 307 */ 1240 unsigned char Reserved7[12]; /* Bytes 308-319 */ 1241 unsigned char SecondProcessorName[16]; /* Bytes 320-335 */ 1242 /* Debugging/Profiling/Command Time Tracing Information */ 1243 unsigned short CurrentProfilingDataPageNumber; /* Bytes 336-337 */ 1244 unsigned short ProgramsAwaitingProfilingData; /* Bytes 338-339 */ 1245 unsigned short CurrentCommandTimeTraceDataPageNumber; /* Bytes 340-341 */ 1246 unsigned short ProgramsAwaitingCommandTimeTraceData; /* Bytes 342-343 */ 1247 unsigned char Reserved8[8]; /* Bytes 344-351 */ 1248 /* Error Counters on Physical Devices */ 1249 unsigned short PhysicalDeviceBusResets; /* Bytes 352-353 */ 1250 unsigned short PhysicalDeviceParityErrors; /* Bytes 355-355 */ 1251 unsigned short PhysicalDeviceSoftErrors; /* Bytes 356-357 */ 1252 unsigned short PhysicalDeviceCommandsFailed; /* Bytes 358-359 */ 1253 unsigned short PhysicalDeviceMiscellaneousErrors; /* Bytes 360-361 */ 1254 unsigned short PhysicalDeviceCommandTimeouts; /* Bytes 362-363 */ 1255 unsigned short PhysicalDeviceSelectionTimeouts; /* Bytes 364-365 */ 1256 unsigned short PhysicalDeviceRetriesDone; /* Bytes 366-367 */ 1257 unsigned short PhysicalDeviceAbortsDone; /* Bytes 368-369 */ 1258 unsigned short PhysicalDeviceHostCommandAbortsDone; /* Bytes 370-371 */ 1259 unsigned short PhysicalDevicePredictedFailuresDetected; /* Bytes 372-373 */ 1260 unsigned short PhysicalDeviceHostCommandsFailed; /* Bytes 374-375 */ 1261 unsigned short PhysicalDeviceHardErrors; /* Bytes 376-377 */ 1262 unsigned char Reserved9[6]; /* Bytes 378-383 */ 1263 /* Error Counters on Logical Devices */ 1264 unsigned short LogicalDeviceSoftErrors; /* Bytes 384-385 */ 1265 unsigned short LogicalDeviceCommandsFailed; /* Bytes 386-387 */ 1266 unsigned short LogicalDeviceHostCommandAbortsDone; /* Bytes 388-389 */ 1267 unsigned short :16; /* Bytes 390-391 */ 1268 /* Error Counters on Controller */ 1269 unsigned short ControllerMemoryErrors; /* Bytes 392-393 */ 1270 unsigned short ControllerHostCommandAbortsDone; /* Bytes 394-395 */ 1271 unsigned int :32; /* Bytes 396-399 */ 1272 /* Long Duration Activity Information */ 1273 unsigned short BackgroundInitializationsActive; /* Bytes 400-401 */ 1274 unsigned short LogicalDeviceInitializationsActive; /* Bytes 402-403 */ 1275 unsigned short PhysicalDeviceInitializationsActive; /* Bytes 404-405 */ 1276 unsigned short ConsistencyChecksActive; /* Bytes 406-407 */ 1277 unsigned short RebuildsActive; /* Bytes 408-409 */ 1278 unsigned short OnlineExpansionsActive; /* Bytes 410-411 */ 1279 unsigned short PatrolActivitiesActive; /* Bytes 412-413 */ 1280 unsigned short :16; /* Bytes 414-415 */ 1281 /* Flash ROM Information */ 1282 unsigned char FlashType; /* Byte 416 */ 1283 unsigned char :8; /* Byte 417 */ 1284 unsigned short FlashSizeMB; /* Bytes 418-419 */ 1285 unsigned int FlashLimit; /* Bytes 420-423 */ 1286 unsigned int FlashCount; /* Bytes 424-427 */ 1287 unsigned int :32; /* Bytes 428-431 */ 1288 unsigned char FlashTypeName[16]; /* Bytes 432-447 */ 1289 /* Firmware Run Time Information */ 1290 unsigned char RebuildRate; /* Byte 448 */ 1291 unsigned char BackgroundInitializationRate; /* Byte 449 */ 1292 unsigned char ForegroundInitializationRate; /* Byte 450 */ 1293 unsigned char ConsistencyCheckRate; /* Byte 451 */ 1294 unsigned int :32; /* Bytes 452-455 */ 1295 unsigned int MaximumDP; /* Bytes 456-459 */ 1296 unsigned int FreeDP; /* Bytes 460-463 */ 1297 unsigned int MaximumIOP; /* Bytes 464-467 */ 1298 unsigned int FreeIOP; /* Bytes 468-471 */ 1299 unsigned short MaximumCombLengthInBlocks; /* Bytes 472-473 */ 1300 unsigned short NumberOfConfigurationGroups; /* Bytes 474-475 */ 1301 bool InstallationAbortStatus:1; /* Byte 476 Bit 0 */ 1302 bool MaintenanceModeStatus:1; /* Byte 476 Bit 1 */ 1303 unsigned int :24; /* Bytes 476-479 */ 1304 unsigned char Reserved10[32]; /* Bytes 480-511 */ 1305 unsigned char Reserved11[512]; /* Bytes 512-1023 */ 1306} 1307DAC960_V2_ControllerInfo_T; 1308 1309 1310/* 1311 Define the DAC960 V2 Firmware Logical Device State type. 1312*/ 1313 1314typedef enum 1315{ 1316 DAC960_V2_LogicalDevice_Online = 0x01, 1317 DAC960_V2_LogicalDevice_Offline = 0x08, 1318 DAC960_V2_LogicalDevice_Critical = 0x09 1319} 1320__attribute__ ((packed)) 1321DAC960_V2_LogicalDeviceState_T; 1322 1323 1324/* 1325 Define the DAC960 V2 Firmware Get Logical Device Info reply structure. 1326*/ 1327 1328typedef struct DAC960_V2_LogicalDeviceInfo 1329{ 1330 unsigned char :8; /* Byte 0 */ 1331 unsigned char Channel; /* Byte 1 */ 1332 unsigned char TargetID; /* Byte 2 */ 1333 unsigned char LogicalUnit; /* Byte 3 */ 1334 DAC960_V2_LogicalDeviceState_T LogicalDeviceState; /* Byte 4 */ 1335 unsigned char RAIDLevel; /* Byte 5 */ 1336 unsigned char StripeSize; /* Byte 6 */ 1337 unsigned char CacheLineSize; /* Byte 7 */ 1338 struct { 1339 enum { 1340 DAC960_V2_ReadCacheDisabled = 0x0, 1341 DAC960_V2_ReadCacheEnabled = 0x1, 1342 DAC960_V2_ReadAheadEnabled = 0x2, 1343 DAC960_V2_IntelligentReadAheadEnabled = 0x3, 1344 DAC960_V2_ReadCache_Last = 0x7 1345 } __attribute__ ((packed)) ReadCache:3; /* Byte 8 Bits 0-2 */ 1346 enum { 1347 DAC960_V2_WriteCacheDisabled = 0x0, 1348 DAC960_V2_LogicalDeviceReadOnly = 0x1, 1349 DAC960_V2_WriteCacheEnabled = 0x2, 1350 DAC960_V2_IntelligentWriteCacheEnabled = 0x3, 1351 DAC960_V2_WriteCache_Last = 0x7 1352 } __attribute__ ((packed)) WriteCache:3; /* Byte 8 Bits 3-5 */ 1353 bool :1; /* Byte 8 Bit 6 */ 1354 bool LogicalDeviceInitialized:1; /* Byte 8 Bit 7 */ 1355 } LogicalDeviceControl; /* Byte 8 */ 1356 /* Logical Device Operations Status */ 1357 bool ConsistencyCheckInProgress:1; /* Byte 9 Bit 0 */ 1358 bool RebuildInProgress:1; /* Byte 9 Bit 1 */ 1359 bool BackgroundInitializationInProgress:1; /* Byte 9 Bit 2 */ 1360 bool ForegroundInitializationInProgress:1; /* Byte 9 Bit 3 */ 1361 bool DataMigrationInProgress:1; /* Byte 9 Bit 4 */ 1362 bool PatrolOperationInProgress:1; /* Byte 9 Bit 5 */ 1363 unsigned char :2; /* Byte 9 Bits 6-7 */ 1364 unsigned char RAID5WriteUpdate; /* Byte 10 */ 1365 unsigned char RAID5Algorithm; /* Byte 11 */ 1366 unsigned short LogicalDeviceNumber; /* Bytes 12-13 */ 1367 /* BIOS Info */ 1368 bool BIOSDisabled:1; /* Byte 14 Bit 0 */ 1369 bool CDROMBootEnabled:1; /* Byte 14 Bit 1 */ 1370 bool DriveCoercionEnabled:1; /* Byte 14 Bit 2 */ 1371 bool WriteSameDisabled:1; /* Byte 14 Bit 3 */ 1372 bool HBA_ModeEnabled:1; /* Byte 14 Bit 4 */ 1373 enum { 1374 DAC960_V2_Geometry_128_32 = 0x0, 1375 DAC960_V2_Geometry_255_63 = 0x1, 1376 DAC960_V2_Geometry_Reserved1 = 0x2, 1377 DAC960_V2_Geometry_Reserved2 = 0x3 1378 } __attribute__ ((packed)) DriveGeometry:2; /* Byte 14 Bits 5-6 */ 1379 bool SuperReadAheadEnabled:1; /* Byte 14 Bit 7 */ 1380 unsigned char :8; /* Byte 15 */ 1381 /* Error Counters */ 1382 unsigned short SoftErrors; /* Bytes 16-17 */ 1383 unsigned short CommandsFailed; /* Bytes 18-19 */ 1384 unsigned short HostCommandAbortsDone; /* Bytes 20-21 */ 1385 unsigned short DeferredWriteErrors; /* Bytes 22-23 */ 1386 unsigned int :32; /* Bytes 24-27 */ 1387 unsigned int :32; /* Bytes 28-31 */ 1388 /* Device Size Information */ 1389 unsigned short :16; /* Bytes 32-33 */ 1390 unsigned short DeviceBlockSizeInBytes; /* Bytes 34-35 */ 1391 unsigned int OriginalDeviceSize; /* Bytes 36-39 */ 1392 unsigned int ConfigurableDeviceSize; /* Bytes 40-43 */ 1393 unsigned int :32; /* Bytes 44-47 */ 1394 unsigned char LogicalDeviceName[32]; /* Bytes 48-79 */ 1395 unsigned char SCSI_InquiryData[36]; /* Bytes 80-115 */ 1396 unsigned char Reserved1[12]; /* Bytes 116-127 */ 1397 DAC960_ByteCount64_T LastReadBlockNumber; /* Bytes 128-135 */ 1398 DAC960_ByteCount64_T LastWrittenBlockNumber; /* Bytes 136-143 */ 1399 DAC960_ByteCount64_T ConsistencyCheckBlockNumber; /* Bytes 144-151 */ 1400 DAC960_ByteCount64_T RebuildBlockNumber; /* Bytes 152-159 */ 1401 DAC960_ByteCount64_T BackgroundInitializationBlockNumber; /* Bytes 160-167 */ 1402 DAC960_ByteCount64_T ForegroundInitializationBlockNumber; /* Bytes 168-175 */ 1403 DAC960_ByteCount64_T DataMigrationBlockNumber; /* Bytes 176-183 */ 1404 DAC960_ByteCount64_T PatrolOperationBlockNumber; /* Bytes 184-191 */ 1405 unsigned char Reserved2[64]; /* Bytes 192-255 */ 1406} 1407DAC960_V2_LogicalDeviceInfo_T; 1408 1409 1410/* 1411 Define the DAC960 V2 Firmware Physical Device State type. 1412*/ 1413 1414typedef enum 1415{ 1416 DAC960_V2_Device_Unconfigured = 0x00, 1417 DAC960_V2_Device_Online = 0x01, 1418 DAC960_V2_Device_Rebuild = 0x03, 1419 DAC960_V2_Device_Missing = 0x04, 1420 DAC960_V2_Device_Critical = 0x05, 1421 DAC960_V2_Device_Dead = 0x08, 1422 DAC960_V2_Device_SuspectedDead = 0x0C, 1423 DAC960_V2_Device_CommandedOffline = 0x10, 1424 DAC960_V2_Device_Standby = 0x21, 1425 DAC960_V2_Device_InvalidState = 0xFF 1426} 1427__attribute__ ((packed)) 1428DAC960_V2_PhysicalDeviceState_T; 1429 1430 1431/* 1432 Define the DAC960 V2 Firmware Get Physical Device Info reply structure. 1433*/ 1434 1435typedef struct DAC960_V2_PhysicalDeviceInfo 1436{ 1437 unsigned char :8; /* Byte 0 */ 1438 unsigned char Channel; /* Byte 1 */ 1439 unsigned char TargetID; /* Byte 2 */ 1440 unsigned char LogicalUnit; /* Byte 3 */ 1441 /* Configuration Status Bits */ 1442 bool PhysicalDeviceFaultTolerant:1; /* Byte 4 Bit 0 */ 1443 bool PhysicalDeviceConnected:1; /* Byte 4 Bit 1 */ 1444 bool PhysicalDeviceLocalToController:1; /* Byte 4 Bit 2 */ 1445 unsigned char :5; /* Byte 4 Bits 3-7 */ 1446 /* Multiple Host/Controller Status Bits */ 1447 bool RemoteHostSystemDead:1; /* Byte 5 Bit 0 */ 1448 bool RemoteControllerDead:1; /* Byte 5 Bit 1 */ 1449 unsigned char :6; /* Byte 5 Bits 2-7 */ 1450 DAC960_V2_PhysicalDeviceState_T PhysicalDeviceState; /* Byte 6 */ 1451 unsigned char NegotiatedDataWidthBits; /* Byte 7 */ 1452 unsigned short NegotiatedSynchronousMegaTransfers; /* Bytes 8-9 */ 1453 /* Multiported Physical Device Information */ 1454 unsigned char NumberOfPortConnections; /* Byte 10 */ 1455 unsigned char DriveAccessibilityBitmap; /* Byte 11 */ 1456 unsigned int :32; /* Bytes 12-15 */ 1457 unsigned char NetworkAddress[16]; /* Bytes 16-31 */ 1458 unsigned short MaximumTags; /* Bytes 32-33 */ 1459 /* Physical Device Operations Status */ 1460 bool ConsistencyCheckInProgress:1; /* Byte 34 Bit 0 */ 1461 bool RebuildInProgress:1; /* Byte 34 Bit 1 */ 1462 bool MakingDataConsistentInProgress:1; /* Byte 34 Bit 2 */ 1463 bool PhysicalDeviceInitializationInProgress:1; /* Byte 34 Bit 3 */ 1464 bool DataMigrationInProgress:1; /* Byte 34 Bit 4 */ 1465 bool PatrolOperationInProgress:1; /* Byte 34 Bit 5 */ 1466 unsigned char :2; /* Byte 34 Bits 6-7 */ 1467 unsigned char LongOperationStatus; /* Byte 35 */ 1468 unsigned char ParityErrors; /* Byte 36 */ 1469 unsigned char SoftErrors; /* Byte 37 */ 1470 unsigned char HardErrors; /* Byte 38 */ 1471 unsigned char MiscellaneousErrors; /* Byte 39 */ 1472 unsigned char CommandTimeouts; /* Byte 40 */ 1473 unsigned char Retries; /* Byte 41 */ 1474 unsigned char Aborts; /* Byte 42 */ 1475 unsigned char PredictedFailuresDetected; /* Byte 43 */ 1476 unsigned int :32; /* Bytes 44-47 */ 1477 unsigned short :16; /* Bytes 48-49 */ 1478 unsigned short DeviceBlockSizeInBytes; /* Bytes 50-51 */ 1479 unsigned int OriginalDeviceSize; /* Bytes 52-55 */ 1480 unsigned int ConfigurableDeviceSize; /* Bytes 56-59 */ 1481 unsigned int :32; /* Bytes 60-63 */ 1482 unsigned char PhysicalDeviceName[16]; /* Bytes 64-79 */ 1483 unsigned char Reserved1[16]; /* Bytes 80-95 */ 1484 unsigned char Reserved2[32]; /* Bytes 96-127 */ 1485 unsigned char SCSI_InquiryData[36]; /* Bytes 128-163 */ 1486 unsigned char Reserved3[20]; /* Bytes 164-183 */ 1487 unsigned char Reserved4[8]; /* Bytes 184-191 */ 1488 DAC960_ByteCount64_T LastReadBlockNumber; /* Bytes 192-199 */ 1489 DAC960_ByteCount64_T LastWrittenBlockNumber; /* Bytes 200-207 */ 1490 DAC960_ByteCount64_T ConsistencyCheckBlockNumber; /* Bytes 208-215 */ 1491 DAC960_ByteCount64_T RebuildBlockNumber; /* Bytes 216-223 */ 1492 DAC960_ByteCount64_T MakingDataConsistentBlockNumber; /* Bytes 224-231 */ 1493 DAC960_ByteCount64_T DeviceInitializationBlockNumber; /* Bytes 232-239 */ 1494 DAC960_ByteCount64_T DataMigrationBlockNumber; /* Bytes 240-247 */ 1495 DAC960_ByteCount64_T PatrolOperationBlockNumber; /* Bytes 248-255 */ 1496 unsigned char Reserved5[256]; /* Bytes 256-511 */ 1497} 1498DAC960_V2_PhysicalDeviceInfo_T; 1499 1500 1501/* 1502 Define the DAC960 V2 Firmware Health Status Buffer structure. 1503*/ 1504 1505typedef struct DAC960_V2_HealthStatusBuffer 1506{ 1507 unsigned int MicrosecondsFromControllerStartTime; /* Bytes 0-3 */ 1508 unsigned int MillisecondsFromControllerStartTime; /* Bytes 4-7 */ 1509 unsigned int SecondsFrom1January1970; /* Bytes 8-11 */ 1510 unsigned int :32; /* Bytes 12-15 */ 1511 unsigned int StatusChangeCounter; /* Bytes 16-19 */ 1512 unsigned int :32; /* Bytes 20-23 */ 1513 unsigned int DebugOutputMessageBufferIndex; /* Bytes 24-27 */ 1514 unsigned int CodedMessageBufferIndex; /* Bytes 28-31 */ 1515 unsigned int CurrentTimeTracePageNumber; /* Bytes 32-35 */ 1516 unsigned int CurrentProfilerPageNumber; /* Bytes 36-39 */ 1517 unsigned int NextEventSequenceNumber; /* Bytes 40-43 */ 1518 unsigned int :32; /* Bytes 44-47 */ 1519 unsigned char Reserved1[16]; /* Bytes 48-63 */ 1520 unsigned char Reserved2[64]; /* Bytes 64-127 */ 1521} 1522DAC960_V2_HealthStatusBuffer_T; 1523 1524 1525/* 1526 Define the DAC960 V2 Firmware Get Event reply structure. 1527*/ 1528 1529typedef struct DAC960_V2_Event 1530{ 1531 unsigned int EventSequenceNumber; /* Bytes 0-3 */ 1532 unsigned int EventTime; /* Bytes 4-7 */ 1533 unsigned int EventCode; /* Bytes 8-11 */ 1534 unsigned char :8; /* Byte 12 */ 1535 unsigned char Channel; /* Byte 13 */ 1536 unsigned char TargetID; /* Byte 14 */ 1537 unsigned char LogicalUnit; /* Byte 15 */ 1538 unsigned int :32; /* Bytes 16-19 */ 1539 unsigned int EventSpecificParameter; /* Bytes 20-23 */ 1540 unsigned char RequestSenseData[40]; /* Bytes 24-63 */ 1541} 1542DAC960_V2_Event_T; 1543 1544 1545/* 1546 Define the DAC960 V2 Firmware Command Control Bits structure. 1547*/ 1548 1549typedef struct DAC960_V2_CommandControlBits 1550{ 1551 bool ForceUnitAccess:1; /* Byte 0 Bit 0 */ 1552 bool DisablePageOut:1; /* Byte 0 Bit 1 */ 1553 bool :1; /* Byte 0 Bit 2 */ 1554 bool AdditionalScatterGatherListMemory:1; /* Byte 0 Bit 3 */ 1555 bool DataTransferControllerToHost:1; /* Byte 0 Bit 4 */ 1556 bool :1; /* Byte 0 Bit 5 */ 1557 bool NoAutoRequestSense:1; /* Byte 0 Bit 6 */ 1558 bool DisconnectProhibited:1; /* Byte 0 Bit 7 */ 1559} 1560DAC960_V2_CommandControlBits_T; 1561 1562 1563/* 1564 Define the DAC960 V2 Firmware Command Timeout structure. 1565*/ 1566 1567typedef struct DAC960_V2_CommandTimeout 1568{ 1569 unsigned char TimeoutValue:6; /* Byte 0 Bits 0-5 */ 1570 enum { 1571 DAC960_V2_TimeoutScale_Seconds = 0, 1572 DAC960_V2_TimeoutScale_Minutes = 1, 1573 DAC960_V2_TimeoutScale_Hours = 2, 1574 DAC960_V2_TimeoutScale_Reserved = 3 1575 } __attribute__ ((packed)) TimeoutScale:2; /* Byte 0 Bits 6-7 */ 1576} 1577DAC960_V2_CommandTimeout_T; 1578 1579 1580/* 1581 Define the DAC960 V2 Firmware Physical Device structure. 1582*/ 1583 1584typedef struct DAC960_V2_PhysicalDevice 1585{ 1586 unsigned char LogicalUnit; /* Byte 0 */ 1587 unsigned char TargetID; /* Byte 1 */ 1588 unsigned char Channel:3; /* Byte 2 Bits 0-2 */ 1589 unsigned char Controller:5; /* Byte 2 Bits 3-7 */ 1590} 1591__attribute__ ((packed)) 1592DAC960_V2_PhysicalDevice_T; 1593 1594 1595/* 1596 Define the DAC960 V2 Firmware Logical Device structure. 1597*/ 1598 1599typedef struct DAC960_V2_LogicalDevice 1600{ 1601 unsigned short LogicalDeviceNumber; /* Bytes 0-1 */ 1602 unsigned char :3; /* Byte 2 Bits 0-2 */ 1603 unsigned char Controller:5; /* Byte 2 Bits 3-7 */ 1604} 1605__attribute__ ((packed)) 1606DAC960_V2_LogicalDevice_T; 1607 1608 1609/* 1610 Define the DAC960 V2 Firmware Operation Device type. 1611*/ 1612 1613typedef enum 1614{ 1615 DAC960_V2_Physical_Device = 0x00, 1616 DAC960_V2_RAID_Device = 0x01, 1617 DAC960_V2_Physical_Channel = 0x02, 1618 DAC960_V2_RAID_Channel = 0x03, 1619 DAC960_V2_Physical_Controller = 0x04, 1620 DAC960_V2_RAID_Controller = 0x05, 1621 DAC960_V2_Configuration_Group = 0x10, 1622 DAC960_V2_Enclosure = 0x11 1623} 1624__attribute__ ((packed)) 1625DAC960_V2_OperationDevice_T; 1626 1627 1628/* 1629 Define the DAC960 V2 Firmware Translate Physical To Logical Device structure. 1630*/ 1631 1632typedef struct DAC960_V2_PhysicalToLogicalDevice 1633{ 1634 unsigned short LogicalDeviceNumber; /* Bytes 0-1 */ 1635 unsigned short :16; /* Bytes 2-3 */ 1636 unsigned char PreviousBootController; /* Byte 4 */ 1637 unsigned char PreviousBootChannel; /* Byte 5 */ 1638 unsigned char PreviousBootTargetID; /* Byte 6 */ 1639 unsigned char PreviousBootLogicalUnit; /* Byte 7 */ 1640} 1641DAC960_V2_PhysicalToLogicalDevice_T; 1642 1643 1644 1645/* 1646 Define the DAC960 V2 Firmware Scatter/Gather List Entry structure. 1647*/ 1648 1649typedef struct DAC960_V2_ScatterGatherSegment 1650{ 1651 DAC960_BusAddress64_T SegmentDataPointer; /* Bytes 0-7 */ 1652 DAC960_ByteCount64_T SegmentByteCount; /* Bytes 8-15 */ 1653} 1654DAC960_V2_ScatterGatherSegment_T; 1655 1656 1657/* 1658 Define the DAC960 V2 Firmware Data Transfer Memory Address structure. 1659*/ 1660 1661typedef union DAC960_V2_DataTransferMemoryAddress 1662{ 1663 DAC960_V2_ScatterGatherSegment_T ScatterGatherSegments[2]; /* Bytes 0-31 */ 1664 struct { 1665 unsigned short ScatterGatherList0Length; /* Bytes 0-1 */ 1666 unsigned short ScatterGatherList1Length; /* Bytes 2-3 */ 1667 unsigned short ScatterGatherList2Length; /* Bytes 4-5 */ 1668 unsigned short :16; /* Bytes 6-7 */ 1669 DAC960_BusAddress64_T ScatterGatherList0Address; /* Bytes 8-15 */ 1670 DAC960_BusAddress64_T ScatterGatherList1Address; /* Bytes 16-23 */ 1671 DAC960_BusAddress64_T ScatterGatherList2Address; /* Bytes 24-31 */ 1672 } ExtendedScatterGather; 1673} 1674DAC960_V2_DataTransferMemoryAddress_T; 1675 1676 1677/* 1678 Define the 64 Byte DAC960 V2 Firmware Command Mailbox structure. 1679*/ 1680 1681typedef union DAC960_V2_CommandMailbox 1682{ 1683 unsigned int Words[16]; /* Words 0-15 */ 1684 struct { 1685 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1686 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1687 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1688 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1689 unsigned char DataTransferPageNumber; /* Byte 7 */ 1690 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1691 unsigned int :24; /* Bytes 16-18 */ 1692 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1693 unsigned char RequestSenseSize; /* Byte 20 */ 1694 unsigned char IOCTL_Opcode; /* Byte 21 */ 1695 unsigned char Reserved[10]; /* Bytes 22-31 */ 1696 DAC960_V2_DataTransferMemoryAddress_T 1697 DataTransferMemoryAddress; /* Bytes 32-63 */ 1698 } Common; 1699 struct { 1700 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1701 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1702 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1703 DAC960_ByteCount32_T DataTransferSize; /* Bytes 4-7 */ 1704 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1705 DAC960_V2_PhysicalDevice_T PhysicalDevice; /* Bytes 16-18 */ 1706 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1707 unsigned char RequestSenseSize; /* Byte 20 */ 1708 unsigned char CDBLength; /* Byte 21 */ 1709 unsigned char SCSI_CDB[10]; /* Bytes 22-31 */ 1710 DAC960_V2_DataTransferMemoryAddress_T 1711 DataTransferMemoryAddress; /* Bytes 32-63 */ 1712 } SCSI_10; 1713 struct { 1714 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1715 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1716 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1717 DAC960_ByteCount32_T DataTransferSize; /* Bytes 4-7 */ 1718 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1719 DAC960_V2_PhysicalDevice_T PhysicalDevice; /* Bytes 16-18 */ 1720 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1721 unsigned char RequestSenseSize; /* Byte 20 */ 1722 unsigned char CDBLength; /* Byte 21 */ 1723 unsigned short :16; /* Bytes 22-23 */ 1724 DAC960_BusAddress64_T SCSI_CDB_BusAddress; /* Bytes 24-31 */ 1725 DAC960_V2_DataTransferMemoryAddress_T 1726 DataTransferMemoryAddress; /* Bytes 32-63 */ 1727 } SCSI_255; 1728 struct { 1729 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1730 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1731 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1732 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1733 unsigned char DataTransferPageNumber; /* Byte 7 */ 1734 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1735 unsigned short :16; /* Bytes 16-17 */ 1736 unsigned char ControllerNumber; /* Byte 18 */ 1737 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1738 unsigned char RequestSenseSize; /* Byte 20 */ 1739 unsigned char IOCTL_Opcode; /* Byte 21 */ 1740 unsigned char Reserved[10]; /* Bytes 22-31 */ 1741 DAC960_V2_DataTransferMemoryAddress_T 1742 DataTransferMemoryAddress; /* Bytes 32-63 */ 1743 } ControllerInfo; 1744 struct { 1745 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1746 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1747 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1748 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1749 unsigned char DataTransferPageNumber; /* Byte 7 */ 1750 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1751 DAC960_V2_LogicalDevice_T LogicalDevice; /* Bytes 16-18 */ 1752 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1753 unsigned char RequestSenseSize; /* Byte 20 */ 1754 unsigned char IOCTL_Opcode; /* Byte 21 */ 1755 unsigned char Reserved[10]; /* Bytes 22-31 */ 1756 DAC960_V2_DataTransferMemoryAddress_T 1757 DataTransferMemoryAddress; /* Bytes 32-63 */ 1758 } LogicalDeviceInfo; 1759 struct { 1760 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1761 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1762 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1763 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1764 unsigned char DataTransferPageNumber; /* Byte 7 */ 1765 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1766 DAC960_V2_PhysicalDevice_T PhysicalDevice; /* Bytes 16-18 */ 1767 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1768 unsigned char RequestSenseSize; /* Byte 20 */ 1769 unsigned char IOCTL_Opcode; /* Byte 21 */ 1770 unsigned char Reserved[10]; /* Bytes 22-31 */ 1771 DAC960_V2_DataTransferMemoryAddress_T 1772 DataTransferMemoryAddress; /* Bytes 32-63 */ 1773 } PhysicalDeviceInfo; 1774 struct { 1775 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1776 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1777 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1778 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1779 unsigned char DataTransferPageNumber; /* Byte 7 */ 1780 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1781 unsigned short EventSequenceNumberHigh16; /* Bytes 16-17 */ 1782 unsigned char ControllerNumber; /* Byte 18 */ 1783 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1784 unsigned char RequestSenseSize; /* Byte 20 */ 1785 unsigned char IOCTL_Opcode; /* Byte 21 */ 1786 unsigned short EventSequenceNumberLow16; /* Bytes 22-23 */ 1787 unsigned char Reserved[8]; /* Bytes 24-31 */ 1788 DAC960_V2_DataTransferMemoryAddress_T 1789 DataTransferMemoryAddress; /* Bytes 32-63 */ 1790 } GetEvent; 1791 struct { 1792 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1793 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1794 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1795 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1796 unsigned char DataTransferPageNumber; /* Byte 7 */ 1797 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1798 DAC960_V2_LogicalDevice_T LogicalDevice; /* Bytes 16-18 */ 1799 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1800 unsigned char RequestSenseSize; /* Byte 20 */ 1801 unsigned char IOCTL_Opcode; /* Byte 21 */ 1802 union { 1803 DAC960_V2_LogicalDeviceState_T LogicalDeviceState; 1804 DAC960_V2_PhysicalDeviceState_T PhysicalDeviceState; 1805 } DeviceState; /* Byte 22 */ 1806 unsigned char Reserved[9]; /* Bytes 23-31 */ 1807 DAC960_V2_DataTransferMemoryAddress_T 1808 DataTransferMemoryAddress; /* Bytes 32-63 */ 1809 } SetDeviceState; 1810 struct { 1811 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1812 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1813 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1814 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1815 unsigned char DataTransferPageNumber; /* Byte 7 */ 1816 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1817 DAC960_V2_LogicalDevice_T LogicalDevice; /* Bytes 16-18 */ 1818 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1819 unsigned char RequestSenseSize; /* Byte 20 */ 1820 unsigned char IOCTL_Opcode; /* Byte 21 */ 1821 bool RestoreConsistency:1; /* Byte 22 Bit 0 */ 1822 bool InitializedAreaOnly:1; /* Byte 22 Bit 1 */ 1823 unsigned char :6; /* Byte 22 Bits 2-7 */ 1824 unsigned char Reserved[9]; /* Bytes 23-31 */ 1825 DAC960_V2_DataTransferMemoryAddress_T 1826 DataTransferMemoryAddress; /* Bytes 32-63 */ 1827 } ConsistencyCheck; 1828 struct { 1829 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1830 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1831 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1832 unsigned char FirstCommandMailboxSizeKB; /* Byte 4 */ 1833 unsigned char FirstStatusMailboxSizeKB; /* Byte 5 */ 1834 unsigned char SecondCommandMailboxSizeKB; /* Byte 6 */ 1835 unsigned char SecondStatusMailboxSizeKB; /* Byte 7 */ 1836 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1837 unsigned int :24; /* Bytes 16-18 */ 1838 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1839 unsigned char RequestSenseSize; /* Byte 20 */ 1840 unsigned char IOCTL_Opcode; /* Byte 21 */ 1841 unsigned char HealthStatusBufferSizeKB; /* Byte 22 */ 1842 unsigned char :8; /* Byte 23 */ 1843 DAC960_BusAddress64_T HealthStatusBufferBusAddress; /* Bytes 24-31 */ 1844 DAC960_BusAddress64_T FirstCommandMailboxBusAddress; /* Bytes 32-39 */ 1845 DAC960_BusAddress64_T FirstStatusMailboxBusAddress; /* Bytes 40-47 */ 1846 DAC960_BusAddress64_T SecondCommandMailboxBusAddress; /* Bytes 48-55 */ 1847 DAC960_BusAddress64_T SecondStatusMailboxBusAddress; /* Bytes 56-63 */ 1848 } SetMemoryMailbox; 1849 struct { 1850 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 1851 DAC960_V2_CommandOpcode_T CommandOpcode; /* Byte 2 */ 1852 DAC960_V2_CommandControlBits_T CommandControlBits; /* Byte 3 */ 1853 DAC960_ByteCount32_T DataTransferSize:24; /* Bytes 4-6 */ 1854 unsigned char DataTransferPageNumber; /* Byte 7 */ 1855 DAC960_BusAddress64_T RequestSenseBusAddress; /* Bytes 8-15 */ 1856 DAC960_V2_PhysicalDevice_T PhysicalDevice; /* Bytes 16-18 */ 1857 DAC960_V2_CommandTimeout_T CommandTimeout; /* Byte 19 */ 1858 unsigned char RequestSenseSize; /* Byte 20 */ 1859 unsigned char IOCTL_Opcode; /* Byte 21 */ 1860 DAC960_V2_OperationDevice_T OperationDevice; /* Byte 22 */ 1861 unsigned char Reserved[9]; /* Bytes 23-31 */ 1862 DAC960_V2_DataTransferMemoryAddress_T 1863 DataTransferMemoryAddress; /* Bytes 32-63 */ 1864 } DeviceOperation; 1865} 1866DAC960_V2_CommandMailbox_T; 1867 1868 1869/* 1870 Define the DAC960 Driver IOCTL requests. 1871*/ 1872 1873#define DAC960_IOCTL_GET_CONTROLLER_COUNT 0xDAC001 1874#define DAC960_IOCTL_GET_CONTROLLER_INFO 0xDAC002 1875#define DAC960_IOCTL_V1_EXECUTE_COMMAND 0xDAC003 1876#define DAC960_IOCTL_V2_EXECUTE_COMMAND 0xDAC004 1877#define DAC960_IOCTL_V2_GET_HEALTH_STATUS 0xDAC005 1878 1879 1880/* 1881 Define the DAC960_IOCTL_GET_CONTROLLER_INFO reply structure. 1882*/ 1883 1884typedef struct DAC960_ControllerInfo 1885{ 1886 unsigned char ControllerNumber; 1887 unsigned char FirmwareType; 1888 unsigned char Channels; 1889 unsigned char Targets; 1890 unsigned char PCI_Bus; 1891 unsigned char PCI_Device; 1892 unsigned char PCI_Function; 1893 unsigned char IRQ_Channel; 1894 DAC960_PCI_Address_T PCI_Address; 1895 unsigned char ModelName[20]; 1896 unsigned char FirmwareVersion[12]; 1897} 1898DAC960_ControllerInfo_T; 1899 1900 1901/* 1902 Define the User Mode DAC960_IOCTL_V1_EXECUTE_COMMAND request structure. 1903*/ 1904 1905typedef struct DAC960_V1_UserCommand 1906{ 1907 unsigned char ControllerNumber; 1908 DAC960_V1_CommandMailbox_T CommandMailbox; 1909 int DataTransferLength; 1910 void __user *DataTransferBuffer; 1911 DAC960_V1_DCDB_T __user *DCDB; 1912} 1913DAC960_V1_UserCommand_T; 1914 1915 1916/* 1917 Define the Kernel Mode DAC960_IOCTL_V1_EXECUTE_COMMAND request structure. 1918*/ 1919 1920typedef struct DAC960_V1_KernelCommand 1921{ 1922 unsigned char ControllerNumber; 1923 DAC960_V1_CommandMailbox_T CommandMailbox; 1924 int DataTransferLength; 1925 void *DataTransferBuffer; 1926 DAC960_V1_DCDB_T *DCDB; 1927 DAC960_V1_CommandStatus_T CommandStatus; 1928 void (*CompletionFunction)(struct DAC960_V1_KernelCommand *); 1929 void *CompletionData; 1930} 1931DAC960_V1_KernelCommand_T; 1932 1933 1934/* 1935 Define the User Mode DAC960_IOCTL_V2_EXECUTE_COMMAND request structure. 1936*/ 1937 1938typedef struct DAC960_V2_UserCommand 1939{ 1940 unsigned char ControllerNumber; 1941 DAC960_V2_CommandMailbox_T CommandMailbox; 1942 int DataTransferLength; 1943 int RequestSenseLength; 1944 void __user *DataTransferBuffer; 1945 void __user *RequestSenseBuffer; 1946} 1947DAC960_V2_UserCommand_T; 1948 1949 1950/* 1951 Define the Kernel Mode DAC960_IOCTL_V2_EXECUTE_COMMAND request structure. 1952*/ 1953 1954typedef struct DAC960_V2_KernelCommand 1955{ 1956 unsigned char ControllerNumber; 1957 DAC960_V2_CommandMailbox_T CommandMailbox; 1958 int DataTransferLength; 1959 int RequestSenseLength; 1960 void *DataTransferBuffer; 1961 void *RequestSenseBuffer; 1962 DAC960_V2_CommandStatus_T CommandStatus; 1963 void (*CompletionFunction)(struct DAC960_V2_KernelCommand *); 1964 void *CompletionData; 1965} 1966DAC960_V2_KernelCommand_T; 1967 1968 1969/* 1970 Define the User Mode DAC960_IOCTL_V2_GET_HEALTH_STATUS request structure. 1971*/ 1972 1973typedef struct DAC960_V2_GetHealthStatus 1974{ 1975 unsigned char ControllerNumber; 1976 DAC960_V2_HealthStatusBuffer_T __user *HealthStatusBuffer; 1977} 1978DAC960_V2_GetHealthStatus_T; 1979 1980 1981/* 1982 Import the Kernel Mode IOCTL interface. 1983*/ 1984 1985extern int DAC960_KernelIOCTL(unsigned int Request, void *Argument); 1986 1987 1988/* 1989 DAC960_DriverVersion protects the private portion of this file. 1990*/ 1991 1992#ifdef DAC960_DriverVersion 1993 1994 1995/* 1996 Define the maximum Driver Queue Depth and Controller Queue Depth supported 1997 by DAC960 V1 and V2 Firmware Controllers. 1998*/ 1999 2000#define DAC960_MaxDriverQueueDepth 511 2001#define DAC960_MaxControllerQueueDepth 512 2002 2003 2004/* 2005 Define the maximum number of Scatter/Gather Segments supported for any 2006 DAC960 V1 and V2 Firmware controller. 2007*/ 2008 2009#define DAC960_V1_ScatterGatherLimit 33 2010#define DAC960_V2_ScatterGatherLimit 128 2011 2012 2013/* 2014 Define the number of Command Mailboxes and Status Mailboxes used by the 2015 DAC960 V1 and V2 Firmware Memory Mailbox Interface. 2016*/ 2017 2018#define DAC960_V1_CommandMailboxCount 256 2019#define DAC960_V1_StatusMailboxCount 1024 2020#define DAC960_V2_CommandMailboxCount 512 2021#define DAC960_V2_StatusMailboxCount 512 2022 2023 2024/* 2025 Define the DAC960 Controller Monitoring Timer Interval. 2026*/ 2027 2028#define DAC960_MonitoringTimerInterval (10 * HZ) 2029 2030 2031/* 2032 Define the DAC960 Controller Secondary Monitoring Interval. 2033*/ 2034 2035#define DAC960_SecondaryMonitoringInterval (60 * HZ) 2036 2037 2038/* 2039 Define the DAC960 Controller Health Status Monitoring Interval. 2040*/ 2041 2042#define DAC960_HealthStatusMonitoringInterval (1 * HZ) 2043 2044 2045/* 2046 Define the DAC960 Controller Progress Reporting Interval. 2047*/ 2048 2049#define DAC960_ProgressReportingInterval (60 * HZ) 2050 2051 2052/* 2053 Define the maximum number of Partitions allowed for each Logical Drive. 2054*/ 2055 2056#define DAC960_MaxPartitions 8 2057#define DAC960_MaxPartitionsBits 3 2058 2059/* 2060 Define the DAC960 Controller fixed Block Size and Block Size Bits. 2061*/ 2062 2063#define DAC960_BlockSize 512 2064#define DAC960_BlockSizeBits 9 2065 2066 2067/* 2068 Define the number of Command structures that should be allocated as a 2069 group to optimize kernel memory allocation. 2070*/ 2071 2072#define DAC960_V1_CommandAllocationGroupSize 11 2073#define DAC960_V2_CommandAllocationGroupSize 29 2074 2075 2076/* 2077 Define the Controller Line Buffer, Progress Buffer, User Message, and 2078 Initial Status Buffer sizes. 2079*/ 2080 2081#define DAC960_LineBufferSize 100 2082#define DAC960_ProgressBufferSize 200 2083#define DAC960_UserMessageSize 200 2084#define DAC960_InitialStatusBufferSize (8192-32) 2085 2086 2087/* 2088 Define the DAC960 Controller Firmware Types. 2089*/ 2090 2091typedef enum 2092{ 2093 DAC960_V1_Controller = 1, 2094 DAC960_V2_Controller = 2 2095} 2096DAC960_FirmwareType_T; 2097 2098 2099/* 2100 Define the DAC960 Controller Hardware Types. 2101*/ 2102 2103typedef enum 2104{ 2105 DAC960_BA_Controller = 1, /* eXtremeRAID 2000 */ 2106 DAC960_LP_Controller = 2, /* AcceleRAID 352 */ 2107 DAC960_LA_Controller = 3, /* DAC1164P */ 2108 DAC960_PG_Controller = 4, /* DAC960PTL/PJ/PG */ 2109 DAC960_PD_Controller = 5, /* DAC960PU/PD/PL/P */ 2110 DAC960_P_Controller = 6, /* DAC960PU/PD/PL/P */ 2111 DAC960_GEM_Controller = 7, /* AcceleRAID 4/5/600 */ 2112} 2113DAC960_HardwareType_T; 2114 2115 2116/* 2117 Define the Driver Message Levels. 2118*/ 2119 2120typedef enum DAC960_MessageLevel 2121{ 2122 DAC960_AnnounceLevel = 0, 2123 DAC960_InfoLevel = 1, 2124 DAC960_NoticeLevel = 2, 2125 DAC960_WarningLevel = 3, 2126 DAC960_ErrorLevel = 4, 2127 DAC960_ProgressLevel = 5, 2128 DAC960_CriticalLevel = 6, 2129 DAC960_UserCriticalLevel = 7 2130} 2131DAC960_MessageLevel_T; 2132 2133static char 2134 *DAC960_MessageLevelMap[] = 2135 { KERN_NOTICE, KERN_NOTICE, KERN_NOTICE, KERN_WARNING, 2136 KERN_ERR, KERN_CRIT, KERN_CRIT, KERN_CRIT }; 2137 2138 2139/* 2140 Define Driver Message macros. 2141*/ 2142 2143#define DAC960_Announce(Format, Arguments...) \ 2144 DAC960_Message(DAC960_AnnounceLevel, Format, ##Arguments) 2145 2146#define DAC960_Info(Format, Arguments...) \ 2147 DAC960_Message(DAC960_InfoLevel, Format, ##Arguments) 2148 2149#define DAC960_Notice(Format, Arguments...) \ 2150 DAC960_Message(DAC960_NoticeLevel, Format, ##Arguments) 2151 2152#define DAC960_Warning(Format, Arguments...) \ 2153 DAC960_Message(DAC960_WarningLevel, Format, ##Arguments) 2154 2155#define DAC960_Error(Format, Arguments...) \ 2156 DAC960_Message(DAC960_ErrorLevel, Format, ##Arguments) 2157 2158#define DAC960_Progress(Format, Arguments...) \ 2159 DAC960_Message(DAC960_ProgressLevel, Format, ##Arguments) 2160 2161#define DAC960_Critical(Format, Arguments...) \ 2162 DAC960_Message(DAC960_CriticalLevel, Format, ##Arguments) 2163 2164#define DAC960_UserCritical(Format, Arguments...) \ 2165 DAC960_Message(DAC960_UserCriticalLevel, Format, ##Arguments) 2166 2167 2168struct DAC960_privdata { 2169 DAC960_HardwareType_T HardwareType; 2170 DAC960_FirmwareType_T FirmwareType; 2171 irq_handler_t InterruptHandler; 2172 unsigned int MemoryWindowSize; 2173}; 2174 2175 2176/* 2177 Define the DAC960 V1 Firmware Controller Status Mailbox structure. 2178*/ 2179 2180typedef union DAC960_V1_StatusMailbox 2181{ 2182 unsigned int Word; /* Word 0 */ 2183 struct { 2184 DAC960_V1_CommandIdentifier_T CommandIdentifier; /* Byte 0 */ 2185 unsigned char :7; /* Byte 1 Bits 0-6 */ 2186 bool Valid:1; /* Byte 1 Bit 7 */ 2187 DAC960_V1_CommandStatus_T CommandStatus; /* Bytes 2-3 */ 2188 } Fields; 2189} 2190DAC960_V1_StatusMailbox_T; 2191 2192 2193/* 2194 Define the DAC960 V2 Firmware Controller Status Mailbox structure. 2195*/ 2196 2197typedef union DAC960_V2_StatusMailbox 2198{ 2199 unsigned int Words[2]; /* Words 0-1 */ 2200 struct { 2201 DAC960_V2_CommandIdentifier_T CommandIdentifier; /* Bytes 0-1 */ 2202 DAC960_V2_CommandStatus_T CommandStatus; /* Byte 2 */ 2203 unsigned char RequestSenseLength; /* Byte 3 */ 2204 int DataTransferResidue; /* Bytes 4-7 */ 2205 } Fields; 2206} 2207DAC960_V2_StatusMailbox_T; 2208 2209 2210/* 2211 Define the DAC960 Driver Command Types. 2212*/ 2213 2214typedef enum 2215{ 2216 DAC960_ReadCommand = 1, 2217 DAC960_WriteCommand = 2, 2218 DAC960_ReadRetryCommand = 3, 2219 DAC960_WriteRetryCommand = 4, 2220 DAC960_MonitoringCommand = 5, 2221 DAC960_ImmediateCommand = 6, 2222 DAC960_QueuedCommand = 7 2223} 2224DAC960_CommandType_T; 2225 2226 2227/* 2228 Define the DAC960 Driver Command structure. 2229*/ 2230 2231typedef struct DAC960_Command 2232{ 2233 int CommandIdentifier; 2234 DAC960_CommandType_T CommandType; 2235 struct DAC960_Controller *Controller; 2236 struct DAC960_Command *Next; 2237 struct completion *Completion; 2238 unsigned int LogicalDriveNumber; 2239 unsigned int BlockNumber; 2240 unsigned int BlockCount; 2241 unsigned int SegmentCount; 2242 int DmaDirection; 2243 struct scatterlist *cmd_sglist; 2244 struct request *Request; 2245 union { 2246 struct { 2247 DAC960_V1_CommandMailbox_T CommandMailbox; 2248 DAC960_V1_KernelCommand_T *KernelCommand; 2249 DAC960_V1_CommandStatus_T CommandStatus; 2250 DAC960_V1_ScatterGatherSegment_T *ScatterGatherList; 2251 dma_addr_t ScatterGatherListDMA; 2252 struct scatterlist ScatterList[DAC960_V1_ScatterGatherLimit]; 2253 unsigned int EndMarker[0]; 2254 } V1; 2255 struct { 2256 DAC960_V2_CommandMailbox_T CommandMailbox; 2257 DAC960_V2_KernelCommand_T *KernelCommand; 2258 DAC960_V2_CommandStatus_T CommandStatus; 2259 unsigned char RequestSenseLength; 2260 int DataTransferResidue; 2261 DAC960_V2_ScatterGatherSegment_T *ScatterGatherList; 2262 dma_addr_t ScatterGatherListDMA; 2263 DAC960_SCSI_RequestSense_T *RequestSense; 2264 dma_addr_t RequestSenseDMA; 2265 struct scatterlist ScatterList[DAC960_V2_ScatterGatherLimit]; 2266 unsigned int EndMarker[0]; 2267 } V2; 2268 } FW; 2269} 2270DAC960_Command_T; 2271 2272 2273/* 2274 Define the DAC960 Driver Controller structure. 2275*/ 2276 2277typedef struct DAC960_Controller 2278{ 2279 void __iomem *BaseAddress; 2280 void __iomem *MemoryMappedAddress; 2281 DAC960_FirmwareType_T FirmwareType; 2282 DAC960_HardwareType_T HardwareType; 2283 DAC960_IO_Address_T IO_Address; 2284 DAC960_PCI_Address_T PCI_Address; 2285 struct pci_dev *PCIDevice; 2286 unsigned char ControllerNumber; 2287 unsigned char ControllerName[4]; 2288 unsigned char ModelName[20]; 2289 unsigned char FullModelName[28]; 2290 unsigned char FirmwareVersion[12]; 2291 unsigned char Bus; 2292 unsigned char Device; 2293 unsigned char Function; 2294 unsigned char IRQ_Channel; 2295 unsigned char Channels; 2296 unsigned char Targets; 2297 unsigned char MemorySize; 2298 unsigned char LogicalDriveCount; 2299 unsigned short CommandAllocationGroupSize; 2300 unsigned short ControllerQueueDepth; 2301 unsigned short DriverQueueDepth; 2302 unsigned short MaxBlocksPerCommand; 2303 unsigned short ControllerScatterGatherLimit; 2304 unsigned short DriverScatterGatherLimit; 2305 u64 BounceBufferLimit; 2306 unsigned int CombinedStatusBufferLength; 2307 unsigned int InitialStatusLength; 2308 unsigned int CurrentStatusLength; 2309 unsigned int ProgressBufferLength; 2310 unsigned int UserStatusLength; 2311 struct dma_loaf DmaPages; 2312 unsigned long MonitoringTimerCount; 2313 unsigned long PrimaryMonitoringTime; 2314 unsigned long SecondaryMonitoringTime; 2315 unsigned long ShutdownMonitoringTimer; 2316 unsigned long LastProgressReportTime; 2317 unsigned long LastCurrentStatusTime; 2318 bool ControllerInitialized; 2319 bool MonitoringCommandDeferred; 2320 bool EphemeralProgressMessage; 2321 bool DriveSpinUpMessageDisplayed; 2322 bool MonitoringAlertMode; 2323 bool SuppressEnclosureMessages; 2324 struct timer_list MonitoringTimer; 2325 struct gendisk *disks[DAC960_MaxLogicalDrives]; 2326 struct pci_pool *ScatterGatherPool; 2327 DAC960_Command_T *FreeCommands; 2328 unsigned char *CombinedStatusBuffer; 2329 unsigned char *CurrentStatusBuffer; 2330 struct request_queue *RequestQueue[DAC960_MaxLogicalDrives]; 2331 int req_q_index; 2332 spinlock_t queue_lock; 2333 wait_queue_head_t CommandWaitQueue; 2334 wait_queue_head_t HealthStatusWaitQueue; 2335 DAC960_Command_T InitialCommand; 2336 DAC960_Command_T *Commands[DAC960_MaxDriverQueueDepth]; 2337 struct proc_dir_entry *ControllerProcEntry; 2338 bool LogicalDriveInitiallyAccessible[DAC960_MaxLogicalDrives]; 2339 void (*QueueCommand)(DAC960_Command_T *Command); 2340 bool (*ReadControllerConfiguration)(struct DAC960_Controller *); 2341 bool (*ReadDeviceConfiguration)(struct DAC960_Controller *); 2342 bool (*ReportDeviceConfiguration)(struct DAC960_Controller *); 2343 void (*QueueReadWriteCommand)(DAC960_Command_T *Command); 2344 union { 2345 struct { 2346 unsigned char GeometryTranslationHeads; 2347 unsigned char GeometryTranslationSectors; 2348 unsigned char PendingRebuildFlag; 2349 unsigned short StripeSize; 2350 unsigned short SegmentSize; 2351 unsigned short NewEventLogSequenceNumber; 2352 unsigned short OldEventLogSequenceNumber; 2353 unsigned short DeviceStateChannel; 2354 unsigned short DeviceStateTargetID; 2355 bool DualModeMemoryMailboxInterface; 2356 bool BackgroundInitializationStatusSupported; 2357 bool SAFTE_EnclosureManagementEnabled; 2358 bool NeedLogicalDriveInformation; 2359 bool NeedErrorTableInformation; 2360 bool NeedDeviceStateInformation; 2361 bool NeedDeviceInquiryInformation; 2362 bool NeedDeviceSerialNumberInformation; 2363 bool NeedRebuildProgress; 2364 bool NeedConsistencyCheckProgress; 2365 bool NeedBackgroundInitializationStatus; 2366 bool StartDeviceStateScan; 2367 bool RebuildProgressFirst; 2368 bool RebuildFlagPending; 2369 bool RebuildStatusPending; 2370 2371 dma_addr_t FirstCommandMailboxDMA; 2372 DAC960_V1_CommandMailbox_T *FirstCommandMailbox; 2373 DAC960_V1_CommandMailbox_T *LastCommandMailbox; 2374 DAC960_V1_CommandMailbox_T *NextCommandMailbox; 2375 DAC960_V1_CommandMailbox_T *PreviousCommandMailbox1; 2376 DAC960_V1_CommandMailbox_T *PreviousCommandMailbox2; 2377 2378 dma_addr_t FirstStatusMailboxDMA; 2379 DAC960_V1_StatusMailbox_T *FirstStatusMailbox; 2380 DAC960_V1_StatusMailbox_T *LastStatusMailbox; 2381 DAC960_V1_StatusMailbox_T *NextStatusMailbox; 2382 2383 DAC960_V1_DCDB_T *MonitoringDCDB; 2384 dma_addr_t MonitoringDCDB_DMA; 2385 2386 DAC960_V1_Enquiry_T Enquiry; 2387 DAC960_V1_Enquiry_T *NewEnquiry; 2388 dma_addr_t NewEnquiryDMA; 2389 2390 DAC960_V1_ErrorTable_T ErrorTable; 2391 DAC960_V1_ErrorTable_T *NewErrorTable; 2392 dma_addr_t NewErrorTableDMA; 2393 2394 DAC960_V1_EventLogEntry_T *EventLogEntry; 2395 dma_addr_t EventLogEntryDMA; 2396 2397 DAC960_V1_RebuildProgress_T *RebuildProgress; 2398 dma_addr_t RebuildProgressDMA; 2399 DAC960_V1_CommandStatus_T LastRebuildStatus; 2400 DAC960_V1_CommandStatus_T PendingRebuildStatus; 2401 2402 DAC960_V1_LogicalDriveInformationArray_T LogicalDriveInformation; 2403 DAC960_V1_LogicalDriveInformationArray_T *NewLogicalDriveInformation; 2404 dma_addr_t NewLogicalDriveInformationDMA; 2405 2406 DAC960_V1_BackgroundInitializationStatus_T 2407 *BackgroundInitializationStatus; 2408 dma_addr_t BackgroundInitializationStatusDMA; 2409 DAC960_V1_BackgroundInitializationStatus_T 2410 LastBackgroundInitializationStatus; 2411 2412 DAC960_V1_DeviceState_T 2413 DeviceState[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 2414 DAC960_V1_DeviceState_T *NewDeviceState; 2415 dma_addr_t NewDeviceStateDMA; 2416 2417 DAC960_SCSI_Inquiry_T 2418 InquiryStandardData[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 2419 DAC960_SCSI_Inquiry_T *NewInquiryStandardData; 2420 dma_addr_t NewInquiryStandardDataDMA; 2421 2422 DAC960_SCSI_Inquiry_UnitSerialNumber_T 2423 InquiryUnitSerialNumber[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 2424 DAC960_SCSI_Inquiry_UnitSerialNumber_T *NewInquiryUnitSerialNumber; 2425 dma_addr_t NewInquiryUnitSerialNumberDMA; 2426 2427 int DeviceResetCount[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 2428 bool DirectCommandActive[DAC960_V1_MaxChannels][DAC960_V1_MaxTargets]; 2429 } V1; 2430 struct { 2431 unsigned int StatusChangeCounter; 2432 unsigned int NextEventSequenceNumber; 2433 unsigned int PhysicalDeviceIndex; 2434 bool NeedLogicalDeviceInformation; 2435 bool NeedPhysicalDeviceInformation; 2436 bool NeedDeviceSerialNumberInformation; 2437 bool StartLogicalDeviceInformationScan; 2438 bool StartPhysicalDeviceInformationScan; 2439 struct pci_pool *RequestSensePool; 2440 2441 dma_addr_t FirstCommandMailboxDMA; 2442 DAC960_V2_CommandMailbox_T *FirstCommandMailbox; 2443 DAC960_V2_CommandMailbox_T *LastCommandMailbox; 2444 DAC960_V2_CommandMailbox_T *NextCommandMailbox; 2445 DAC960_V2_CommandMailbox_T *PreviousCommandMailbox1; 2446 DAC960_V2_CommandMailbox_T *PreviousCommandMailbox2; 2447 2448 dma_addr_t FirstStatusMailboxDMA; 2449 DAC960_V2_StatusMailbox_T *FirstStatusMailbox; 2450 DAC960_V2_StatusMailbox_T *LastStatusMailbox; 2451 DAC960_V2_StatusMailbox_T *NextStatusMailbox; 2452 2453 dma_addr_t HealthStatusBufferDMA; 2454 DAC960_V2_HealthStatusBuffer_T *HealthStatusBuffer; 2455 2456 DAC960_V2_ControllerInfo_T ControllerInformation; 2457 DAC960_V2_ControllerInfo_T *NewControllerInformation; 2458 dma_addr_t NewControllerInformationDMA; 2459 2460 DAC960_V2_LogicalDeviceInfo_T 2461 *LogicalDeviceInformation[DAC960_MaxLogicalDrives]; 2462 DAC960_V2_LogicalDeviceInfo_T *NewLogicalDeviceInformation; 2463 dma_addr_t NewLogicalDeviceInformationDMA; 2464 2465 DAC960_V2_PhysicalDeviceInfo_T 2466 *PhysicalDeviceInformation[DAC960_V2_MaxPhysicalDevices]; 2467 DAC960_V2_PhysicalDeviceInfo_T *NewPhysicalDeviceInformation; 2468 dma_addr_t NewPhysicalDeviceInformationDMA; 2469 2470 DAC960_SCSI_Inquiry_UnitSerialNumber_T *NewInquiryUnitSerialNumber; 2471 dma_addr_t NewInquiryUnitSerialNumberDMA; 2472 DAC960_SCSI_Inquiry_UnitSerialNumber_T 2473 *InquiryUnitSerialNumber[DAC960_V2_MaxPhysicalDevices]; 2474 2475 DAC960_V2_Event_T *Event; 2476 dma_addr_t EventDMA; 2477 2478 DAC960_V2_PhysicalToLogicalDevice_T *PhysicalToLogicalDevice; 2479 dma_addr_t PhysicalToLogicalDeviceDMA; 2480 2481 DAC960_V2_PhysicalDevice_T 2482 LogicalDriveToVirtualDevice[DAC960_MaxLogicalDrives]; 2483 bool LogicalDriveFoundDuringScan[DAC960_MaxLogicalDrives]; 2484 } V2; 2485 } FW; 2486 unsigned char ProgressBuffer[DAC960_ProgressBufferSize]; 2487 unsigned char UserStatusBuffer[DAC960_UserMessageSize]; 2488} 2489DAC960_Controller_T; 2490 2491 2492/* 2493 Simplify access to Firmware Version Dependent Data Structure Components 2494 and Functions. 2495*/ 2496 2497#define V1 FW.V1 2498#define V2 FW.V2 2499#define DAC960_QueueCommand(Command) \ 2500 (Controller->QueueCommand)(Command) 2501#define DAC960_ReadControllerConfiguration(Controller) \ 2502 (Controller->ReadControllerConfiguration)(Controller) 2503#define DAC960_ReadDeviceConfiguration(Controller) \ 2504 (Controller->ReadDeviceConfiguration)(Controller) 2505#define DAC960_ReportDeviceConfiguration(Controller) \ 2506 (Controller->ReportDeviceConfiguration)(Controller) 2507#define DAC960_QueueReadWriteCommand(Command) \ 2508 (Controller->QueueReadWriteCommand)(Command) 2509 2510/* 2511 * dma_addr_writeql is provided to write dma_addr_t types 2512 * to a 64-bit pci address space register. The controller 2513 * will accept having the register written as two 32-bit 2514 * values. 2515 * 2516 * In HIGHMEM kernels, dma_addr_t is a 64-bit value. 2517 * without HIGHMEM, dma_addr_t is a 32-bit value. 2518 * 2519 * The compiler should always fix up the assignment 2520 * to u.wq appropriately, depending upon the size of 2521 * dma_addr_t. 2522 */ 2523static inline 2524void dma_addr_writeql(dma_addr_t addr, void __iomem *write_address) 2525{ 2526 union { 2527 u64 wq; 2528 uint wl[2]; 2529 } u; 2530 2531 u.wq = addr; 2532 2533 writel(u.wl[0], write_address); 2534 writel(u.wl[1], write_address + 4); 2535} 2536 2537/* 2538 Define the DAC960 GEM Series Controller Interface Register Offsets. 2539 */ 2540 2541#define DAC960_GEM_RegisterWindowSize 0x600 2542 2543typedef enum 2544{ 2545 DAC960_GEM_InboundDoorBellRegisterReadSetOffset = 0x214, 2546 DAC960_GEM_InboundDoorBellRegisterClearOffset = 0x218, 2547 DAC960_GEM_OutboundDoorBellRegisterReadSetOffset = 0x224, 2548 DAC960_GEM_OutboundDoorBellRegisterClearOffset = 0x228, 2549 DAC960_GEM_InterruptStatusRegisterOffset = 0x208, 2550 DAC960_GEM_InterruptMaskRegisterReadSetOffset = 0x22C, 2551 DAC960_GEM_InterruptMaskRegisterClearOffset = 0x230, 2552 DAC960_GEM_CommandMailboxBusAddressOffset = 0x510, 2553 DAC960_GEM_CommandStatusOffset = 0x518, 2554 DAC960_GEM_ErrorStatusRegisterReadSetOffset = 0x224, 2555 DAC960_GEM_ErrorStatusRegisterClearOffset = 0x228, 2556} 2557DAC960_GEM_RegisterOffsets_T; 2558 2559/* 2560 Define the structure of the DAC960 GEM Series Inbound Door Bell 2561 */ 2562 2563typedef union DAC960_GEM_InboundDoorBellRegister 2564{ 2565 unsigned int All; 2566 struct { 2567 unsigned int :24; 2568 bool HardwareMailboxNewCommand:1; 2569 bool AcknowledgeHardwareMailboxStatus:1; 2570 bool GenerateInterrupt:1; 2571 bool ControllerReset:1; 2572 bool MemoryMailboxNewCommand:1; 2573 unsigned int :3; 2574 } Write; 2575 struct { 2576 unsigned int :24; 2577 bool HardwareMailboxFull:1; 2578 bool InitializationInProgress:1; 2579 unsigned int :6; 2580 } Read; 2581} 2582DAC960_GEM_InboundDoorBellRegister_T; 2583 2584/* 2585 Define the structure of the DAC960 GEM Series Outbound Door Bell Register. 2586 */ 2587typedef union DAC960_GEM_OutboundDoorBellRegister 2588{ 2589 unsigned int All; 2590 struct { 2591 unsigned int :24; 2592 bool AcknowledgeHardwareMailboxInterrupt:1; 2593 bool AcknowledgeMemoryMailboxInterrupt:1; 2594 unsigned int :6; 2595 } Write; 2596 struct { 2597 unsigned int :24; 2598 bool HardwareMailboxStatusAvailable:1; 2599 bool MemoryMailboxStatusAvailable:1; 2600 unsigned int :6; 2601 } Read; 2602} 2603DAC960_GEM_OutboundDoorBellRegister_T; 2604 2605/* 2606 Define the structure of the DAC960 GEM Series Interrupt Mask Register. 2607 */ 2608typedef union DAC960_GEM_InterruptMaskRegister 2609{ 2610 unsigned int All; 2611 struct { 2612 unsigned int :16; 2613 unsigned int :8; 2614 unsigned int HardwareMailboxInterrupt:1; 2615 unsigned int MemoryMailboxInterrupt:1; 2616 unsigned int :6; 2617 } Bits; 2618} 2619DAC960_GEM_InterruptMaskRegister_T; 2620 2621/* 2622 Define the structure of the DAC960 GEM Series Error Status Register. 2623 */ 2624 2625typedef union DAC960_GEM_ErrorStatusRegister 2626{ 2627 unsigned int All; 2628 struct { 2629 unsigned int :24; 2630 unsigned int :5; 2631 bool ErrorStatusPending:1; 2632 unsigned int :2; 2633 } Bits; 2634} 2635DAC960_GEM_ErrorStatusRegister_T; 2636 2637/* 2638 Define inline functions to provide an abstraction for reading and writing the 2639 DAC960 GEM Series Controller Interface Registers. 2640*/ 2641 2642static inline 2643void DAC960_GEM_HardwareMailboxNewCommand(void __iomem *ControllerBaseAddress) 2644{ 2645 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2646 InboundDoorBellRegister.All = 0; 2647 InboundDoorBellRegister.Write.HardwareMailboxNewCommand = true; 2648 writel(InboundDoorBellRegister.All, 2649 ControllerBaseAddress + DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2650} 2651 2652static inline 2653void DAC960_GEM_AcknowledgeHardwareMailboxStatus(void __iomem *ControllerBaseAddress) 2654{ 2655 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2656 InboundDoorBellRegister.All = 0; 2657 InboundDoorBellRegister.Write.AcknowledgeHardwareMailboxStatus = true; 2658 writel(InboundDoorBellRegister.All, 2659 ControllerBaseAddress + DAC960_GEM_InboundDoorBellRegisterClearOffset); 2660} 2661 2662static inline 2663void DAC960_GEM_GenerateInterrupt(void __iomem *ControllerBaseAddress) 2664{ 2665 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2666 InboundDoorBellRegister.All = 0; 2667 InboundDoorBellRegister.Write.GenerateInterrupt = true; 2668 writel(InboundDoorBellRegister.All, 2669 ControllerBaseAddress + DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2670} 2671 2672static inline 2673void DAC960_GEM_ControllerReset(void __iomem *ControllerBaseAddress) 2674{ 2675 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2676 InboundDoorBellRegister.All = 0; 2677 InboundDoorBellRegister.Write.ControllerReset = true; 2678 writel(InboundDoorBellRegister.All, 2679 ControllerBaseAddress + DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2680} 2681 2682static inline 2683void DAC960_GEM_MemoryMailboxNewCommand(void __iomem *ControllerBaseAddress) 2684{ 2685 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2686 InboundDoorBellRegister.All = 0; 2687 InboundDoorBellRegister.Write.MemoryMailboxNewCommand = true; 2688 writel(InboundDoorBellRegister.All, 2689 ControllerBaseAddress + DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2690} 2691 2692static inline 2693bool DAC960_GEM_HardwareMailboxFullP(void __iomem *ControllerBaseAddress) 2694{ 2695 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2696 InboundDoorBellRegister.All = 2697 readl(ControllerBaseAddress + 2698 DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2699 return InboundDoorBellRegister.Read.HardwareMailboxFull; 2700} 2701 2702static inline 2703bool DAC960_GEM_InitializationInProgressP(void __iomem *ControllerBaseAddress) 2704{ 2705 DAC960_GEM_InboundDoorBellRegister_T InboundDoorBellRegister; 2706 InboundDoorBellRegister.All = 2707 readl(ControllerBaseAddress + 2708 DAC960_GEM_InboundDoorBellRegisterReadSetOffset); 2709 return InboundDoorBellRegister.Read.InitializationInProgress; 2710} 2711 2712static inline 2713void DAC960_GEM_AcknowledgeHardwareMailboxInterrupt(void __iomem *ControllerBaseAddress) 2714{ 2715 DAC960_GEM_OutboundDoorBellRegister_T OutboundDoorBellRegister; 2716 OutboundDoorBellRegister.All = 0; 2717 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 2718 writel(OutboundDoorBellRegister.All, 2719 ControllerBaseAddress + DAC960_GEM_OutboundDoorBellRegisterClearOffset); 2720} 2721 2722static inline 2723void DAC960_GEM_AcknowledgeMemoryMailboxInterrupt(void __iomem *ControllerBaseAddress) 2724{ 2725 DAC960_GEM_OutboundDoorBellRegister_T OutboundDoorBellRegister; 2726 OutboundDoorBellRegister.All = 0; 2727 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 2728 writel(OutboundDoorBellRegister.All, 2729 ControllerBaseAddress + DAC960_GEM_OutboundDoorBellRegisterClearOffset); 2730} 2731 2732static inline 2733void DAC960_GEM_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 2734{ 2735 DAC960_GEM_OutboundDoorBellRegister_T OutboundDoorBellRegister; 2736 OutboundDoorBellRegister.All = 0; 2737 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 2738 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 2739 writel(OutboundDoorBellRegister.All, 2740 ControllerBaseAddress + DAC960_GEM_OutboundDoorBellRegisterClearOffset); 2741} 2742 2743static inline 2744bool DAC960_GEM_HardwareMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 2745{ 2746 DAC960_GEM_OutboundDoorBellRegister_T OutboundDoorBellRegister; 2747 OutboundDoorBellRegister.All = 2748 readl(ControllerBaseAddress + 2749 DAC960_GEM_OutboundDoorBellRegisterReadSetOffset); 2750 return OutboundDoorBellRegister.Read.HardwareMailboxStatusAvailable; 2751} 2752 2753static inline 2754bool DAC960_GEM_MemoryMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 2755{ 2756 DAC960_GEM_OutboundDoorBellRegister_T OutboundDoorBellRegister; 2757 OutboundDoorBellRegister.All = 2758 readl(ControllerBaseAddress + 2759 DAC960_GEM_OutboundDoorBellRegisterReadSetOffset); 2760 return OutboundDoorBellRegister.Read.MemoryMailboxStatusAvailable; 2761} 2762 2763static inline 2764void DAC960_GEM_EnableInterrupts(void __iomem *ControllerBaseAddress) 2765{ 2766 DAC960_GEM_InterruptMaskRegister_T InterruptMaskRegister; 2767 InterruptMaskRegister.All = 0; 2768 InterruptMaskRegister.Bits.HardwareMailboxInterrupt = true; 2769 InterruptMaskRegister.Bits.MemoryMailboxInterrupt = true; 2770 writel(InterruptMaskRegister.All, 2771 ControllerBaseAddress + DAC960_GEM_InterruptMaskRegisterClearOffset); 2772} 2773 2774static inline 2775void DAC960_GEM_DisableInterrupts(void __iomem *ControllerBaseAddress) 2776{ 2777 DAC960_GEM_InterruptMaskRegister_T InterruptMaskRegister; 2778 InterruptMaskRegister.All = 0; 2779 InterruptMaskRegister.Bits.HardwareMailboxInterrupt = true; 2780 InterruptMaskRegister.Bits.MemoryMailboxInterrupt = true; 2781 writel(InterruptMaskRegister.All, 2782 ControllerBaseAddress + DAC960_GEM_InterruptMaskRegisterReadSetOffset); 2783} 2784 2785static inline 2786bool DAC960_GEM_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 2787{ 2788 DAC960_GEM_InterruptMaskRegister_T InterruptMaskRegister; 2789 InterruptMaskRegister.All = 2790 readl(ControllerBaseAddress + 2791 DAC960_GEM_InterruptMaskRegisterReadSetOffset); 2792 return !(InterruptMaskRegister.Bits.HardwareMailboxInterrupt || 2793 InterruptMaskRegister.Bits.MemoryMailboxInterrupt); 2794} 2795 2796static inline 2797void DAC960_GEM_WriteCommandMailbox(DAC960_V2_CommandMailbox_T 2798 *MemoryCommandMailbox, 2799 DAC960_V2_CommandMailbox_T 2800 *CommandMailbox) 2801{ 2802 memcpy(&MemoryCommandMailbox->Words[1], &CommandMailbox->Words[1], 2803 sizeof(DAC960_V2_CommandMailbox_T) - sizeof(unsigned int)); 2804 wmb(); 2805 MemoryCommandMailbox->Words[0] = CommandMailbox->Words[0]; 2806 mb(); 2807} 2808 2809static inline 2810void DAC960_GEM_WriteHardwareMailbox(void __iomem *ControllerBaseAddress, 2811 dma_addr_t CommandMailboxDMA) 2812{ 2813 dma_addr_writeql(CommandMailboxDMA, 2814 ControllerBaseAddress + 2815 DAC960_GEM_CommandMailboxBusAddressOffset); 2816} 2817 2818static inline DAC960_V2_CommandIdentifier_T 2819DAC960_GEM_ReadCommandIdentifier(void __iomem *ControllerBaseAddress) 2820{ 2821 return readw(ControllerBaseAddress + DAC960_GEM_CommandStatusOffset); 2822} 2823 2824static inline DAC960_V2_CommandStatus_T 2825DAC960_GEM_ReadCommandStatus(void __iomem *ControllerBaseAddress) 2826{ 2827 return readw(ControllerBaseAddress + DAC960_GEM_CommandStatusOffset + 2); 2828} 2829 2830static inline bool 2831DAC960_GEM_ReadErrorStatus(void __iomem *ControllerBaseAddress, 2832 unsigned char *ErrorStatus, 2833 unsigned char *Parameter0, 2834 unsigned char *Parameter1) 2835{ 2836 DAC960_GEM_ErrorStatusRegister_T ErrorStatusRegister; 2837 ErrorStatusRegister.All = 2838 readl(ControllerBaseAddress + DAC960_GEM_ErrorStatusRegisterReadSetOffset); 2839 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 2840 ErrorStatusRegister.Bits.ErrorStatusPending = false; 2841 *ErrorStatus = ErrorStatusRegister.All; 2842 *Parameter0 = 2843 readb(ControllerBaseAddress + DAC960_GEM_CommandMailboxBusAddressOffset + 0); 2844 *Parameter1 = 2845 readb(ControllerBaseAddress + DAC960_GEM_CommandMailboxBusAddressOffset + 1); 2846 writel(0x03000000, ControllerBaseAddress + 2847 DAC960_GEM_ErrorStatusRegisterClearOffset); 2848 return true; 2849} 2850 2851/* 2852 Define the DAC960 BA Series Controller Interface Register Offsets. 2853*/ 2854 2855#define DAC960_BA_RegisterWindowSize 0x80 2856 2857typedef enum 2858{ 2859 DAC960_BA_InboundDoorBellRegisterOffset = 0x60, 2860 DAC960_BA_OutboundDoorBellRegisterOffset = 0x61, 2861 DAC960_BA_InterruptStatusRegisterOffset = 0x30, 2862 DAC960_BA_InterruptMaskRegisterOffset = 0x34, 2863 DAC960_BA_CommandMailboxBusAddressOffset = 0x50, 2864 DAC960_BA_CommandStatusOffset = 0x58, 2865 DAC960_BA_ErrorStatusRegisterOffset = 0x63 2866} 2867DAC960_BA_RegisterOffsets_T; 2868 2869 2870/* 2871 Define the structure of the DAC960 BA Series Inbound Door Bell Register. 2872*/ 2873 2874typedef union DAC960_BA_InboundDoorBellRegister 2875{ 2876 unsigned char All; 2877 struct { 2878 bool HardwareMailboxNewCommand:1; /* Bit 0 */ 2879 bool AcknowledgeHardwareMailboxStatus:1; /* Bit 1 */ 2880 bool GenerateInterrupt:1; /* Bit 2 */ 2881 bool ControllerReset:1; /* Bit 3 */ 2882 bool MemoryMailboxNewCommand:1; /* Bit 4 */ 2883 unsigned char :3; /* Bits 5-7 */ 2884 } Write; 2885 struct { 2886 bool HardwareMailboxEmpty:1; /* Bit 0 */ 2887 bool InitializationNotInProgress:1; /* Bit 1 */ 2888 unsigned char :6; /* Bits 2-7 */ 2889 } Read; 2890} 2891DAC960_BA_InboundDoorBellRegister_T; 2892 2893 2894/* 2895 Define the structure of the DAC960 BA Series Outbound Door Bell Register. 2896*/ 2897 2898typedef union DAC960_BA_OutboundDoorBellRegister 2899{ 2900 unsigned char All; 2901 struct { 2902 bool AcknowledgeHardwareMailboxInterrupt:1; /* Bit 0 */ 2903 bool AcknowledgeMemoryMailboxInterrupt:1; /* Bit 1 */ 2904 unsigned char :6; /* Bits 2-7 */ 2905 } Write; 2906 struct { 2907 bool HardwareMailboxStatusAvailable:1; /* Bit 0 */ 2908 bool MemoryMailboxStatusAvailable:1; /* Bit 1 */ 2909 unsigned char :6; /* Bits 2-7 */ 2910 } Read; 2911} 2912DAC960_BA_OutboundDoorBellRegister_T; 2913 2914 2915/* 2916 Define the structure of the DAC960 BA Series Interrupt Mask Register. 2917*/ 2918 2919typedef union DAC960_BA_InterruptMaskRegister 2920{ 2921 unsigned char All; 2922 struct { 2923 unsigned int :2; /* Bits 0-1 */ 2924 bool DisableInterrupts:1; /* Bit 2 */ 2925 bool DisableInterruptsI2O:1; /* Bit 3 */ 2926 unsigned int :4; /* Bits 4-7 */ 2927 } Bits; 2928} 2929DAC960_BA_InterruptMaskRegister_T; 2930 2931 2932/* 2933 Define the structure of the DAC960 BA Series Error Status Register. 2934*/ 2935 2936typedef union DAC960_BA_ErrorStatusRegister 2937{ 2938 unsigned char All; 2939 struct { 2940 unsigned int :2; /* Bits 0-1 */ 2941 bool ErrorStatusPending:1; /* Bit 2 */ 2942 unsigned int :5; /* Bits 3-7 */ 2943 } Bits; 2944} 2945DAC960_BA_ErrorStatusRegister_T; 2946 2947 2948/* 2949 Define inline functions to provide an abstraction for reading and writing the 2950 DAC960 BA Series Controller Interface Registers. 2951*/ 2952 2953static inline 2954void DAC960_BA_HardwareMailboxNewCommand(void __iomem *ControllerBaseAddress) 2955{ 2956 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 2957 InboundDoorBellRegister.All = 0; 2958 InboundDoorBellRegister.Write.HardwareMailboxNewCommand = true; 2959 writeb(InboundDoorBellRegister.All, 2960 ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 2961} 2962 2963static inline 2964void DAC960_BA_AcknowledgeHardwareMailboxStatus(void __iomem *ControllerBaseAddress) 2965{ 2966 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 2967 InboundDoorBellRegister.All = 0; 2968 InboundDoorBellRegister.Write.AcknowledgeHardwareMailboxStatus = true; 2969 writeb(InboundDoorBellRegister.All, 2970 ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 2971} 2972 2973static inline 2974void DAC960_BA_GenerateInterrupt(void __iomem *ControllerBaseAddress) 2975{ 2976 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 2977 InboundDoorBellRegister.All = 0; 2978 InboundDoorBellRegister.Write.GenerateInterrupt = true; 2979 writeb(InboundDoorBellRegister.All, 2980 ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 2981} 2982 2983static inline 2984void DAC960_BA_ControllerReset(void __iomem *ControllerBaseAddress) 2985{ 2986 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 2987 InboundDoorBellRegister.All = 0; 2988 InboundDoorBellRegister.Write.ControllerReset = true; 2989 writeb(InboundDoorBellRegister.All, 2990 ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 2991} 2992 2993static inline 2994void DAC960_BA_MemoryMailboxNewCommand(void __iomem *ControllerBaseAddress) 2995{ 2996 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 2997 InboundDoorBellRegister.All = 0; 2998 InboundDoorBellRegister.Write.MemoryMailboxNewCommand = true; 2999 writeb(InboundDoorBellRegister.All, 3000 ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 3001} 3002 3003static inline 3004bool DAC960_BA_HardwareMailboxFullP(void __iomem *ControllerBaseAddress) 3005{ 3006 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 3007 InboundDoorBellRegister.All = 3008 readb(ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 3009 return !InboundDoorBellRegister.Read.HardwareMailboxEmpty; 3010} 3011 3012static inline 3013bool DAC960_BA_InitializationInProgressP(void __iomem *ControllerBaseAddress) 3014{ 3015 DAC960_BA_InboundDoorBellRegister_T InboundDoorBellRegister; 3016 InboundDoorBellRegister.All = 3017 readb(ControllerBaseAddress + DAC960_BA_InboundDoorBellRegisterOffset); 3018 return !InboundDoorBellRegister.Read.InitializationNotInProgress; 3019} 3020 3021static inline 3022void DAC960_BA_AcknowledgeHardwareMailboxInterrupt(void __iomem *ControllerBaseAddress) 3023{ 3024 DAC960_BA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3025 OutboundDoorBellRegister.All = 0; 3026 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3027 writeb(OutboundDoorBellRegister.All, 3028 ControllerBaseAddress + DAC960_BA_OutboundDoorBellRegisterOffset); 3029} 3030 3031static inline 3032void DAC960_BA_AcknowledgeMemoryMailboxInterrupt(void __iomem *ControllerBaseAddress) 3033{ 3034 DAC960_BA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3035 OutboundDoorBellRegister.All = 0; 3036 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3037 writeb(OutboundDoorBellRegister.All, 3038 ControllerBaseAddress + DAC960_BA_OutboundDoorBellRegisterOffset); 3039} 3040 3041static inline 3042void DAC960_BA_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 3043{ 3044 DAC960_BA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3045 OutboundDoorBellRegister.All = 0; 3046 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3047 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3048 writeb(OutboundDoorBellRegister.All, 3049 ControllerBaseAddress + DAC960_BA_OutboundDoorBellRegisterOffset); 3050} 3051 3052static inline 3053bool DAC960_BA_HardwareMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3054{ 3055 DAC960_BA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3056 OutboundDoorBellRegister.All = 3057 readb(ControllerBaseAddress + DAC960_BA_OutboundDoorBellRegisterOffset); 3058 return OutboundDoorBellRegister.Read.HardwareMailboxStatusAvailable; 3059} 3060 3061static inline 3062bool DAC960_BA_MemoryMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3063{ 3064 DAC960_BA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3065 OutboundDoorBellRegister.All = 3066 readb(ControllerBaseAddress + DAC960_BA_OutboundDoorBellRegisterOffset); 3067 return OutboundDoorBellRegister.Read.MemoryMailboxStatusAvailable; 3068} 3069 3070static inline 3071void DAC960_BA_EnableInterrupts(void __iomem *ControllerBaseAddress) 3072{ 3073 DAC960_BA_InterruptMaskRegister_T InterruptMaskRegister; 3074 InterruptMaskRegister.All = 0xFF; 3075 InterruptMaskRegister.Bits.DisableInterrupts = false; 3076 InterruptMaskRegister.Bits.DisableInterruptsI2O = true; 3077 writeb(InterruptMaskRegister.All, 3078 ControllerBaseAddress + DAC960_BA_InterruptMaskRegisterOffset); 3079} 3080 3081static inline 3082void DAC960_BA_DisableInterrupts(void __iomem *ControllerBaseAddress) 3083{ 3084 DAC960_BA_InterruptMaskRegister_T InterruptMaskRegister; 3085 InterruptMaskRegister.All = 0xFF; 3086 InterruptMaskRegister.Bits.DisableInterrupts = true; 3087 InterruptMaskRegister.Bits.DisableInterruptsI2O = true; 3088 writeb(InterruptMaskRegister.All, 3089 ControllerBaseAddress + DAC960_BA_InterruptMaskRegisterOffset); 3090} 3091 3092static inline 3093bool DAC960_BA_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 3094{ 3095 DAC960_BA_InterruptMaskRegister_T InterruptMaskRegister; 3096 InterruptMaskRegister.All = 3097 readb(ControllerBaseAddress + DAC960_BA_InterruptMaskRegisterOffset); 3098 return !InterruptMaskRegister.Bits.DisableInterrupts; 3099} 3100 3101static inline 3102void DAC960_BA_WriteCommandMailbox(DAC960_V2_CommandMailbox_T 3103 *MemoryCommandMailbox, 3104 DAC960_V2_CommandMailbox_T 3105 *CommandMailbox) 3106{ 3107 memcpy(&MemoryCommandMailbox->Words[1], &CommandMailbox->Words[1], 3108 sizeof(DAC960_V2_CommandMailbox_T) - sizeof(unsigned int)); 3109 wmb(); 3110 MemoryCommandMailbox->Words[0] = CommandMailbox->Words[0]; 3111 mb(); 3112} 3113 3114 3115static inline 3116void DAC960_BA_WriteHardwareMailbox(void __iomem *ControllerBaseAddress, 3117 dma_addr_t CommandMailboxDMA) 3118{ 3119 dma_addr_writeql(CommandMailboxDMA, 3120 ControllerBaseAddress + 3121 DAC960_BA_CommandMailboxBusAddressOffset); 3122} 3123 3124static inline DAC960_V2_CommandIdentifier_T 3125DAC960_BA_ReadCommandIdentifier(void __iomem *ControllerBaseAddress) 3126{ 3127 return readw(ControllerBaseAddress + DAC960_BA_CommandStatusOffset); 3128} 3129 3130static inline DAC960_V2_CommandStatus_T 3131DAC960_BA_ReadCommandStatus(void __iomem *ControllerBaseAddress) 3132{ 3133 return readw(ControllerBaseAddress + DAC960_BA_CommandStatusOffset + 2); 3134} 3135 3136static inline bool 3137DAC960_BA_ReadErrorStatus(void __iomem *ControllerBaseAddress, 3138 unsigned char *ErrorStatus, 3139 unsigned char *Parameter0, 3140 unsigned char *Parameter1) 3141{ 3142 DAC960_BA_ErrorStatusRegister_T ErrorStatusRegister; 3143 ErrorStatusRegister.All = 3144 readb(ControllerBaseAddress + DAC960_BA_ErrorStatusRegisterOffset); 3145 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 3146 ErrorStatusRegister.Bits.ErrorStatusPending = false; 3147 *ErrorStatus = ErrorStatusRegister.All; 3148 *Parameter0 = 3149 readb(ControllerBaseAddress + DAC960_BA_CommandMailboxBusAddressOffset + 0); 3150 *Parameter1 = 3151 readb(ControllerBaseAddress + DAC960_BA_CommandMailboxBusAddressOffset + 1); 3152 writeb(0xFF, ControllerBaseAddress + DAC960_BA_ErrorStatusRegisterOffset); 3153 return true; 3154} 3155 3156 3157/* 3158 Define the DAC960 LP Series Controller Interface Register Offsets. 3159*/ 3160 3161#define DAC960_LP_RegisterWindowSize 0x80 3162 3163typedef enum 3164{ 3165 DAC960_LP_InboundDoorBellRegisterOffset = 0x20, 3166 DAC960_LP_OutboundDoorBellRegisterOffset = 0x2C, 3167 DAC960_LP_InterruptStatusRegisterOffset = 0x30, 3168 DAC960_LP_InterruptMaskRegisterOffset = 0x34, 3169 DAC960_LP_CommandMailboxBusAddressOffset = 0x10, 3170 DAC960_LP_CommandStatusOffset = 0x18, 3171 DAC960_LP_ErrorStatusRegisterOffset = 0x2E 3172} 3173DAC960_LP_RegisterOffsets_T; 3174 3175 3176/* 3177 Define the structure of the DAC960 LP Series Inbound Door Bell Register. 3178*/ 3179 3180typedef union DAC960_LP_InboundDoorBellRegister 3181{ 3182 unsigned char All; 3183 struct { 3184 bool HardwareMailboxNewCommand:1; /* Bit 0 */ 3185 bool AcknowledgeHardwareMailboxStatus:1; /* Bit 1 */ 3186 bool GenerateInterrupt:1; /* Bit 2 */ 3187 bool ControllerReset:1; /* Bit 3 */ 3188 bool MemoryMailboxNewCommand:1; /* Bit 4 */ 3189 unsigned char :3; /* Bits 5-7 */ 3190 } Write; 3191 struct { 3192 bool HardwareMailboxFull:1; /* Bit 0 */ 3193 bool InitializationInProgress:1; /* Bit 1 */ 3194 unsigned char :6; /* Bits 2-7 */ 3195 } Read; 3196} 3197DAC960_LP_InboundDoorBellRegister_T; 3198 3199 3200/* 3201 Define the structure of the DAC960 LP Series Outbound Door Bell Register. 3202*/ 3203 3204typedef union DAC960_LP_OutboundDoorBellRegister 3205{ 3206 unsigned char All; 3207 struct { 3208 bool AcknowledgeHardwareMailboxInterrupt:1; /* Bit 0 */ 3209 bool AcknowledgeMemoryMailboxInterrupt:1; /* Bit 1 */ 3210 unsigned char :6; /* Bits 2-7 */ 3211 } Write; 3212 struct { 3213 bool HardwareMailboxStatusAvailable:1; /* Bit 0 */ 3214 bool MemoryMailboxStatusAvailable:1; /* Bit 1 */ 3215 unsigned char :6; /* Bits 2-7 */ 3216 } Read; 3217} 3218DAC960_LP_OutboundDoorBellRegister_T; 3219 3220 3221/* 3222 Define the structure of the DAC960 LP Series Interrupt Mask Register. 3223*/ 3224 3225typedef union DAC960_LP_InterruptMaskRegister 3226{ 3227 unsigned char All; 3228 struct { 3229 unsigned int :2; /* Bits 0-1 */ 3230 bool DisableInterrupts:1; /* Bit 2 */ 3231 unsigned int :5; /* Bits 3-7 */ 3232 } Bits; 3233} 3234DAC960_LP_InterruptMaskRegister_T; 3235 3236 3237/* 3238 Define the structure of the DAC960 LP Series Error Status Register. 3239*/ 3240 3241typedef union DAC960_LP_ErrorStatusRegister 3242{ 3243 unsigned char All; 3244 struct { 3245 unsigned int :2; /* Bits 0-1 */ 3246 bool ErrorStatusPending:1; /* Bit 2 */ 3247 unsigned int :5; /* Bits 3-7 */ 3248 } Bits; 3249} 3250DAC960_LP_ErrorStatusRegister_T; 3251 3252 3253/* 3254 Define inline functions to provide an abstraction for reading and writing the 3255 DAC960 LP Series Controller Interface Registers. 3256*/ 3257 3258static inline 3259void DAC960_LP_HardwareMailboxNewCommand(void __iomem *ControllerBaseAddress) 3260{ 3261 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3262 InboundDoorBellRegister.All = 0; 3263 InboundDoorBellRegister.Write.HardwareMailboxNewCommand = true; 3264 writeb(InboundDoorBellRegister.All, 3265 ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3266} 3267 3268static inline 3269void DAC960_LP_AcknowledgeHardwareMailboxStatus(void __iomem *ControllerBaseAddress) 3270{ 3271 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3272 InboundDoorBellRegister.All = 0; 3273 InboundDoorBellRegister.Write.AcknowledgeHardwareMailboxStatus = true; 3274 writeb(InboundDoorBellRegister.All, 3275 ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3276} 3277 3278static inline 3279void DAC960_LP_GenerateInterrupt(void __iomem *ControllerBaseAddress) 3280{ 3281 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3282 InboundDoorBellRegister.All = 0; 3283 InboundDoorBellRegister.Write.GenerateInterrupt = true; 3284 writeb(InboundDoorBellRegister.All, 3285 ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3286} 3287 3288static inline 3289void DAC960_LP_ControllerReset(void __iomem *ControllerBaseAddress) 3290{ 3291 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3292 InboundDoorBellRegister.All = 0; 3293 InboundDoorBellRegister.Write.ControllerReset = true; 3294 writeb(InboundDoorBellRegister.All, 3295 ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3296} 3297 3298static inline 3299void DAC960_LP_MemoryMailboxNewCommand(void __iomem *ControllerBaseAddress) 3300{ 3301 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3302 InboundDoorBellRegister.All = 0; 3303 InboundDoorBellRegister.Write.MemoryMailboxNewCommand = true; 3304 writeb(InboundDoorBellRegister.All, 3305 ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3306} 3307 3308static inline 3309bool DAC960_LP_HardwareMailboxFullP(void __iomem *ControllerBaseAddress) 3310{ 3311 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3312 InboundDoorBellRegister.All = 3313 readb(ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3314 return InboundDoorBellRegister.Read.HardwareMailboxFull; 3315} 3316 3317static inline 3318bool DAC960_LP_InitializationInProgressP(void __iomem *ControllerBaseAddress) 3319{ 3320 DAC960_LP_InboundDoorBellRegister_T InboundDoorBellRegister; 3321 InboundDoorBellRegister.All = 3322 readb(ControllerBaseAddress + DAC960_LP_InboundDoorBellRegisterOffset); 3323 return InboundDoorBellRegister.Read.InitializationInProgress; 3324} 3325 3326static inline 3327void DAC960_LP_AcknowledgeHardwareMailboxInterrupt(void __iomem *ControllerBaseAddress) 3328{ 3329 DAC960_LP_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3330 OutboundDoorBellRegister.All = 0; 3331 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3332 writeb(OutboundDoorBellRegister.All, 3333 ControllerBaseAddress + DAC960_LP_OutboundDoorBellRegisterOffset); 3334} 3335 3336static inline 3337void DAC960_LP_AcknowledgeMemoryMailboxInterrupt(void __iomem *ControllerBaseAddress) 3338{ 3339 DAC960_LP_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3340 OutboundDoorBellRegister.All = 0; 3341 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3342 writeb(OutboundDoorBellRegister.All, 3343 ControllerBaseAddress + DAC960_LP_OutboundDoorBellRegisterOffset); 3344} 3345 3346static inline 3347void DAC960_LP_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 3348{ 3349 DAC960_LP_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3350 OutboundDoorBellRegister.All = 0; 3351 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3352 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3353 writeb(OutboundDoorBellRegister.All, 3354 ControllerBaseAddress + DAC960_LP_OutboundDoorBellRegisterOffset); 3355} 3356 3357static inline 3358bool DAC960_LP_HardwareMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3359{ 3360 DAC960_LP_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3361 OutboundDoorBellRegister.All = 3362 readb(ControllerBaseAddress + DAC960_LP_OutboundDoorBellRegisterOffset); 3363 return OutboundDoorBellRegister.Read.HardwareMailboxStatusAvailable; 3364} 3365 3366static inline 3367bool DAC960_LP_MemoryMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3368{ 3369 DAC960_LP_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3370 OutboundDoorBellRegister.All = 3371 readb(ControllerBaseAddress + DAC960_LP_OutboundDoorBellRegisterOffset); 3372 return OutboundDoorBellRegister.Read.MemoryMailboxStatusAvailable; 3373} 3374 3375static inline 3376void DAC960_LP_EnableInterrupts(void __iomem *ControllerBaseAddress) 3377{ 3378 DAC960_LP_InterruptMaskRegister_T InterruptMaskRegister; 3379 InterruptMaskRegister.All = 0xFF; 3380 InterruptMaskRegister.Bits.DisableInterrupts = false; 3381 writeb(InterruptMaskRegister.All, 3382 ControllerBaseAddress + DAC960_LP_InterruptMaskRegisterOffset); 3383} 3384 3385static inline 3386void DAC960_LP_DisableInterrupts(void __iomem *ControllerBaseAddress) 3387{ 3388 DAC960_LP_InterruptMaskRegister_T InterruptMaskRegister; 3389 InterruptMaskRegister.All = 0xFF; 3390 InterruptMaskRegister.Bits.DisableInterrupts = true; 3391 writeb(InterruptMaskRegister.All, 3392 ControllerBaseAddress + DAC960_LP_InterruptMaskRegisterOffset); 3393} 3394 3395static inline 3396bool DAC960_LP_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 3397{ 3398 DAC960_LP_InterruptMaskRegister_T InterruptMaskRegister; 3399 InterruptMaskRegister.All = 3400 readb(ControllerBaseAddress + DAC960_LP_InterruptMaskRegisterOffset); 3401 return !InterruptMaskRegister.Bits.DisableInterrupts; 3402} 3403 3404static inline 3405void DAC960_LP_WriteCommandMailbox(DAC960_V2_CommandMailbox_T 3406 *MemoryCommandMailbox, 3407 DAC960_V2_CommandMailbox_T 3408 *CommandMailbox) 3409{ 3410 memcpy(&MemoryCommandMailbox->Words[1], &CommandMailbox->Words[1], 3411 sizeof(DAC960_V2_CommandMailbox_T) - sizeof(unsigned int)); 3412 wmb(); 3413 MemoryCommandMailbox->Words[0] = CommandMailbox->Words[0]; 3414 mb(); 3415} 3416 3417static inline 3418void DAC960_LP_WriteHardwareMailbox(void __iomem *ControllerBaseAddress, 3419 dma_addr_t CommandMailboxDMA) 3420{ 3421 dma_addr_writeql(CommandMailboxDMA, 3422 ControllerBaseAddress + 3423 DAC960_LP_CommandMailboxBusAddressOffset); 3424} 3425 3426static inline DAC960_V2_CommandIdentifier_T 3427DAC960_LP_ReadCommandIdentifier(void __iomem *ControllerBaseAddress) 3428{ 3429 return readw(ControllerBaseAddress + DAC960_LP_CommandStatusOffset); 3430} 3431 3432static inline DAC960_V2_CommandStatus_T 3433DAC960_LP_ReadCommandStatus(void __iomem *ControllerBaseAddress) 3434{ 3435 return readw(ControllerBaseAddress + DAC960_LP_CommandStatusOffset + 2); 3436} 3437 3438static inline bool 3439DAC960_LP_ReadErrorStatus(void __iomem *ControllerBaseAddress, 3440 unsigned char *ErrorStatus, 3441 unsigned char *Parameter0, 3442 unsigned char *Parameter1) 3443{ 3444 DAC960_LP_ErrorStatusRegister_T ErrorStatusRegister; 3445 ErrorStatusRegister.All = 3446 readb(ControllerBaseAddress + DAC960_LP_ErrorStatusRegisterOffset); 3447 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 3448 ErrorStatusRegister.Bits.ErrorStatusPending = false; 3449 *ErrorStatus = ErrorStatusRegister.All; 3450 *Parameter0 = 3451 readb(ControllerBaseAddress + DAC960_LP_CommandMailboxBusAddressOffset + 0); 3452 *Parameter1 = 3453 readb(ControllerBaseAddress + DAC960_LP_CommandMailboxBusAddressOffset + 1); 3454 writeb(0xFF, ControllerBaseAddress + DAC960_LP_ErrorStatusRegisterOffset); 3455 return true; 3456} 3457 3458 3459/* 3460 Define the DAC960 LA Series Controller Interface Register Offsets. 3461*/ 3462 3463#define DAC960_LA_RegisterWindowSize 0x80 3464 3465typedef enum 3466{ 3467 DAC960_LA_InboundDoorBellRegisterOffset = 0x60, 3468 DAC960_LA_OutboundDoorBellRegisterOffset = 0x61, 3469 DAC960_LA_InterruptMaskRegisterOffset = 0x34, 3470 DAC960_LA_CommandOpcodeRegisterOffset = 0x50, 3471 DAC960_LA_CommandIdentifierRegisterOffset = 0x51, 3472 DAC960_LA_MailboxRegister2Offset = 0x52, 3473 DAC960_LA_MailboxRegister3Offset = 0x53, 3474 DAC960_LA_MailboxRegister4Offset = 0x54, 3475 DAC960_LA_MailboxRegister5Offset = 0x55, 3476 DAC960_LA_MailboxRegister6Offset = 0x56, 3477 DAC960_LA_MailboxRegister7Offset = 0x57, 3478 DAC960_LA_MailboxRegister8Offset = 0x58, 3479 DAC960_LA_MailboxRegister9Offset = 0x59, 3480 DAC960_LA_MailboxRegister10Offset = 0x5A, 3481 DAC960_LA_MailboxRegister11Offset = 0x5B, 3482 DAC960_LA_MailboxRegister12Offset = 0x5C, 3483 DAC960_LA_StatusCommandIdentifierRegOffset = 0x5D, 3484 DAC960_LA_StatusRegisterOffset = 0x5E, 3485 DAC960_LA_ErrorStatusRegisterOffset = 0x63 3486} 3487DAC960_LA_RegisterOffsets_T; 3488 3489 3490/* 3491 Define the structure of the DAC960 LA Series Inbound Door Bell Register. 3492*/ 3493 3494typedef union DAC960_LA_InboundDoorBellRegister 3495{ 3496 unsigned char All; 3497 struct { 3498 bool HardwareMailboxNewCommand:1; /* Bit 0 */ 3499 bool AcknowledgeHardwareMailboxStatus:1; /* Bit 1 */ 3500 bool GenerateInterrupt:1; /* Bit 2 */ 3501 bool ControllerReset:1; /* Bit 3 */ 3502 bool MemoryMailboxNewCommand:1; /* Bit 4 */ 3503 unsigned char :3; /* Bits 5-7 */ 3504 } Write; 3505 struct { 3506 bool HardwareMailboxEmpty:1; /* Bit 0 */ 3507 bool InitializationNotInProgress:1; /* Bit 1 */ 3508 unsigned char :6; /* Bits 2-7 */ 3509 } Read; 3510} 3511DAC960_LA_InboundDoorBellRegister_T; 3512 3513 3514/* 3515 Define the structure of the DAC960 LA Series Outbound Door Bell Register. 3516*/ 3517 3518typedef union DAC960_LA_OutboundDoorBellRegister 3519{ 3520 unsigned char All; 3521 struct { 3522 bool AcknowledgeHardwareMailboxInterrupt:1; /* Bit 0 */ 3523 bool AcknowledgeMemoryMailboxInterrupt:1; /* Bit 1 */ 3524 unsigned char :6; /* Bits 2-7 */ 3525 } Write; 3526 struct { 3527 bool HardwareMailboxStatusAvailable:1; /* Bit 0 */ 3528 bool MemoryMailboxStatusAvailable:1; /* Bit 1 */ 3529 unsigned char :6; /* Bits 2-7 */ 3530 } Read; 3531} 3532DAC960_LA_OutboundDoorBellRegister_T; 3533 3534 3535/* 3536 Define the structure of the DAC960 LA Series Interrupt Mask Register. 3537*/ 3538 3539typedef union DAC960_LA_InterruptMaskRegister 3540{ 3541 unsigned char All; 3542 struct { 3543 unsigned char :2; /* Bits 0-1 */ 3544 bool DisableInterrupts:1; /* Bit 2 */ 3545 unsigned char :5; /* Bits 3-7 */ 3546 } Bits; 3547} 3548DAC960_LA_InterruptMaskRegister_T; 3549 3550 3551/* 3552 Define the structure of the DAC960 LA Series Error Status Register. 3553*/ 3554 3555typedef union DAC960_LA_ErrorStatusRegister 3556{ 3557 unsigned char All; 3558 struct { 3559 unsigned int :2; /* Bits 0-1 */ 3560 bool ErrorStatusPending:1; /* Bit 2 */ 3561 unsigned int :5; /* Bits 3-7 */ 3562 } Bits; 3563} 3564DAC960_LA_ErrorStatusRegister_T; 3565 3566 3567/* 3568 Define inline functions to provide an abstraction for reading and writing the 3569 DAC960 LA Series Controller Interface Registers. 3570*/ 3571 3572static inline 3573void DAC960_LA_HardwareMailboxNewCommand(void __iomem *ControllerBaseAddress) 3574{ 3575 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3576 InboundDoorBellRegister.All = 0; 3577 InboundDoorBellRegister.Write.HardwareMailboxNewCommand = true; 3578 writeb(InboundDoorBellRegister.All, 3579 ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3580} 3581 3582static inline 3583void DAC960_LA_AcknowledgeHardwareMailboxStatus(void __iomem *ControllerBaseAddress) 3584{ 3585 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3586 InboundDoorBellRegister.All = 0; 3587 InboundDoorBellRegister.Write.AcknowledgeHardwareMailboxStatus = true; 3588 writeb(InboundDoorBellRegister.All, 3589 ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3590} 3591 3592static inline 3593void DAC960_LA_GenerateInterrupt(void __iomem *ControllerBaseAddress) 3594{ 3595 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3596 InboundDoorBellRegister.All = 0; 3597 InboundDoorBellRegister.Write.GenerateInterrupt = true; 3598 writeb(InboundDoorBellRegister.All, 3599 ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3600} 3601 3602static inline 3603void DAC960_LA_ControllerReset(void __iomem *ControllerBaseAddress) 3604{ 3605 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3606 InboundDoorBellRegister.All = 0; 3607 InboundDoorBellRegister.Write.ControllerReset = true; 3608 writeb(InboundDoorBellRegister.All, 3609 ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3610} 3611 3612static inline 3613void DAC960_LA_MemoryMailboxNewCommand(void __iomem *ControllerBaseAddress) 3614{ 3615 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3616 InboundDoorBellRegister.All = 0; 3617 InboundDoorBellRegister.Write.MemoryMailboxNewCommand = true; 3618 writeb(InboundDoorBellRegister.All, 3619 ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3620} 3621 3622static inline 3623bool DAC960_LA_HardwareMailboxFullP(void __iomem *ControllerBaseAddress) 3624{ 3625 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3626 InboundDoorBellRegister.All = 3627 readb(ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3628 return !InboundDoorBellRegister.Read.HardwareMailboxEmpty; 3629} 3630 3631static inline 3632bool DAC960_LA_InitializationInProgressP(void __iomem *ControllerBaseAddress) 3633{ 3634 DAC960_LA_InboundDoorBellRegister_T InboundDoorBellRegister; 3635 InboundDoorBellRegister.All = 3636 readb(ControllerBaseAddress + DAC960_LA_InboundDoorBellRegisterOffset); 3637 return !InboundDoorBellRegister.Read.InitializationNotInProgress; 3638} 3639 3640static inline 3641void DAC960_LA_AcknowledgeHardwareMailboxInterrupt(void __iomem *ControllerBaseAddress) 3642{ 3643 DAC960_LA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3644 OutboundDoorBellRegister.All = 0; 3645 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3646 writeb(OutboundDoorBellRegister.All, 3647 ControllerBaseAddress + DAC960_LA_OutboundDoorBellRegisterOffset); 3648} 3649 3650static inline 3651void DAC960_LA_AcknowledgeMemoryMailboxInterrupt(void __iomem *ControllerBaseAddress) 3652{ 3653 DAC960_LA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3654 OutboundDoorBellRegister.All = 0; 3655 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3656 writeb(OutboundDoorBellRegister.All, 3657 ControllerBaseAddress + DAC960_LA_OutboundDoorBellRegisterOffset); 3658} 3659 3660static inline 3661void DAC960_LA_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 3662{ 3663 DAC960_LA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3664 OutboundDoorBellRegister.All = 0; 3665 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3666 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3667 writeb(OutboundDoorBellRegister.All, 3668 ControllerBaseAddress + DAC960_LA_OutboundDoorBellRegisterOffset); 3669} 3670 3671static inline 3672bool DAC960_LA_HardwareMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3673{ 3674 DAC960_LA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3675 OutboundDoorBellRegister.All = 3676 readb(ControllerBaseAddress + DAC960_LA_OutboundDoorBellRegisterOffset); 3677 return OutboundDoorBellRegister.Read.HardwareMailboxStatusAvailable; 3678} 3679 3680static inline 3681bool DAC960_LA_MemoryMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3682{ 3683 DAC960_LA_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3684 OutboundDoorBellRegister.All = 3685 readb(ControllerBaseAddress + DAC960_LA_OutboundDoorBellRegisterOffset); 3686 return OutboundDoorBellRegister.Read.MemoryMailboxStatusAvailable; 3687} 3688 3689static inline 3690void DAC960_LA_EnableInterrupts(void __iomem *ControllerBaseAddress) 3691{ 3692 DAC960_LA_InterruptMaskRegister_T InterruptMaskRegister; 3693 InterruptMaskRegister.All = 0xFF; 3694 InterruptMaskRegister.Bits.DisableInterrupts = false; 3695 writeb(InterruptMaskRegister.All, 3696 ControllerBaseAddress + DAC960_LA_InterruptMaskRegisterOffset); 3697} 3698 3699static inline 3700void DAC960_LA_DisableInterrupts(void __iomem *ControllerBaseAddress) 3701{ 3702 DAC960_LA_InterruptMaskRegister_T InterruptMaskRegister; 3703 InterruptMaskRegister.All = 0xFF; 3704 InterruptMaskRegister.Bits.DisableInterrupts = true; 3705 writeb(InterruptMaskRegister.All, 3706 ControllerBaseAddress + DAC960_LA_InterruptMaskRegisterOffset); 3707} 3708 3709static inline 3710bool DAC960_LA_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 3711{ 3712 DAC960_LA_InterruptMaskRegister_T InterruptMaskRegister; 3713 InterruptMaskRegister.All = 3714 readb(ControllerBaseAddress + DAC960_LA_InterruptMaskRegisterOffset); 3715 return !InterruptMaskRegister.Bits.DisableInterrupts; 3716} 3717 3718static inline 3719void DAC960_LA_WriteCommandMailbox(DAC960_V1_CommandMailbox_T 3720 *MemoryCommandMailbox, 3721 DAC960_V1_CommandMailbox_T 3722 *CommandMailbox) 3723{ 3724 MemoryCommandMailbox->Words[1] = CommandMailbox->Words[1]; 3725 MemoryCommandMailbox->Words[2] = CommandMailbox->Words[2]; 3726 MemoryCommandMailbox->Words[3] = CommandMailbox->Words[3]; 3727 wmb(); 3728 MemoryCommandMailbox->Words[0] = CommandMailbox->Words[0]; 3729 mb(); 3730} 3731 3732static inline 3733void DAC960_LA_WriteHardwareMailbox(void __iomem *ControllerBaseAddress, 3734 DAC960_V1_CommandMailbox_T *CommandMailbox) 3735{ 3736 writel(CommandMailbox->Words[0], 3737 ControllerBaseAddress + DAC960_LA_CommandOpcodeRegisterOffset); 3738 writel(CommandMailbox->Words[1], 3739 ControllerBaseAddress + DAC960_LA_MailboxRegister4Offset); 3740 writel(CommandMailbox->Words[2], 3741 ControllerBaseAddress + DAC960_LA_MailboxRegister8Offset); 3742 writeb(CommandMailbox->Bytes[12], 3743 ControllerBaseAddress + DAC960_LA_MailboxRegister12Offset); 3744} 3745 3746static inline DAC960_V1_CommandIdentifier_T 3747DAC960_LA_ReadStatusCommandIdentifier(void __iomem *ControllerBaseAddress) 3748{ 3749 return readb(ControllerBaseAddress 3750 + DAC960_LA_StatusCommandIdentifierRegOffset); 3751} 3752 3753static inline DAC960_V1_CommandStatus_T 3754DAC960_LA_ReadStatusRegister(void __iomem *ControllerBaseAddress) 3755{ 3756 return readw(ControllerBaseAddress + DAC960_LA_StatusRegisterOffset); 3757} 3758 3759static inline bool 3760DAC960_LA_ReadErrorStatus(void __iomem *ControllerBaseAddress, 3761 unsigned char *ErrorStatus, 3762 unsigned char *Parameter0, 3763 unsigned char *Parameter1) 3764{ 3765 DAC960_LA_ErrorStatusRegister_T ErrorStatusRegister; 3766 ErrorStatusRegister.All = 3767 readb(ControllerBaseAddress + DAC960_LA_ErrorStatusRegisterOffset); 3768 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 3769 ErrorStatusRegister.Bits.ErrorStatusPending = false; 3770 *ErrorStatus = ErrorStatusRegister.All; 3771 *Parameter0 = 3772 readb(ControllerBaseAddress + DAC960_LA_CommandOpcodeRegisterOffset); 3773 *Parameter1 = 3774 readb(ControllerBaseAddress + DAC960_LA_CommandIdentifierRegisterOffset); 3775 writeb(0xFF, ControllerBaseAddress + DAC960_LA_ErrorStatusRegisterOffset); 3776 return true; 3777} 3778 3779/* 3780 Define the DAC960 PG Series Controller Interface Register Offsets. 3781*/ 3782 3783#define DAC960_PG_RegisterWindowSize 0x2000 3784 3785typedef enum 3786{ 3787 DAC960_PG_InboundDoorBellRegisterOffset = 0x0020, 3788 DAC960_PG_OutboundDoorBellRegisterOffset = 0x002C, 3789 DAC960_PG_InterruptMaskRegisterOffset = 0x0034, 3790 DAC960_PG_CommandOpcodeRegisterOffset = 0x1000, 3791 DAC960_PG_CommandIdentifierRegisterOffset = 0x1001, 3792 DAC960_PG_MailboxRegister2Offset = 0x1002, 3793 DAC960_PG_MailboxRegister3Offset = 0x1003, 3794 DAC960_PG_MailboxRegister4Offset = 0x1004, 3795 DAC960_PG_MailboxRegister5Offset = 0x1005, 3796 DAC960_PG_MailboxRegister6Offset = 0x1006, 3797 DAC960_PG_MailboxRegister7Offset = 0x1007, 3798 DAC960_PG_MailboxRegister8Offset = 0x1008, 3799 DAC960_PG_MailboxRegister9Offset = 0x1009, 3800 DAC960_PG_MailboxRegister10Offset = 0x100A, 3801 DAC960_PG_MailboxRegister11Offset = 0x100B, 3802 DAC960_PG_MailboxRegister12Offset = 0x100C, 3803 DAC960_PG_StatusCommandIdentifierRegOffset = 0x1018, 3804 DAC960_PG_StatusRegisterOffset = 0x101A, 3805 DAC960_PG_ErrorStatusRegisterOffset = 0x103F 3806} 3807DAC960_PG_RegisterOffsets_T; 3808 3809 3810/* 3811 Define the structure of the DAC960 PG Series Inbound Door Bell Register. 3812*/ 3813 3814typedef union DAC960_PG_InboundDoorBellRegister 3815{ 3816 unsigned int All; 3817 struct { 3818 bool HardwareMailboxNewCommand:1; /* Bit 0 */ 3819 bool AcknowledgeHardwareMailboxStatus:1; /* Bit 1 */ 3820 bool GenerateInterrupt:1; /* Bit 2 */ 3821 bool ControllerReset:1; /* Bit 3 */ 3822 bool MemoryMailboxNewCommand:1; /* Bit 4 */ 3823 unsigned int :27; /* Bits 5-31 */ 3824 } Write; 3825 struct { 3826 bool HardwareMailboxFull:1; /* Bit 0 */ 3827 bool InitializationInProgress:1; /* Bit 1 */ 3828 unsigned int :30; /* Bits 2-31 */ 3829 } Read; 3830} 3831DAC960_PG_InboundDoorBellRegister_T; 3832 3833 3834/* 3835 Define the structure of the DAC960 PG Series Outbound Door Bell Register. 3836*/ 3837 3838typedef union DAC960_PG_OutboundDoorBellRegister 3839{ 3840 unsigned int All; 3841 struct { 3842 bool AcknowledgeHardwareMailboxInterrupt:1; /* Bit 0 */ 3843 bool AcknowledgeMemoryMailboxInterrupt:1; /* Bit 1 */ 3844 unsigned int :30; /* Bits 2-31 */ 3845 } Write; 3846 struct { 3847 bool HardwareMailboxStatusAvailable:1; /* Bit 0 */ 3848 bool MemoryMailboxStatusAvailable:1; /* Bit 1 */ 3849 unsigned int :30; /* Bits 2-31 */ 3850 } Read; 3851} 3852DAC960_PG_OutboundDoorBellRegister_T; 3853 3854 3855/* 3856 Define the structure of the DAC960 PG Series Interrupt Mask Register. 3857*/ 3858 3859typedef union DAC960_PG_InterruptMaskRegister 3860{ 3861 unsigned int All; 3862 struct { 3863 unsigned int MessageUnitInterruptMask1:2; /* Bits 0-1 */ 3864 bool DisableInterrupts:1; /* Bit 2 */ 3865 unsigned int MessageUnitInterruptMask2:5; /* Bits 3-7 */ 3866 unsigned int Reserved0:24; /* Bits 8-31 */ 3867 } Bits; 3868} 3869DAC960_PG_InterruptMaskRegister_T; 3870 3871 3872/* 3873 Define the structure of the DAC960 PG Series Error Status Register. 3874*/ 3875 3876typedef union DAC960_PG_ErrorStatusRegister 3877{ 3878 unsigned char All; 3879 struct { 3880 unsigned int :2; /* Bits 0-1 */ 3881 bool ErrorStatusPending:1; /* Bit 2 */ 3882 unsigned int :5; /* Bits 3-7 */ 3883 } Bits; 3884} 3885DAC960_PG_ErrorStatusRegister_T; 3886 3887 3888/* 3889 Define inline functions to provide an abstraction for reading and writing the 3890 DAC960 PG Series Controller Interface Registers. 3891*/ 3892 3893static inline 3894void DAC960_PG_HardwareMailboxNewCommand(void __iomem *ControllerBaseAddress) 3895{ 3896 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3897 InboundDoorBellRegister.All = 0; 3898 InboundDoorBellRegister.Write.HardwareMailboxNewCommand = true; 3899 writel(InboundDoorBellRegister.All, 3900 ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3901} 3902 3903static inline 3904void DAC960_PG_AcknowledgeHardwareMailboxStatus(void __iomem *ControllerBaseAddress) 3905{ 3906 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3907 InboundDoorBellRegister.All = 0; 3908 InboundDoorBellRegister.Write.AcknowledgeHardwareMailboxStatus = true; 3909 writel(InboundDoorBellRegister.All, 3910 ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3911} 3912 3913static inline 3914void DAC960_PG_GenerateInterrupt(void __iomem *ControllerBaseAddress) 3915{ 3916 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3917 InboundDoorBellRegister.All = 0; 3918 InboundDoorBellRegister.Write.GenerateInterrupt = true; 3919 writel(InboundDoorBellRegister.All, 3920 ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3921} 3922 3923static inline 3924void DAC960_PG_ControllerReset(void __iomem *ControllerBaseAddress) 3925{ 3926 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3927 InboundDoorBellRegister.All = 0; 3928 InboundDoorBellRegister.Write.ControllerReset = true; 3929 writel(InboundDoorBellRegister.All, 3930 ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3931} 3932 3933static inline 3934void DAC960_PG_MemoryMailboxNewCommand(void __iomem *ControllerBaseAddress) 3935{ 3936 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3937 InboundDoorBellRegister.All = 0; 3938 InboundDoorBellRegister.Write.MemoryMailboxNewCommand = true; 3939 writel(InboundDoorBellRegister.All, 3940 ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3941} 3942 3943static inline 3944bool DAC960_PG_HardwareMailboxFullP(void __iomem *ControllerBaseAddress) 3945{ 3946 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3947 InboundDoorBellRegister.All = 3948 readl(ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3949 return InboundDoorBellRegister.Read.HardwareMailboxFull; 3950} 3951 3952static inline 3953bool DAC960_PG_InitializationInProgressP(void __iomem *ControllerBaseAddress) 3954{ 3955 DAC960_PG_InboundDoorBellRegister_T InboundDoorBellRegister; 3956 InboundDoorBellRegister.All = 3957 readl(ControllerBaseAddress + DAC960_PG_InboundDoorBellRegisterOffset); 3958 return InboundDoorBellRegister.Read.InitializationInProgress; 3959} 3960 3961static inline 3962void DAC960_PG_AcknowledgeHardwareMailboxInterrupt(void __iomem *ControllerBaseAddress) 3963{ 3964 DAC960_PG_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3965 OutboundDoorBellRegister.All = 0; 3966 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3967 writel(OutboundDoorBellRegister.All, 3968 ControllerBaseAddress + DAC960_PG_OutboundDoorBellRegisterOffset); 3969} 3970 3971static inline 3972void DAC960_PG_AcknowledgeMemoryMailboxInterrupt(void __iomem *ControllerBaseAddress) 3973{ 3974 DAC960_PG_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3975 OutboundDoorBellRegister.All = 0; 3976 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3977 writel(OutboundDoorBellRegister.All, 3978 ControllerBaseAddress + DAC960_PG_OutboundDoorBellRegisterOffset); 3979} 3980 3981static inline 3982void DAC960_PG_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 3983{ 3984 DAC960_PG_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3985 OutboundDoorBellRegister.All = 0; 3986 OutboundDoorBellRegister.Write.AcknowledgeHardwareMailboxInterrupt = true; 3987 OutboundDoorBellRegister.Write.AcknowledgeMemoryMailboxInterrupt = true; 3988 writel(OutboundDoorBellRegister.All, 3989 ControllerBaseAddress + DAC960_PG_OutboundDoorBellRegisterOffset); 3990} 3991 3992static inline 3993bool DAC960_PG_HardwareMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 3994{ 3995 DAC960_PG_OutboundDoorBellRegister_T OutboundDoorBellRegister; 3996 OutboundDoorBellRegister.All = 3997 readl(ControllerBaseAddress + DAC960_PG_OutboundDoorBellRegisterOffset); 3998 return OutboundDoorBellRegister.Read.HardwareMailboxStatusAvailable; 3999} 4000 4001static inline 4002bool DAC960_PG_MemoryMailboxStatusAvailableP(void __iomem *ControllerBaseAddress) 4003{ 4004 DAC960_PG_OutboundDoorBellRegister_T OutboundDoorBellRegister; 4005 OutboundDoorBellRegister.All = 4006 readl(ControllerBaseAddress + DAC960_PG_OutboundDoorBellRegisterOffset); 4007 return OutboundDoorBellRegister.Read.MemoryMailboxStatusAvailable; 4008} 4009 4010static inline 4011void DAC960_PG_EnableInterrupts(void __iomem *ControllerBaseAddress) 4012{ 4013 DAC960_PG_InterruptMaskRegister_T InterruptMaskRegister; 4014 InterruptMaskRegister.All = 0; 4015 InterruptMaskRegister.Bits.MessageUnitInterruptMask1 = 0x3; 4016 InterruptMaskRegister.Bits.DisableInterrupts = false; 4017 InterruptMaskRegister.Bits.MessageUnitInterruptMask2 = 0x1F; 4018 writel(InterruptMaskRegister.All, 4019 ControllerBaseAddress + DAC960_PG_InterruptMaskRegisterOffset); 4020} 4021 4022static inline 4023void DAC960_PG_DisableInterrupts(void __iomem *ControllerBaseAddress) 4024{ 4025 DAC960_PG_InterruptMaskRegister_T InterruptMaskRegister; 4026 InterruptMaskRegister.All = 0; 4027 InterruptMaskRegister.Bits.MessageUnitInterruptMask1 = 0x3; 4028 InterruptMaskRegister.Bits.DisableInterrupts = true; 4029 InterruptMaskRegister.Bits.MessageUnitInterruptMask2 = 0x1F; 4030 writel(InterruptMaskRegister.All, 4031 ControllerBaseAddress + DAC960_PG_InterruptMaskRegisterOffset); 4032} 4033 4034static inline 4035bool DAC960_PG_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 4036{ 4037 DAC960_PG_InterruptMaskRegister_T InterruptMaskRegister; 4038 InterruptMaskRegister.All = 4039 readl(ControllerBaseAddress + DAC960_PG_InterruptMaskRegisterOffset); 4040 return !InterruptMaskRegister.Bits.DisableInterrupts; 4041} 4042 4043static inline 4044void DAC960_PG_WriteCommandMailbox(DAC960_V1_CommandMailbox_T 4045 *MemoryCommandMailbox, 4046 DAC960_V1_CommandMailbox_T 4047 *CommandMailbox) 4048{ 4049 MemoryCommandMailbox->Words[1] = CommandMailbox->Words[1]; 4050 MemoryCommandMailbox->Words[2] = CommandMailbox->Words[2]; 4051 MemoryCommandMailbox->Words[3] = CommandMailbox->Words[3]; 4052 wmb(); 4053 MemoryCommandMailbox->Words[0] = CommandMailbox->Words[0]; 4054 mb(); 4055} 4056 4057static inline 4058void DAC960_PG_WriteHardwareMailbox(void __iomem *ControllerBaseAddress, 4059 DAC960_V1_CommandMailbox_T *CommandMailbox) 4060{ 4061 writel(CommandMailbox->Words[0], 4062 ControllerBaseAddress + DAC960_PG_CommandOpcodeRegisterOffset); 4063 writel(CommandMailbox->Words[1], 4064 ControllerBaseAddress + DAC960_PG_MailboxRegister4Offset); 4065 writel(CommandMailbox->Words[2], 4066 ControllerBaseAddress + DAC960_PG_MailboxRegister8Offset); 4067 writeb(CommandMailbox->Bytes[12], 4068 ControllerBaseAddress + DAC960_PG_MailboxRegister12Offset); 4069} 4070 4071static inline DAC960_V1_CommandIdentifier_T 4072DAC960_PG_ReadStatusCommandIdentifier(void __iomem *ControllerBaseAddress) 4073{ 4074 return readb(ControllerBaseAddress 4075 + DAC960_PG_StatusCommandIdentifierRegOffset); 4076} 4077 4078static inline DAC960_V1_CommandStatus_T 4079DAC960_PG_ReadStatusRegister(void __iomem *ControllerBaseAddress) 4080{ 4081 return readw(ControllerBaseAddress + DAC960_PG_StatusRegisterOffset); 4082} 4083 4084static inline bool 4085DAC960_PG_ReadErrorStatus(void __iomem *ControllerBaseAddress, 4086 unsigned char *ErrorStatus, 4087 unsigned char *Parameter0, 4088 unsigned char *Parameter1) 4089{ 4090 DAC960_PG_ErrorStatusRegister_T ErrorStatusRegister; 4091 ErrorStatusRegister.All = 4092 readb(ControllerBaseAddress + DAC960_PG_ErrorStatusRegisterOffset); 4093 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 4094 ErrorStatusRegister.Bits.ErrorStatusPending = false; 4095 *ErrorStatus = ErrorStatusRegister.All; 4096 *Parameter0 = 4097 readb(ControllerBaseAddress + DAC960_PG_CommandOpcodeRegisterOffset); 4098 *Parameter1 = 4099 readb(ControllerBaseAddress + DAC960_PG_CommandIdentifierRegisterOffset); 4100 writeb(0, ControllerBaseAddress + DAC960_PG_ErrorStatusRegisterOffset); 4101 return true; 4102} 4103 4104/* 4105 Define the DAC960 PD Series Controller Interface Register Offsets. 4106*/ 4107 4108#define DAC960_PD_RegisterWindowSize 0x80 4109 4110typedef enum 4111{ 4112 DAC960_PD_CommandOpcodeRegisterOffset = 0x00, 4113 DAC960_PD_CommandIdentifierRegisterOffset = 0x01, 4114 DAC960_PD_MailboxRegister2Offset = 0x02, 4115 DAC960_PD_MailboxRegister3Offset = 0x03, 4116 DAC960_PD_MailboxRegister4Offset = 0x04, 4117 DAC960_PD_MailboxRegister5Offset = 0x05, 4118 DAC960_PD_MailboxRegister6Offset = 0x06, 4119 DAC960_PD_MailboxRegister7Offset = 0x07, 4120 DAC960_PD_MailboxRegister8Offset = 0x08, 4121 DAC960_PD_MailboxRegister9Offset = 0x09, 4122 DAC960_PD_MailboxRegister10Offset = 0x0A, 4123 DAC960_PD_MailboxRegister11Offset = 0x0B, 4124 DAC960_PD_MailboxRegister12Offset = 0x0C, 4125 DAC960_PD_StatusCommandIdentifierRegOffset = 0x0D, 4126 DAC960_PD_StatusRegisterOffset = 0x0E, 4127 DAC960_PD_ErrorStatusRegisterOffset = 0x3F, 4128 DAC960_PD_InboundDoorBellRegisterOffset = 0x40, 4129 DAC960_PD_OutboundDoorBellRegisterOffset = 0x41, 4130 DAC960_PD_InterruptEnableRegisterOffset = 0x43 4131} 4132DAC960_PD_RegisterOffsets_T; 4133 4134 4135/* 4136 Define the structure of the DAC960 PD Series Inbound Door Bell Register. 4137*/ 4138 4139typedef union DAC960_PD_InboundDoorBellRegister 4140{ 4141 unsigned char All; 4142 struct { 4143 bool NewCommand:1; /* Bit 0 */ 4144 bool AcknowledgeStatus:1; /* Bit 1 */ 4145 bool GenerateInterrupt:1; /* Bit 2 */ 4146 bool ControllerReset:1; /* Bit 3 */ 4147 unsigned char :4; /* Bits 4-7 */ 4148 } Write; 4149 struct { 4150 bool MailboxFull:1; /* Bit 0 */ 4151 bool InitializationInProgress:1; /* Bit 1 */ 4152 unsigned char :6; /* Bits 2-7 */ 4153 } Read; 4154} 4155DAC960_PD_InboundDoorBellRegister_T; 4156 4157 4158/* 4159 Define the structure of the DAC960 PD Series Outbound Door Bell Register. 4160*/ 4161 4162typedef union DAC960_PD_OutboundDoorBellRegister 4163{ 4164 unsigned char All; 4165 struct { 4166 bool AcknowledgeInterrupt:1; /* Bit 0 */ 4167 unsigned char :7; /* Bits 1-7 */ 4168 } Write; 4169 struct { 4170 bool StatusAvailable:1; /* Bit 0 */ 4171 unsigned char :7; /* Bits 1-7 */ 4172 } Read; 4173} 4174DAC960_PD_OutboundDoorBellRegister_T; 4175 4176 4177/* 4178 Define the structure of the DAC960 PD Series Interrupt Enable Register. 4179*/ 4180 4181typedef union DAC960_PD_InterruptEnableRegister 4182{ 4183 unsigned char All; 4184 struct { 4185 bool EnableInterrupts:1; /* Bit 0 */ 4186 unsigned char :7; /* Bits 1-7 */ 4187 } Bits; 4188} 4189DAC960_PD_InterruptEnableRegister_T; 4190 4191 4192/* 4193 Define the structure of the DAC960 PD Series Error Status Register. 4194*/ 4195 4196typedef union DAC960_PD_ErrorStatusRegister 4197{ 4198 unsigned char All; 4199 struct { 4200 unsigned int :2; /* Bits 0-1 */ 4201 bool ErrorStatusPending:1; /* Bit 2 */ 4202 unsigned int :5; /* Bits 3-7 */ 4203 } Bits; 4204} 4205DAC960_PD_ErrorStatusRegister_T; 4206 4207 4208/* 4209 Define inline functions to provide an abstraction for reading and writing the 4210 DAC960 PD Series Controller Interface Registers. 4211*/ 4212 4213static inline 4214void DAC960_PD_NewCommand(void __iomem *ControllerBaseAddress) 4215{ 4216 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4217 InboundDoorBellRegister.All = 0; 4218 InboundDoorBellRegister.Write.NewCommand = true; 4219 writeb(InboundDoorBellRegister.All, 4220 ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4221} 4222 4223static inline 4224void DAC960_PD_AcknowledgeStatus(void __iomem *ControllerBaseAddress) 4225{ 4226 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4227 InboundDoorBellRegister.All = 0; 4228 InboundDoorBellRegister.Write.AcknowledgeStatus = true; 4229 writeb(InboundDoorBellRegister.All, 4230 ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4231} 4232 4233static inline 4234void DAC960_PD_GenerateInterrupt(void __iomem *ControllerBaseAddress) 4235{ 4236 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4237 InboundDoorBellRegister.All = 0; 4238 InboundDoorBellRegister.Write.GenerateInterrupt = true; 4239 writeb(InboundDoorBellRegister.All, 4240 ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4241} 4242 4243static inline 4244void DAC960_PD_ControllerReset(void __iomem *ControllerBaseAddress) 4245{ 4246 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4247 InboundDoorBellRegister.All = 0; 4248 InboundDoorBellRegister.Write.ControllerReset = true; 4249 writeb(InboundDoorBellRegister.All, 4250 ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4251} 4252 4253static inline 4254bool DAC960_PD_MailboxFullP(void __iomem *ControllerBaseAddress) 4255{ 4256 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4257 InboundDoorBellRegister.All = 4258 readb(ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4259 return InboundDoorBellRegister.Read.MailboxFull; 4260} 4261 4262static inline 4263bool DAC960_PD_InitializationInProgressP(void __iomem *ControllerBaseAddress) 4264{ 4265 DAC960_PD_InboundDoorBellRegister_T InboundDoorBellRegister; 4266 InboundDoorBellRegister.All = 4267 readb(ControllerBaseAddress + DAC960_PD_InboundDoorBellRegisterOffset); 4268 return InboundDoorBellRegister.Read.InitializationInProgress; 4269} 4270 4271static inline 4272void DAC960_PD_AcknowledgeInterrupt(void __iomem *ControllerBaseAddress) 4273{ 4274 DAC960_PD_OutboundDoorBellRegister_T OutboundDoorBellRegister; 4275 OutboundDoorBellRegister.All = 0; 4276 OutboundDoorBellRegister.Write.AcknowledgeInterrupt = true; 4277 writeb(OutboundDoorBellRegister.All, 4278 ControllerBaseAddress + DAC960_PD_OutboundDoorBellRegisterOffset); 4279} 4280 4281static inline 4282bool DAC960_PD_StatusAvailableP(void __iomem *ControllerBaseAddress) 4283{ 4284 DAC960_PD_OutboundDoorBellRegister_T OutboundDoorBellRegister; 4285 OutboundDoorBellRegister.All = 4286 readb(ControllerBaseAddress + DAC960_PD_OutboundDoorBellRegisterOffset); 4287 return OutboundDoorBellRegister.Read.StatusAvailable; 4288} 4289 4290static inline 4291void DAC960_PD_EnableInterrupts(void __iomem *ControllerBaseAddress) 4292{ 4293 DAC960_PD_InterruptEnableRegister_T InterruptEnableRegister; 4294 InterruptEnableRegister.All = 0; 4295 InterruptEnableRegister.Bits.EnableInterrupts = true; 4296 writeb(InterruptEnableRegister.All, 4297 ControllerBaseAddress + DAC960_PD_InterruptEnableRegisterOffset); 4298} 4299 4300static inline 4301void DAC960_PD_DisableInterrupts(void __iomem *ControllerBaseAddress) 4302{ 4303 DAC960_PD_InterruptEnableRegister_T InterruptEnableRegister; 4304 InterruptEnableRegister.All = 0; 4305 InterruptEnableRegister.Bits.EnableInterrupts = false; 4306 writeb(InterruptEnableRegister.All, 4307 ControllerBaseAddress + DAC960_PD_InterruptEnableRegisterOffset); 4308} 4309 4310static inline 4311bool DAC960_PD_InterruptsEnabledP(void __iomem *ControllerBaseAddress) 4312{ 4313 DAC960_PD_InterruptEnableRegister_T InterruptEnableRegister; 4314 InterruptEnableRegister.All = 4315 readb(ControllerBaseAddress + DAC960_PD_InterruptEnableRegisterOffset); 4316 return InterruptEnableRegister.Bits.EnableInterrupts; 4317} 4318 4319static inline 4320void DAC960_PD_WriteCommandMailbox(void __iomem *ControllerBaseAddress, 4321 DAC960_V1_CommandMailbox_T *CommandMailbox) 4322{ 4323 writel(CommandMailbox->Words[0], 4324 ControllerBaseAddress + DAC960_PD_CommandOpcodeRegisterOffset); 4325 writel(CommandMailbox->Words[1], 4326 ControllerBaseAddress + DAC960_PD_MailboxRegister4Offset); 4327 writel(CommandMailbox->Words[2], 4328 ControllerBaseAddress + DAC960_PD_MailboxRegister8Offset); 4329 writeb(CommandMailbox->Bytes[12], 4330 ControllerBaseAddress + DAC960_PD_MailboxRegister12Offset); 4331} 4332 4333static inline DAC960_V1_CommandIdentifier_T 4334DAC960_PD_ReadStatusCommandIdentifier(void __iomem *ControllerBaseAddress) 4335{ 4336 return readb(ControllerBaseAddress 4337 + DAC960_PD_StatusCommandIdentifierRegOffset); 4338} 4339 4340static inline DAC960_V1_CommandStatus_T 4341DAC960_PD_ReadStatusRegister(void __iomem *ControllerBaseAddress) 4342{ 4343 return readw(ControllerBaseAddress + DAC960_PD_StatusRegisterOffset); 4344} 4345 4346static inline bool 4347DAC960_PD_ReadErrorStatus(void __iomem *ControllerBaseAddress, 4348 unsigned char *ErrorStatus, 4349 unsigned char *Parameter0, 4350 unsigned char *Parameter1) 4351{ 4352 DAC960_PD_ErrorStatusRegister_T ErrorStatusRegister; 4353 ErrorStatusRegister.All = 4354 readb(ControllerBaseAddress + DAC960_PD_ErrorStatusRegisterOffset); 4355 if (!ErrorStatusRegister.Bits.ErrorStatusPending) return false; 4356 ErrorStatusRegister.Bits.ErrorStatusPending = false; 4357 *ErrorStatus = ErrorStatusRegister.All; 4358 *Parameter0 = 4359 readb(ControllerBaseAddress + DAC960_PD_CommandOpcodeRegisterOffset); 4360 *Parameter1 = 4361 readb(ControllerBaseAddress + DAC960_PD_CommandIdentifierRegisterOffset); 4362 writeb(0, ControllerBaseAddress + DAC960_PD_ErrorStatusRegisterOffset); 4363 return true; 4364} 4365 4366static inline void DAC960_P_To_PD_TranslateEnquiry(void *Enquiry) 4367{ 4368 memcpy(Enquiry + 132, Enquiry + 36, 64); 4369 memset(Enquiry + 36, 0, 96); 4370} 4371 4372static inline void DAC960_P_To_PD_TranslateDeviceState(void *DeviceState) 4373{ 4374 memcpy(DeviceState + 2, DeviceState + 3, 1); 4375 memmove(DeviceState + 4, DeviceState + 5, 2); 4376 memmove(DeviceState + 6, DeviceState + 8, 4); 4377} 4378 4379static inline 4380void DAC960_PD_To_P_TranslateReadWriteCommand(DAC960_V1_CommandMailbox_T 4381 *CommandMailbox) 4382{ 4383 int LogicalDriveNumber = CommandMailbox->Type5.LD.LogicalDriveNumber; 4384 CommandMailbox->Bytes[3] &= 0x7; 4385 CommandMailbox->Bytes[3] |= CommandMailbox->Bytes[7] << 6; 4386 CommandMailbox->Bytes[7] = LogicalDriveNumber; 4387} 4388 4389static inline 4390void DAC960_P_To_PD_TranslateReadWriteCommand(DAC960_V1_CommandMailbox_T 4391 *CommandMailbox) 4392{ 4393 int LogicalDriveNumber = CommandMailbox->Bytes[7]; 4394 CommandMailbox->Bytes[7] = CommandMailbox->Bytes[3] >> 6; 4395 CommandMailbox->Bytes[3] &= 0x7; 4396 CommandMailbox->Bytes[3] |= LogicalDriveNumber << 3; 4397} 4398 4399 4400/* 4401 Define prototypes for the forward referenced DAC960 Driver Internal Functions. 4402*/ 4403 4404static void DAC960_FinalizeController(DAC960_Controller_T *); 4405static void DAC960_V1_QueueReadWriteCommand(DAC960_Command_T *); 4406static void DAC960_V2_QueueReadWriteCommand(DAC960_Command_T *); 4407static void DAC960_RequestFunction(struct request_queue *); 4408static irqreturn_t DAC960_BA_InterruptHandler(int, void *); 4409static irqreturn_t DAC960_LP_InterruptHandler(int, void *); 4410static irqreturn_t DAC960_LA_InterruptHandler(int, void *); 4411static irqreturn_t DAC960_PG_InterruptHandler(int, void *); 4412static irqreturn_t DAC960_PD_InterruptHandler(int, void *); 4413static irqreturn_t DAC960_P_InterruptHandler(int, void *); 4414static void DAC960_V1_QueueMonitoringCommand(DAC960_Command_T *); 4415static void DAC960_V2_QueueMonitoringCommand(DAC960_Command_T *); 4416static void DAC960_MonitoringTimerFunction(unsigned long); 4417static void DAC960_Message(DAC960_MessageLevel_T, unsigned char *, 4418 DAC960_Controller_T *, ...); 4419static void DAC960_CreateProcEntries(DAC960_Controller_T *); 4420static void DAC960_DestroyProcEntries(DAC960_Controller_T *); 4421 4422#endif /* DAC960_DriverVersion */ 4423