1 2/* 3 4 Linux Driver for BusLogic MultiMaster and FlashPoint SCSI Host Adapters 5 6 Copyright 1995-1998 by Leonard N. Zubkoff <lnz@dandelion.com> 7 8 This program is free software; you may redistribute and/or modify it under 9 the terms of the GNU General Public License Version 2 as published by the 10 Free Software Foundation. 11 12 This program is distributed in the hope that it will be useful, but 13 WITHOUT ANY WARRANTY, without even the implied warranty of MERCHANTABILITY 14 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 for complete details. 16 17 The author respectfully requests that any modifications to this software be 18 sent directly to him for evaluation and testing. 19 20 Special thanks to Wayne Yen, Jin-Lon Hon, and Alex Win of BusLogic, whose 21 advice has been invaluable, to David Gentzel, for writing the original Linux 22 BusLogic driver, and to Paul Gortmaker, for being such a dedicated test site. 23 24 Finally, special thanks to Mylex/BusLogic for making the FlashPoint SCCB 25 Manager available as freely redistributable source code. 26 27*/ 28 29#define BusLogic_DriverVersion "2.1.16" 30#define BusLogic_DriverDate "18 July 2002" 31 32#include <linux/module.h> 33#include <linux/init.h> 34#include <linux/interrupt.h> 35#include <linux/types.h> 36#include <linux/blkdev.h> 37#include <linux/delay.h> 38#include <linux/ioport.h> 39#include <linux/mm.h> 40#include <linux/stat.h> 41#include <linux/pci.h> 42#include <linux/spinlock.h> 43#include <linux/jiffies.h> 44#include <linux/dma-mapping.h> 45#include <scsi/scsicam.h> 46 47#include <asm/dma.h> 48#include <asm/io.h> 49#include <asm/system.h> 50 51#include <scsi/scsi.h> 52#include <scsi/scsi_cmnd.h> 53#include <scsi/scsi_device.h> 54#include <scsi/scsi_host.h> 55#include <scsi/scsi_tcq.h> 56#include "BusLogic.h" 57#include "FlashPoint.c" 58 59#ifndef FAILURE 60#define FAILURE (-1) 61#endif 62 63static struct scsi_host_template Bus_Logic_template; 64 65/* 66 BusLogic_DriverOptionsCount is a count of the number of BusLogic Driver 67 Options specifications provided via the Linux Kernel Command Line or via 68 the Loadable Kernel Module Installation Facility. 69*/ 70 71static int BusLogic_DriverOptionsCount; 72 73 74/* 75 BusLogic_DriverOptions is an array of Driver Options structures representing 76 BusLogic Driver Options specifications provided via the Linux Kernel Command 77 Line or via the Loadable Kernel Module Installation Facility. 78*/ 79 80static struct BusLogic_DriverOptions BusLogic_DriverOptions[BusLogic_MaxHostAdapters]; 81 82 83/* 84 BusLogic can be assigned a string by insmod. 85*/ 86 87MODULE_LICENSE("GPL"); 88#ifdef MODULE 89static char *BusLogic; 90module_param(BusLogic, charp, 0); 91#endif 92 93 94/* 95 BusLogic_ProbeOptions is a set of Probe Options to be applied across 96 all BusLogic Host Adapters. 97*/ 98 99static struct BusLogic_ProbeOptions BusLogic_ProbeOptions; 100 101 102/* 103 BusLogic_GlobalOptions is a set of Global Options to be applied across 104 all BusLogic Host Adapters. 105*/ 106 107static struct BusLogic_GlobalOptions BusLogic_GlobalOptions; 108 109static LIST_HEAD(BusLogic_host_list); 110 111/* 112 BusLogic_ProbeInfoCount is the number of entries in BusLogic_ProbeInfoList. 113*/ 114 115static int BusLogic_ProbeInfoCount; 116 117 118/* 119 BusLogic_ProbeInfoList is the list of I/O Addresses and Bus Probe Information 120 to be checked for potential BusLogic Host Adapters. It is initialized by 121 interrogating the PCI Configuration Space on PCI machines as well as from the 122 list of standard BusLogic I/O Addresses. 123*/ 124 125static struct BusLogic_ProbeInfo *BusLogic_ProbeInfoList; 126 127 128/* 129 BusLogic_CommandFailureReason holds a string identifying the reason why a 130 call to BusLogic_Command failed. It is only non-NULL when BusLogic_Command 131 returns a failure code. 132*/ 133 134static char *BusLogic_CommandFailureReason; 135 136/* 137 BusLogic_AnnounceDriver announces the Driver Version and Date, Author's 138 Name, Copyright Notice, and Electronic Mail Address. 139*/ 140 141static void BusLogic_AnnounceDriver(struct BusLogic_HostAdapter *HostAdapter) 142{ 143 BusLogic_Announce("***** BusLogic SCSI Driver Version " BusLogic_DriverVersion " of " BusLogic_DriverDate " *****\n", HostAdapter); 144 BusLogic_Announce("Copyright 1995-1998 by Leonard N. Zubkoff " "<lnz@dandelion.com>\n", HostAdapter); 145} 146 147 148/* 149 BusLogic_DriverInfo returns the Host Adapter Name to identify this SCSI 150 Driver and Host Adapter. 151*/ 152 153static const char *BusLogic_DriverInfo(struct Scsi_Host *Host) 154{ 155 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) Host->hostdata; 156 return HostAdapter->FullModelName; 157} 158 159/* 160 BusLogic_InitializeCCBs initializes a group of Command Control Blocks (CCBs) 161 for Host Adapter from the BlockSize bytes located at BlockPointer. The newly 162 created CCBs are added to Host Adapter's free list. 163*/ 164 165static void BusLogic_InitializeCCBs(struct BusLogic_HostAdapter *HostAdapter, void *BlockPointer, int BlockSize, dma_addr_t BlockPointerHandle) 166{ 167 struct BusLogic_CCB *CCB = (struct BusLogic_CCB *) BlockPointer; 168 unsigned int offset = 0; 169 memset(BlockPointer, 0, BlockSize); 170 CCB->AllocationGroupHead = BlockPointerHandle; 171 CCB->AllocationGroupSize = BlockSize; 172 while ((BlockSize -= sizeof(struct BusLogic_CCB)) >= 0) { 173 CCB->Status = BusLogic_CCB_Free; 174 CCB->HostAdapter = HostAdapter; 175 CCB->DMA_Handle = (u32) BlockPointerHandle + offset; 176 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) { 177 CCB->CallbackFunction = BusLogic_QueueCompletedCCB; 178 CCB->BaseAddress = HostAdapter->FlashPointInfo.BaseAddress; 179 } 180 CCB->Next = HostAdapter->Free_CCBs; 181 CCB->NextAll = HostAdapter->All_CCBs; 182 HostAdapter->Free_CCBs = CCB; 183 HostAdapter->All_CCBs = CCB; 184 HostAdapter->AllocatedCCBs++; 185 CCB++; 186 offset += sizeof(struct BusLogic_CCB); 187 } 188} 189 190 191/* 192 BusLogic_CreateInitialCCBs allocates the initial CCBs for Host Adapter. 193*/ 194 195static bool __init BusLogic_CreateInitialCCBs(struct BusLogic_HostAdapter *HostAdapter) 196{ 197 int BlockSize = BusLogic_CCB_AllocationGroupSize * sizeof(struct BusLogic_CCB); 198 void *BlockPointer; 199 dma_addr_t BlockPointerHandle; 200 while (HostAdapter->AllocatedCCBs < HostAdapter->InitialCCBs) { 201 BlockPointer = pci_alloc_consistent(HostAdapter->PCI_Device, BlockSize, &BlockPointerHandle); 202 if (BlockPointer == NULL) { 203 BusLogic_Error("UNABLE TO ALLOCATE CCB GROUP - DETACHING\n", HostAdapter); 204 return false; 205 } 206 BusLogic_InitializeCCBs(HostAdapter, BlockPointer, BlockSize, BlockPointerHandle); 207 } 208 return true; 209} 210 211 212/* 213 BusLogic_DestroyCCBs deallocates the CCBs for Host Adapter. 214*/ 215 216static void BusLogic_DestroyCCBs(struct BusLogic_HostAdapter *HostAdapter) 217{ 218 struct BusLogic_CCB *NextCCB = HostAdapter->All_CCBs, *CCB, *Last_CCB = NULL; 219 HostAdapter->All_CCBs = NULL; 220 HostAdapter->Free_CCBs = NULL; 221 while ((CCB = NextCCB) != NULL) { 222 NextCCB = CCB->NextAll; 223 if (CCB->AllocationGroupHead) { 224 if (Last_CCB) 225 pci_free_consistent(HostAdapter->PCI_Device, Last_CCB->AllocationGroupSize, Last_CCB, Last_CCB->AllocationGroupHead); 226 Last_CCB = CCB; 227 } 228 } 229 if (Last_CCB) 230 pci_free_consistent(HostAdapter->PCI_Device, Last_CCB->AllocationGroupSize, Last_CCB, Last_CCB->AllocationGroupHead); 231} 232 233 234/* 235 BusLogic_CreateAdditionalCCBs allocates Additional CCBs for Host Adapter. If 236 allocation fails and there are no remaining CCBs available, the Driver Queue 237 Depth is decreased to a known safe value to avoid potential deadlocks when 238 multiple host adapters share the same IRQ Channel. 239*/ 240 241static void BusLogic_CreateAdditionalCCBs(struct BusLogic_HostAdapter *HostAdapter, int AdditionalCCBs, bool SuccessMessageP) 242{ 243 int BlockSize = BusLogic_CCB_AllocationGroupSize * sizeof(struct BusLogic_CCB); 244 int PreviouslyAllocated = HostAdapter->AllocatedCCBs; 245 void *BlockPointer; 246 dma_addr_t BlockPointerHandle; 247 if (AdditionalCCBs <= 0) 248 return; 249 while (HostAdapter->AllocatedCCBs - PreviouslyAllocated < AdditionalCCBs) { 250 BlockPointer = pci_alloc_consistent(HostAdapter->PCI_Device, BlockSize, &BlockPointerHandle); 251 if (BlockPointer == NULL) 252 break; 253 BusLogic_InitializeCCBs(HostAdapter, BlockPointer, BlockSize, BlockPointerHandle); 254 } 255 if (HostAdapter->AllocatedCCBs > PreviouslyAllocated) { 256 if (SuccessMessageP) 257 BusLogic_Notice("Allocated %d additional CCBs (total now %d)\n", HostAdapter, HostAdapter->AllocatedCCBs - PreviouslyAllocated, HostAdapter->AllocatedCCBs); 258 return; 259 } 260 BusLogic_Notice("Failed to allocate additional CCBs\n", HostAdapter); 261 if (HostAdapter->DriverQueueDepth > HostAdapter->AllocatedCCBs - HostAdapter->TargetDeviceCount) { 262 HostAdapter->DriverQueueDepth = HostAdapter->AllocatedCCBs - HostAdapter->TargetDeviceCount; 263 HostAdapter->SCSI_Host->can_queue = HostAdapter->DriverQueueDepth; 264 } 265} 266 267/* 268 BusLogic_AllocateCCB allocates a CCB from Host Adapter's free list, 269 allocating more memory from the Kernel if necessary. The Host Adapter's 270 Lock should already have been acquired by the caller. 271*/ 272 273static struct BusLogic_CCB *BusLogic_AllocateCCB(struct BusLogic_HostAdapter 274 *HostAdapter) 275{ 276 static unsigned long SerialNumber = 0; 277 struct BusLogic_CCB *CCB; 278 CCB = HostAdapter->Free_CCBs; 279 if (CCB != NULL) { 280 CCB->SerialNumber = ++SerialNumber; 281 HostAdapter->Free_CCBs = CCB->Next; 282 CCB->Next = NULL; 283 if (HostAdapter->Free_CCBs == NULL) 284 BusLogic_CreateAdditionalCCBs(HostAdapter, HostAdapter->IncrementalCCBs, true); 285 return CCB; 286 } 287 BusLogic_CreateAdditionalCCBs(HostAdapter, HostAdapter->IncrementalCCBs, true); 288 CCB = HostAdapter->Free_CCBs; 289 if (CCB == NULL) 290 return NULL; 291 CCB->SerialNumber = ++SerialNumber; 292 HostAdapter->Free_CCBs = CCB->Next; 293 CCB->Next = NULL; 294 return CCB; 295} 296 297 298/* 299 BusLogic_DeallocateCCB deallocates a CCB, returning it to the Host Adapter's 300 free list. The Host Adapter's Lock should already have been acquired by the 301 caller. 302*/ 303 304static void BusLogic_DeallocateCCB(struct BusLogic_CCB *CCB) 305{ 306 struct BusLogic_HostAdapter *HostAdapter = CCB->HostAdapter; 307 struct scsi_cmnd *cmd = CCB->Command; 308 309 if (cmd->use_sg != 0) { 310 pci_unmap_sg(HostAdapter->PCI_Device, 311 (struct scatterlist *)cmd->request_buffer, 312 cmd->use_sg, cmd->sc_data_direction); 313 } else if (cmd->request_bufflen != 0) { 314 pci_unmap_single(HostAdapter->PCI_Device, CCB->DataPointer, 315 CCB->DataLength, cmd->sc_data_direction); 316 } 317 pci_unmap_single(HostAdapter->PCI_Device, CCB->SenseDataPointer, 318 CCB->SenseDataLength, PCI_DMA_FROMDEVICE); 319 320 CCB->Command = NULL; 321 CCB->Status = BusLogic_CCB_Free; 322 CCB->Next = HostAdapter->Free_CCBs; 323 HostAdapter->Free_CCBs = CCB; 324} 325 326 327/* 328 BusLogic_Command sends the command OperationCode to HostAdapter, optionally 329 providing ParameterLength bytes of ParameterData and receiving at most 330 ReplyLength bytes of ReplyData; any excess reply data is received but 331 discarded. 332 333 On success, this function returns the number of reply bytes read from 334 the Host Adapter (including any discarded data); on failure, it returns 335 -1 if the command was invalid, or -2 if a timeout occurred. 336 337 BusLogic_Command is called exclusively during host adapter detection and 338 initialization, so performance and latency are not critical, and exclusive 339 access to the Host Adapter hardware is assumed. Once the host adapter and 340 driver are initialized, the only Host Adapter command that is issued is the 341 single byte Execute Mailbox Command operation code, which does not require 342 waiting for the Host Adapter Ready bit to be set in the Status Register. 343*/ 344 345static int BusLogic_Command(struct BusLogic_HostAdapter *HostAdapter, enum BusLogic_OperationCode OperationCode, void *ParameterData, int ParameterLength, void *ReplyData, int ReplyLength) 346{ 347 unsigned char *ParameterPointer = (unsigned char *) ParameterData; 348 unsigned char *ReplyPointer = (unsigned char *) ReplyData; 349 union BusLogic_StatusRegister StatusRegister; 350 union BusLogic_InterruptRegister InterruptRegister; 351 unsigned long ProcessorFlags = 0; 352 int ReplyBytes = 0, Result; 353 long TimeoutCounter; 354 /* 355 Clear out the Reply Data if provided. 356 */ 357 if (ReplyLength > 0) 358 memset(ReplyData, 0, ReplyLength); 359 /* 360 If the IRQ Channel has not yet been acquired, then interrupts must be 361 disabled while issuing host adapter commands since a Command Complete 362 interrupt could occur if the IRQ Channel was previously enabled by another 363 BusLogic Host Adapter or another driver sharing the same IRQ Channel. 364 */ 365 if (!HostAdapter->IRQ_ChannelAcquired) 366 local_irq_save(ProcessorFlags); 367 /* 368 Wait for the Host Adapter Ready bit to be set and the Command/Parameter 369 Register Busy bit to be reset in the Status Register. 370 */ 371 TimeoutCounter = 10000; 372 while (--TimeoutCounter >= 0) { 373 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 374 if (StatusRegister.sr.HostAdapterReady && !StatusRegister.sr.CommandParameterRegisterBusy) 375 break; 376 udelay(100); 377 } 378 if (TimeoutCounter < 0) { 379 BusLogic_CommandFailureReason = "Timeout waiting for Host Adapter Ready"; 380 Result = -2; 381 goto Done; 382 } 383 /* 384 Write the OperationCode to the Command/Parameter Register. 385 */ 386 HostAdapter->HostAdapterCommandCompleted = false; 387 BusLogic_WriteCommandParameterRegister(HostAdapter, OperationCode); 388 /* 389 Write any additional Parameter Bytes. 390 */ 391 TimeoutCounter = 10000; 392 while (ParameterLength > 0 && --TimeoutCounter >= 0) { 393 /* 394 Wait 100 microseconds to give the Host Adapter enough time to determine 395 whether the last value written to the Command/Parameter Register was 396 valid or not. If the Command Complete bit is set in the Interrupt 397 Register, then the Command Invalid bit in the Status Register will be 398 reset if the Operation Code or Parameter was valid and the command 399 has completed, or set if the Operation Code or Parameter was invalid. 400 If the Data In Register Ready bit is set in the Status Register, then 401 the Operation Code was valid, and data is waiting to be read back 402 from the Host Adapter. Otherwise, wait for the Command/Parameter 403 Register Busy bit in the Status Register to be reset. 404 */ 405 udelay(100); 406 InterruptRegister.All = BusLogic_ReadInterruptRegister(HostAdapter); 407 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 408 if (InterruptRegister.ir.CommandComplete) 409 break; 410 if (HostAdapter->HostAdapterCommandCompleted) 411 break; 412 if (StatusRegister.sr.DataInRegisterReady) 413 break; 414 if (StatusRegister.sr.CommandParameterRegisterBusy) 415 continue; 416 BusLogic_WriteCommandParameterRegister(HostAdapter, *ParameterPointer++); 417 ParameterLength--; 418 } 419 if (TimeoutCounter < 0) { 420 BusLogic_CommandFailureReason = "Timeout waiting for Parameter Acceptance"; 421 Result = -2; 422 goto Done; 423 } 424 /* 425 The Modify I/O Address command does not cause a Command Complete Interrupt. 426 */ 427 if (OperationCode == BusLogic_ModifyIOAddress) { 428 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 429 if (StatusRegister.sr.CommandInvalid) { 430 BusLogic_CommandFailureReason = "Modify I/O Address Invalid"; 431 Result = -1; 432 goto Done; 433 } 434 if (BusLogic_GlobalOptions.TraceConfiguration) 435 BusLogic_Notice("BusLogic_Command(%02X) Status = %02X: " "(Modify I/O Address)\n", HostAdapter, OperationCode, StatusRegister.All); 436 Result = 0; 437 goto Done; 438 } 439 /* 440 Select an appropriate timeout value for awaiting command completion. 441 */ 442 switch (OperationCode) { 443 case BusLogic_InquireInstalledDevicesID0to7: 444 case BusLogic_InquireInstalledDevicesID8to15: 445 case BusLogic_InquireTargetDevices: 446 /* Approximately 60 seconds. */ 447 TimeoutCounter = 60 * 10000; 448 break; 449 default: 450 /* Approximately 1 second. */ 451 TimeoutCounter = 10000; 452 break; 453 } 454 /* 455 Receive any Reply Bytes, waiting for either the Command Complete bit to 456 be set in the Interrupt Register, or for the Interrupt Handler to set the 457 Host Adapter Command Completed bit in the Host Adapter structure. 458 */ 459 while (--TimeoutCounter >= 0) { 460 InterruptRegister.All = BusLogic_ReadInterruptRegister(HostAdapter); 461 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 462 if (InterruptRegister.ir.CommandComplete) 463 break; 464 if (HostAdapter->HostAdapterCommandCompleted) 465 break; 466 if (StatusRegister.sr.DataInRegisterReady) { 467 if (++ReplyBytes <= ReplyLength) 468 *ReplyPointer++ = BusLogic_ReadDataInRegister(HostAdapter); 469 else 470 BusLogic_ReadDataInRegister(HostAdapter); 471 } 472 if (OperationCode == BusLogic_FetchHostAdapterLocalRAM && StatusRegister.sr.HostAdapterReady) 473 break; 474 udelay(100); 475 } 476 if (TimeoutCounter < 0) { 477 BusLogic_CommandFailureReason = "Timeout waiting for Command Complete"; 478 Result = -2; 479 goto Done; 480 } 481 /* 482 Clear any pending Command Complete Interrupt. 483 */ 484 BusLogic_InterruptReset(HostAdapter); 485 /* 486 Provide tracing information if requested. 487 */ 488 if (BusLogic_GlobalOptions.TraceConfiguration) { 489 int i; 490 BusLogic_Notice("BusLogic_Command(%02X) Status = %02X: %2d ==> %2d:", HostAdapter, OperationCode, StatusRegister.All, ReplyLength, ReplyBytes); 491 if (ReplyLength > ReplyBytes) 492 ReplyLength = ReplyBytes; 493 for (i = 0; i < ReplyLength; i++) 494 BusLogic_Notice(" %02X", HostAdapter, ((unsigned char *) ReplyData)[i]); 495 BusLogic_Notice("\n", HostAdapter); 496 } 497 /* 498 Process Command Invalid conditions. 499 */ 500 if (StatusRegister.sr.CommandInvalid) { 501 /* 502 Some early BusLogic Host Adapters may not recover properly from 503 a Command Invalid condition, so if this appears to be the case, 504 a Soft Reset is issued to the Host Adapter. Potentially invalid 505 commands are never attempted after Mailbox Initialization is 506 performed, so there should be no Host Adapter state lost by a 507 Soft Reset in response to a Command Invalid condition. 508 */ 509 udelay(1000); 510 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 511 if (StatusRegister.sr.CommandInvalid || 512 StatusRegister.sr.Reserved || 513 StatusRegister.sr.DataInRegisterReady || 514 StatusRegister.sr.CommandParameterRegisterBusy || !StatusRegister.sr.HostAdapterReady || !StatusRegister.sr.InitializationRequired || StatusRegister.sr.DiagnosticActive || StatusRegister.sr.DiagnosticFailure) { 515 BusLogic_SoftReset(HostAdapter); 516 udelay(1000); 517 } 518 BusLogic_CommandFailureReason = "Command Invalid"; 519 Result = -1; 520 goto Done; 521 } 522 /* 523 Handle Excess Parameters Supplied conditions. 524 */ 525 if (ParameterLength > 0) { 526 BusLogic_CommandFailureReason = "Excess Parameters Supplied"; 527 Result = -1; 528 goto Done; 529 } 530 /* 531 Indicate the command completed successfully. 532 */ 533 BusLogic_CommandFailureReason = NULL; 534 Result = ReplyBytes; 535 /* 536 Restore the interrupt status if necessary and return. 537 */ 538 Done: 539 if (!HostAdapter->IRQ_ChannelAcquired) 540 local_irq_restore(ProcessorFlags); 541 return Result; 542} 543 544 545/* 546 BusLogic_AppendProbeAddressISA appends a single ISA I/O Address to the list 547 of I/O Address and Bus Probe Information to be checked for potential BusLogic 548 Host Adapters. 549*/ 550 551static void __init BusLogic_AppendProbeAddressISA(unsigned long IO_Address) 552{ 553 struct BusLogic_ProbeInfo *ProbeInfo; 554 if (BusLogic_ProbeInfoCount >= BusLogic_MaxHostAdapters) 555 return; 556 ProbeInfo = &BusLogic_ProbeInfoList[BusLogic_ProbeInfoCount++]; 557 ProbeInfo->HostAdapterType = BusLogic_MultiMaster; 558 ProbeInfo->HostAdapterBusType = BusLogic_ISA_Bus; 559 ProbeInfo->IO_Address = IO_Address; 560 ProbeInfo->PCI_Device = NULL; 561} 562 563 564/* 565 BusLogic_InitializeProbeInfoListISA initializes the list of I/O Address and 566 Bus Probe Information to be checked for potential BusLogic SCSI Host Adapters 567 only from the list of standard BusLogic MultiMaster ISA I/O Addresses. 568*/ 569 570static void __init BusLogic_InitializeProbeInfoListISA(struct BusLogic_HostAdapter 571 *PrototypeHostAdapter) 572{ 573 /* 574 If BusLogic Driver Options specifications requested that ISA Bus Probes 575 be inhibited, do not proceed further. 576 */ 577 if (BusLogic_ProbeOptions.NoProbeISA) 578 return; 579 /* 580 Append the list of standard BusLogic MultiMaster ISA I/O Addresses. 581 */ 582 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe330) 583 BusLogic_AppendProbeAddressISA(0x330); 584 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe334) 585 BusLogic_AppendProbeAddressISA(0x334); 586 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe230) 587 BusLogic_AppendProbeAddressISA(0x230); 588 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe234) 589 BusLogic_AppendProbeAddressISA(0x234); 590 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe130) 591 BusLogic_AppendProbeAddressISA(0x130); 592 if (!BusLogic_ProbeOptions.LimitedProbeISA || BusLogic_ProbeOptions.Probe134) 593 BusLogic_AppendProbeAddressISA(0x134); 594} 595 596 597#ifdef CONFIG_PCI 598 599 600/* 601 BusLogic_SortProbeInfo sorts a section of BusLogic_ProbeInfoList in order 602 of increasing PCI Bus and Device Number. 603*/ 604 605static void __init BusLogic_SortProbeInfo(struct BusLogic_ProbeInfo *ProbeInfoList, int ProbeInfoCount) 606{ 607 int LastInterchange = ProbeInfoCount - 1, Bound, j; 608 while (LastInterchange > 0) { 609 Bound = LastInterchange; 610 LastInterchange = 0; 611 for (j = 0; j < Bound; j++) { 612 struct BusLogic_ProbeInfo *ProbeInfo1 = &ProbeInfoList[j]; 613 struct BusLogic_ProbeInfo *ProbeInfo2 = &ProbeInfoList[j + 1]; 614 if (ProbeInfo1->Bus > ProbeInfo2->Bus || (ProbeInfo1->Bus == ProbeInfo2->Bus && (ProbeInfo1->Device > ProbeInfo2->Device))) { 615 struct BusLogic_ProbeInfo TempProbeInfo; 616 memcpy(&TempProbeInfo, ProbeInfo1, sizeof(struct BusLogic_ProbeInfo)); 617 memcpy(ProbeInfo1, ProbeInfo2, sizeof(struct BusLogic_ProbeInfo)); 618 memcpy(ProbeInfo2, &TempProbeInfo, sizeof(struct BusLogic_ProbeInfo)); 619 LastInterchange = j; 620 } 621 } 622 } 623} 624 625 626/* 627 BusLogic_InitializeMultiMasterProbeInfo initializes the list of I/O Address 628 and Bus Probe Information to be checked for potential BusLogic MultiMaster 629 SCSI Host Adapters by interrogating the PCI Configuration Space on PCI 630 machines as well as from the list of standard BusLogic MultiMaster ISA 631 I/O Addresses. It returns the number of PCI MultiMaster Host Adapters found. 632*/ 633 634static int __init BusLogic_InitializeMultiMasterProbeInfo(struct BusLogic_HostAdapter 635 *PrototypeHostAdapter) 636{ 637 struct BusLogic_ProbeInfo *PrimaryProbeInfo = &BusLogic_ProbeInfoList[BusLogic_ProbeInfoCount]; 638 int NonPrimaryPCIMultiMasterIndex = BusLogic_ProbeInfoCount + 1; 639 int NonPrimaryPCIMultiMasterCount = 0, PCIMultiMasterCount = 0; 640 bool ForceBusDeviceScanningOrder = false; 641 bool ForceBusDeviceScanningOrderChecked = false; 642 bool StandardAddressSeen[6]; 643 struct pci_dev *PCI_Device = NULL; 644 int i; 645 if (BusLogic_ProbeInfoCount >= BusLogic_MaxHostAdapters) 646 return 0; 647 BusLogic_ProbeInfoCount++; 648 for (i = 0; i < 6; i++) 649 StandardAddressSeen[i] = false; 650 /* 651 Iterate over the MultiMaster PCI Host Adapters. For each enumerated host 652 adapter, determine whether its ISA Compatible I/O Port is enabled and if 653 so, whether it is assigned the Primary I/O Address. A host adapter that is 654 assigned the Primary I/O Address will always be the preferred boot device. 655 The MultiMaster BIOS will first recognize a host adapter at the Primary I/O 656 Address, then any other PCI host adapters, and finally any host adapters 657 located at the remaining standard ISA I/O Addresses. When a PCI host 658 adapter is found with its ISA Compatible I/O Port enabled, a command is 659 issued to disable the ISA Compatible I/O Port, and it is noted that the 660 particular standard ISA I/O Address need not be probed. 661 */ 662 PrimaryProbeInfo->IO_Address = 0; 663 while ((PCI_Device = pci_get_device(PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_MULTIMASTER, PCI_Device)) != NULL) { 664 struct BusLogic_HostAdapter *HostAdapter = PrototypeHostAdapter; 665 struct BusLogic_PCIHostAdapterInformation PCIHostAdapterInformation; 666 enum BusLogic_ISACompatibleIOPort ModifyIOAddressRequest; 667 unsigned char Bus; 668 unsigned char Device; 669 unsigned int IRQ_Channel; 670 unsigned long BaseAddress0; 671 unsigned long BaseAddress1; 672 unsigned long IO_Address; 673 unsigned long PCI_Address; 674 675 if (pci_enable_device(PCI_Device)) 676 continue; 677 678 if (pci_set_dma_mask(PCI_Device, DMA_32BIT_MASK )) 679 continue; 680 681 Bus = PCI_Device->bus->number; 682 Device = PCI_Device->devfn >> 3; 683 IRQ_Channel = PCI_Device->irq; 684 IO_Address = BaseAddress0 = pci_resource_start(PCI_Device, 0); 685 PCI_Address = BaseAddress1 = pci_resource_start(PCI_Device, 1); 686 687 if (pci_resource_flags(PCI_Device, 0) & IORESOURCE_MEM) { 688 BusLogic_Error("BusLogic: Base Address0 0x%X not I/O for " "MultiMaster Host Adapter\n", NULL, BaseAddress0); 689 BusLogic_Error("at PCI Bus %d Device %d I/O Address 0x%X\n", NULL, Bus, Device, IO_Address); 690 continue; 691 } 692 if (pci_resource_flags(PCI_Device, 1) & IORESOURCE_IO) { 693 BusLogic_Error("BusLogic: Base Address1 0x%X not Memory for " "MultiMaster Host Adapter\n", NULL, BaseAddress1); 694 BusLogic_Error("at PCI Bus %d Device %d PCI Address 0x%X\n", NULL, Bus, Device, PCI_Address); 695 continue; 696 } 697 if (IRQ_Channel == 0) { 698 BusLogic_Error("BusLogic: IRQ Channel %d invalid for " "MultiMaster Host Adapter\n", NULL, IRQ_Channel); 699 BusLogic_Error("at PCI Bus %d Device %d I/O Address 0x%X\n", NULL, Bus, Device, IO_Address); 700 continue; 701 } 702 if (BusLogic_GlobalOptions.TraceProbe) { 703 BusLogic_Notice("BusLogic: PCI MultiMaster Host Adapter " "detected at\n", NULL); 704 BusLogic_Notice("BusLogic: PCI Bus %d Device %d I/O Address " "0x%X PCI Address 0x%X\n", NULL, Bus, Device, IO_Address, PCI_Address); 705 } 706 /* 707 Issue the Inquire PCI Host Adapter Information command to determine 708 the ISA Compatible I/O Port. If the ISA Compatible I/O Port is 709 known and enabled, note that the particular Standard ISA I/O 710 Address should not be probed. 711 */ 712 HostAdapter->IO_Address = IO_Address; 713 BusLogic_InterruptReset(HostAdapter); 714 if (BusLogic_Command(HostAdapter, BusLogic_InquirePCIHostAdapterInformation, NULL, 0, &PCIHostAdapterInformation, sizeof(PCIHostAdapterInformation)) 715 == sizeof(PCIHostAdapterInformation)) { 716 if (PCIHostAdapterInformation.ISACompatibleIOPort < 6) 717 StandardAddressSeen[PCIHostAdapterInformation.ISACompatibleIOPort] = true; 718 } else 719 PCIHostAdapterInformation.ISACompatibleIOPort = BusLogic_IO_Disable; 720 /* 721 * Issue the Modify I/O Address command to disable the ISA Compatible 722 * I/O Port. On PCI Host Adapters, the Modify I/O Address command 723 * allows modification of the ISA compatible I/O Address that the Host 724 * Adapter responds to; it does not affect the PCI compliant I/O Address 725 * assigned at system initialization. 726 */ 727 ModifyIOAddressRequest = BusLogic_IO_Disable; 728 BusLogic_Command(HostAdapter, BusLogic_ModifyIOAddress, &ModifyIOAddressRequest, sizeof(ModifyIOAddressRequest), NULL, 0); 729 /* 730 For the first MultiMaster Host Adapter enumerated, issue the Fetch 731 Host Adapter Local RAM command to read byte 45 of the AutoSCSI area, 732 for the setting of the "Use Bus And Device # For PCI Scanning Seq." 733 option. Issue the Inquire Board ID command since this option is 734 only valid for the BT-948/958/958D. 735 */ 736 if (!ForceBusDeviceScanningOrderChecked) { 737 struct BusLogic_FetchHostAdapterLocalRAMRequest FetchHostAdapterLocalRAMRequest; 738 struct BusLogic_AutoSCSIByte45 AutoSCSIByte45; 739 struct BusLogic_BoardID BoardID; 740 FetchHostAdapterLocalRAMRequest.ByteOffset = BusLogic_AutoSCSI_BaseOffset + 45; 741 FetchHostAdapterLocalRAMRequest.ByteCount = sizeof(AutoSCSIByte45); 742 BusLogic_Command(HostAdapter, BusLogic_FetchHostAdapterLocalRAM, &FetchHostAdapterLocalRAMRequest, sizeof(FetchHostAdapterLocalRAMRequest), &AutoSCSIByte45, sizeof(AutoSCSIByte45)); 743 BusLogic_Command(HostAdapter, BusLogic_InquireBoardID, NULL, 0, &BoardID, sizeof(BoardID)); 744 if (BoardID.FirmwareVersion1stDigit == '5') 745 ForceBusDeviceScanningOrder = AutoSCSIByte45.ForceBusDeviceScanningOrder; 746 ForceBusDeviceScanningOrderChecked = true; 747 } 748 /* 749 Determine whether this MultiMaster Host Adapter has its ISA 750 Compatible I/O Port enabled and is assigned the Primary I/O Address. 751 If it does, then it is the Primary MultiMaster Host Adapter and must 752 be recognized first. If it does not, then it is added to the list 753 for probing after any Primary MultiMaster Host Adapter is probed. 754 */ 755 if (PCIHostAdapterInformation.ISACompatibleIOPort == BusLogic_IO_330) { 756 PrimaryProbeInfo->HostAdapterType = BusLogic_MultiMaster; 757 PrimaryProbeInfo->HostAdapterBusType = BusLogic_PCI_Bus; 758 PrimaryProbeInfo->IO_Address = IO_Address; 759 PrimaryProbeInfo->PCI_Address = PCI_Address; 760 PrimaryProbeInfo->Bus = Bus; 761 PrimaryProbeInfo->Device = Device; 762 PrimaryProbeInfo->IRQ_Channel = IRQ_Channel; 763 PrimaryProbeInfo->PCI_Device = pci_dev_get(PCI_Device); 764 PCIMultiMasterCount++; 765 } else if (BusLogic_ProbeInfoCount < BusLogic_MaxHostAdapters) { 766 struct BusLogic_ProbeInfo *ProbeInfo = &BusLogic_ProbeInfoList[BusLogic_ProbeInfoCount++]; 767 ProbeInfo->HostAdapterType = BusLogic_MultiMaster; 768 ProbeInfo->HostAdapterBusType = BusLogic_PCI_Bus; 769 ProbeInfo->IO_Address = IO_Address; 770 ProbeInfo->PCI_Address = PCI_Address; 771 ProbeInfo->Bus = Bus; 772 ProbeInfo->Device = Device; 773 ProbeInfo->IRQ_Channel = IRQ_Channel; 774 ProbeInfo->PCI_Device = pci_dev_get(PCI_Device); 775 NonPrimaryPCIMultiMasterCount++; 776 PCIMultiMasterCount++; 777 } else 778 BusLogic_Warning("BusLogic: Too many Host Adapters " "detected\n", NULL); 779 } 780 /* 781 If the AutoSCSI "Use Bus And Device # For PCI Scanning Seq." option is ON 782 for the first enumerated MultiMaster Host Adapter, and if that host adapter 783 is a BT-948/958/958D, then the MultiMaster BIOS will recognize MultiMaster 784 Host Adapters in the order of increasing PCI Bus and Device Number. In 785 that case, sort the probe information into the same order the BIOS uses. 786 If this option is OFF, then the MultiMaster BIOS will recognize MultiMaster 787 Host Adapters in the order they are enumerated by the PCI BIOS, and hence 788 no sorting is necessary. 789 */ 790 if (ForceBusDeviceScanningOrder) 791 BusLogic_SortProbeInfo(&BusLogic_ProbeInfoList[NonPrimaryPCIMultiMasterIndex], NonPrimaryPCIMultiMasterCount); 792 /* 793 If no PCI MultiMaster Host Adapter is assigned the Primary I/O Address, 794 then the Primary I/O Address must be probed explicitly before any PCI 795 host adapters are probed. 796 */ 797 if (!BusLogic_ProbeOptions.NoProbeISA) 798 if (PrimaryProbeInfo->IO_Address == 0 && 799 (!BusLogic_ProbeOptions.LimitedProbeISA || 800 BusLogic_ProbeOptions.Probe330)) { 801 PrimaryProbeInfo->HostAdapterType = BusLogic_MultiMaster; 802 PrimaryProbeInfo->HostAdapterBusType = BusLogic_ISA_Bus; 803 PrimaryProbeInfo->IO_Address = 0x330; 804 } 805 /* 806 Append the list of standard BusLogic MultiMaster ISA I/O Addresses, 807 omitting the Primary I/O Address which has already been handled. 808 */ 809 if (!BusLogic_ProbeOptions.NoProbeISA) { 810 if (!StandardAddressSeen[1] && 811 (!BusLogic_ProbeOptions.LimitedProbeISA || 812 BusLogic_ProbeOptions.Probe334)) 813 BusLogic_AppendProbeAddressISA(0x334); 814 if (!StandardAddressSeen[2] && 815 (!BusLogic_ProbeOptions.LimitedProbeISA || 816 BusLogic_ProbeOptions.Probe230)) 817 BusLogic_AppendProbeAddressISA(0x230); 818 if (!StandardAddressSeen[3] && 819 (!BusLogic_ProbeOptions.LimitedProbeISA || 820 BusLogic_ProbeOptions.Probe234)) 821 BusLogic_AppendProbeAddressISA(0x234); 822 if (!StandardAddressSeen[4] && 823 (!BusLogic_ProbeOptions.LimitedProbeISA || 824 BusLogic_ProbeOptions.Probe130)) 825 BusLogic_AppendProbeAddressISA(0x130); 826 if (!StandardAddressSeen[5] && 827 (!BusLogic_ProbeOptions.LimitedProbeISA || 828 BusLogic_ProbeOptions.Probe134)) 829 BusLogic_AppendProbeAddressISA(0x134); 830 } 831 /* 832 Iterate over the older non-compliant MultiMaster PCI Host Adapters, 833 noting the PCI bus location and assigned IRQ Channel. 834 */ 835 PCI_Device = NULL; 836 while ((PCI_Device = pci_get_device(PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_MULTIMASTER_NC, PCI_Device)) != NULL) { 837 unsigned char Bus; 838 unsigned char Device; 839 unsigned int IRQ_Channel; 840 unsigned long IO_Address; 841 842 if (pci_enable_device(PCI_Device)) 843 continue; 844 845 if (pci_set_dma_mask(PCI_Device, DMA_32BIT_MASK)) 846 continue; 847 848 Bus = PCI_Device->bus->number; 849 Device = PCI_Device->devfn >> 3; 850 IRQ_Channel = PCI_Device->irq; 851 IO_Address = pci_resource_start(PCI_Device, 0); 852 853 if (IO_Address == 0 || IRQ_Channel == 0) 854 continue; 855 for (i = 0; i < BusLogic_ProbeInfoCount; i++) { 856 struct BusLogic_ProbeInfo *ProbeInfo = &BusLogic_ProbeInfoList[i]; 857 if (ProbeInfo->IO_Address == IO_Address && ProbeInfo->HostAdapterType == BusLogic_MultiMaster) { 858 ProbeInfo->HostAdapterBusType = BusLogic_PCI_Bus; 859 ProbeInfo->PCI_Address = 0; 860 ProbeInfo->Bus = Bus; 861 ProbeInfo->Device = Device; 862 ProbeInfo->IRQ_Channel = IRQ_Channel; 863 ProbeInfo->PCI_Device = pci_dev_get(PCI_Device); 864 break; 865 } 866 } 867 } 868 return PCIMultiMasterCount; 869} 870 871 872/* 873 BusLogic_InitializeFlashPointProbeInfo initializes the list of I/O Address 874 and Bus Probe Information to be checked for potential BusLogic FlashPoint 875 Host Adapters by interrogating the PCI Configuration Space. It returns the 876 number of FlashPoint Host Adapters found. 877*/ 878 879static int __init BusLogic_InitializeFlashPointProbeInfo(struct BusLogic_HostAdapter 880 *PrototypeHostAdapter) 881{ 882 int FlashPointIndex = BusLogic_ProbeInfoCount, FlashPointCount = 0; 883 struct pci_dev *PCI_Device = NULL; 884 /* 885 Interrogate PCI Configuration Space for any FlashPoint Host Adapters. 886 */ 887 while ((PCI_Device = pci_get_device(PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_FLASHPOINT, PCI_Device)) != NULL) { 888 unsigned char Bus; 889 unsigned char Device; 890 unsigned int IRQ_Channel; 891 unsigned long BaseAddress0; 892 unsigned long BaseAddress1; 893 unsigned long IO_Address; 894 unsigned long PCI_Address; 895 896 if (pci_enable_device(PCI_Device)) 897 continue; 898 899 if (pci_set_dma_mask(PCI_Device, DMA_32BIT_MASK)) 900 continue; 901 902 Bus = PCI_Device->bus->number; 903 Device = PCI_Device->devfn >> 3; 904 IRQ_Channel = PCI_Device->irq; 905 IO_Address = BaseAddress0 = pci_resource_start(PCI_Device, 0); 906 PCI_Address = BaseAddress1 = pci_resource_start(PCI_Device, 1); 907#ifndef CONFIG_SCSI_OMIT_FLASHPOINT 908 if (pci_resource_flags(PCI_Device, 0) & IORESOURCE_MEM) { 909 BusLogic_Error("BusLogic: Base Address0 0x%X not I/O for " "FlashPoint Host Adapter\n", NULL, BaseAddress0); 910 BusLogic_Error("at PCI Bus %d Device %d I/O Address 0x%X\n", NULL, Bus, Device, IO_Address); 911 continue; 912 } 913 if (pci_resource_flags(PCI_Device, 1) & IORESOURCE_IO) { 914 BusLogic_Error("BusLogic: Base Address1 0x%X not Memory for " "FlashPoint Host Adapter\n", NULL, BaseAddress1); 915 BusLogic_Error("at PCI Bus %d Device %d PCI Address 0x%X\n", NULL, Bus, Device, PCI_Address); 916 continue; 917 } 918 if (IRQ_Channel == 0) { 919 BusLogic_Error("BusLogic: IRQ Channel %d invalid for " "FlashPoint Host Adapter\n", NULL, IRQ_Channel); 920 BusLogic_Error("at PCI Bus %d Device %d I/O Address 0x%X\n", NULL, Bus, Device, IO_Address); 921 continue; 922 } 923 if (BusLogic_GlobalOptions.TraceProbe) { 924 BusLogic_Notice("BusLogic: FlashPoint Host Adapter " "detected at\n", NULL); 925 BusLogic_Notice("BusLogic: PCI Bus %d Device %d I/O Address " "0x%X PCI Address 0x%X\n", NULL, Bus, Device, IO_Address, PCI_Address); 926 } 927 if (BusLogic_ProbeInfoCount < BusLogic_MaxHostAdapters) { 928 struct BusLogic_ProbeInfo *ProbeInfo = &BusLogic_ProbeInfoList[BusLogic_ProbeInfoCount++]; 929 ProbeInfo->HostAdapterType = BusLogic_FlashPoint; 930 ProbeInfo->HostAdapterBusType = BusLogic_PCI_Bus; 931 ProbeInfo->IO_Address = IO_Address; 932 ProbeInfo->PCI_Address = PCI_Address; 933 ProbeInfo->Bus = Bus; 934 ProbeInfo->Device = Device; 935 ProbeInfo->IRQ_Channel = IRQ_Channel; 936 ProbeInfo->PCI_Device = pci_dev_get(PCI_Device); 937 FlashPointCount++; 938 } else 939 BusLogic_Warning("BusLogic: Too many Host Adapters " "detected\n", NULL); 940#else 941 BusLogic_Error("BusLogic: FlashPoint Host Adapter detected at " "PCI Bus %d Device %d\n", NULL, Bus, Device); 942 BusLogic_Error("BusLogic: I/O Address 0x%X PCI Address 0x%X, irq %d, " "but FlashPoint\n", NULL, IO_Address, PCI_Address, IRQ_Channel); 943 BusLogic_Error("BusLogic: support was omitted in this kernel " "configuration.\n", NULL); 944#endif 945 } 946 /* 947 The FlashPoint BIOS will scan for FlashPoint Host Adapters in the order of 948 increasing PCI Bus and Device Number, so sort the probe information into 949 the same order the BIOS uses. 950 */ 951 BusLogic_SortProbeInfo(&BusLogic_ProbeInfoList[FlashPointIndex], FlashPointCount); 952 return FlashPointCount; 953} 954 955 956/* 957 BusLogic_InitializeProbeInfoList initializes the list of I/O Address and Bus 958 Probe Information to be checked for potential BusLogic SCSI Host Adapters by 959 interrogating the PCI Configuration Space on PCI machines as well as from the 960 list of standard BusLogic MultiMaster ISA I/O Addresses. By default, if both 961 FlashPoint and PCI MultiMaster Host Adapters are present, this driver will 962 probe for FlashPoint Host Adapters first unless the BIOS primary disk is 963 controlled by the first PCI MultiMaster Host Adapter, in which case 964 MultiMaster Host Adapters will be probed first. The BusLogic Driver Options 965 specifications "MultiMasterFirst" and "FlashPointFirst" can be used to force 966 a particular probe order. 967*/ 968 969static void __init BusLogic_InitializeProbeInfoList(struct BusLogic_HostAdapter 970 *PrototypeHostAdapter) 971{ 972 /* 973 If a PCI BIOS is present, interrogate it for MultiMaster and FlashPoint 974 Host Adapters; otherwise, default to the standard ISA MultiMaster probe. 975 */ 976 if (!BusLogic_ProbeOptions.NoProbePCI) { 977 if (BusLogic_ProbeOptions.MultiMasterFirst) { 978 BusLogic_InitializeMultiMasterProbeInfo(PrototypeHostAdapter); 979 BusLogic_InitializeFlashPointProbeInfo(PrototypeHostAdapter); 980 } else if (BusLogic_ProbeOptions.FlashPointFirst) { 981 BusLogic_InitializeFlashPointProbeInfo(PrototypeHostAdapter); 982 BusLogic_InitializeMultiMasterProbeInfo(PrototypeHostAdapter); 983 } else { 984 int FlashPointCount = BusLogic_InitializeFlashPointProbeInfo(PrototypeHostAdapter); 985 int PCIMultiMasterCount = BusLogic_InitializeMultiMasterProbeInfo(PrototypeHostAdapter); 986 if (FlashPointCount > 0 && PCIMultiMasterCount > 0) { 987 struct BusLogic_ProbeInfo *ProbeInfo = &BusLogic_ProbeInfoList[FlashPointCount]; 988 struct BusLogic_HostAdapter *HostAdapter = PrototypeHostAdapter; 989 struct BusLogic_FetchHostAdapterLocalRAMRequest FetchHostAdapterLocalRAMRequest; 990 struct BusLogic_BIOSDriveMapByte Drive0MapByte; 991 while (ProbeInfo->HostAdapterBusType != BusLogic_PCI_Bus) 992 ProbeInfo++; 993 HostAdapter->IO_Address = ProbeInfo->IO_Address; 994 FetchHostAdapterLocalRAMRequest.ByteOffset = BusLogic_BIOS_BaseOffset + BusLogic_BIOS_DriveMapOffset + 0; 995 FetchHostAdapterLocalRAMRequest.ByteCount = sizeof(Drive0MapByte); 996 BusLogic_Command(HostAdapter, BusLogic_FetchHostAdapterLocalRAM, &FetchHostAdapterLocalRAMRequest, sizeof(FetchHostAdapterLocalRAMRequest), &Drive0MapByte, sizeof(Drive0MapByte)); 997 /* 998 If the Map Byte for BIOS Drive 0 indicates that BIOS Drive 0 999 is controlled by this PCI MultiMaster Host Adapter, then 1000 reverse the probe order so that MultiMaster Host Adapters are 1001 probed before FlashPoint Host Adapters. 1002 */ 1003 if (Drive0MapByte.DiskGeometry != BusLogic_BIOS_Disk_Not_Installed) { 1004 struct BusLogic_ProbeInfo SavedProbeInfo[BusLogic_MaxHostAdapters]; 1005 int MultiMasterCount = BusLogic_ProbeInfoCount - FlashPointCount; 1006 memcpy(SavedProbeInfo, BusLogic_ProbeInfoList, BusLogic_ProbeInfoCount * sizeof(struct BusLogic_ProbeInfo)); 1007 memcpy(&BusLogic_ProbeInfoList[0], &SavedProbeInfo[FlashPointCount], MultiMasterCount * sizeof(struct BusLogic_ProbeInfo)); 1008 memcpy(&BusLogic_ProbeInfoList[MultiMasterCount], &SavedProbeInfo[0], FlashPointCount * sizeof(struct BusLogic_ProbeInfo)); 1009 } 1010 } 1011 } 1012 } else 1013 BusLogic_InitializeProbeInfoListISA(PrototypeHostAdapter); 1014} 1015 1016 1017#endif /* CONFIG_PCI */ 1018 1019 1020/* 1021 BusLogic_Failure prints a standardized error message, and then returns false. 1022*/ 1023 1024static bool BusLogic_Failure(struct BusLogic_HostAdapter *HostAdapter, char *ErrorMessage) 1025{ 1026 BusLogic_AnnounceDriver(HostAdapter); 1027 if (HostAdapter->HostAdapterBusType == BusLogic_PCI_Bus) { 1028 BusLogic_Error("While configuring BusLogic PCI Host Adapter at\n", HostAdapter); 1029 BusLogic_Error("Bus %d Device %d I/O Address 0x%X PCI Address 0x%X:\n", HostAdapter, HostAdapter->Bus, HostAdapter->Device, HostAdapter->IO_Address, HostAdapter->PCI_Address); 1030 } else 1031 BusLogic_Error("While configuring BusLogic Host Adapter at " "I/O Address 0x%X:\n", HostAdapter, HostAdapter->IO_Address); 1032 BusLogic_Error("%s FAILED - DETACHING\n", HostAdapter, ErrorMessage); 1033 if (BusLogic_CommandFailureReason != NULL) 1034 BusLogic_Error("ADDITIONAL FAILURE INFO - %s\n", HostAdapter, BusLogic_CommandFailureReason); 1035 return false; 1036} 1037 1038 1039/* 1040 BusLogic_ProbeHostAdapter probes for a BusLogic Host Adapter. 1041*/ 1042 1043static bool __init BusLogic_ProbeHostAdapter(struct BusLogic_HostAdapter *HostAdapter) 1044{ 1045 union BusLogic_StatusRegister StatusRegister; 1046 union BusLogic_InterruptRegister InterruptRegister; 1047 union BusLogic_GeometryRegister GeometryRegister; 1048 /* 1049 FlashPoint Host Adapters are Probed by the FlashPoint SCCB Manager. 1050 */ 1051 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) { 1052 struct FlashPoint_Info *FlashPointInfo = &HostAdapter->FlashPointInfo; 1053 FlashPointInfo->BaseAddress = (u32) HostAdapter->IO_Address; 1054 FlashPointInfo->IRQ_Channel = HostAdapter->IRQ_Channel; 1055 FlashPointInfo->Present = false; 1056 if (!(FlashPoint_ProbeHostAdapter(FlashPointInfo) == 0 && FlashPointInfo->Present)) { 1057 BusLogic_Error("BusLogic: FlashPoint Host Adapter detected at " "PCI Bus %d Device %d\n", HostAdapter, HostAdapter->Bus, HostAdapter->Device); 1058 BusLogic_Error("BusLogic: I/O Address 0x%X PCI Address 0x%X, " "but FlashPoint\n", HostAdapter, HostAdapter->IO_Address, HostAdapter->PCI_Address); 1059 BusLogic_Error("BusLogic: Probe Function failed to validate it.\n", HostAdapter); 1060 return false; 1061 } 1062 if (BusLogic_GlobalOptions.TraceProbe) 1063 BusLogic_Notice("BusLogic_Probe(0x%X): FlashPoint Found\n", HostAdapter, HostAdapter->IO_Address); 1064 /* 1065 Indicate the Host Adapter Probe completed successfully. 1066 */ 1067 return true; 1068 } 1069 /* 1070 Read the Status, Interrupt, and Geometry Registers to test if there are I/O 1071 ports that respond, and to check the values to determine if they are from a 1072 BusLogic Host Adapter. A nonexistent I/O port will return 0xFF, in which 1073 case there is definitely no BusLogic Host Adapter at this base I/O Address. 1074 The test here is a subset of that used by the BusLogic Host Adapter BIOS. 1075 */ 1076 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 1077 InterruptRegister.All = BusLogic_ReadInterruptRegister(HostAdapter); 1078 GeometryRegister.All = BusLogic_ReadGeometryRegister(HostAdapter); 1079 if (BusLogic_GlobalOptions.TraceProbe) 1080 BusLogic_Notice("BusLogic_Probe(0x%X): Status 0x%02X, Interrupt 0x%02X, " "Geometry 0x%02X\n", HostAdapter, HostAdapter->IO_Address, StatusRegister.All, InterruptRegister.All, GeometryRegister.All); 1081 if (StatusRegister.All == 0 || StatusRegister.sr.DiagnosticActive || StatusRegister.sr.CommandParameterRegisterBusy || StatusRegister.sr.Reserved || StatusRegister.sr.CommandInvalid || InterruptRegister.ir.Reserved != 0) 1082 return false; 1083 /* 1084 Check the undocumented Geometry Register to test if there is an I/O port 1085 that responded. Adaptec Host Adapters do not implement the Geometry 1086 Register, so this test helps serve to avoid incorrectly recognizing an 1087 Adaptec 1542A or 1542B as a BusLogic. Unfortunately, the Adaptec 1542C 1088 series does respond to the Geometry Register I/O port, but it will be 1089 rejected later when the Inquire Extended Setup Information command is 1090 issued in BusLogic_CheckHostAdapter. The AMI FastDisk Host Adapter is a 1091 BusLogic clone that implements the same interface as earlier BusLogic 1092 Host Adapters, including the undocumented commands, and is therefore 1093 supported by this driver. However, the AMI FastDisk always returns 0x00 1094 upon reading the Geometry Register, so the extended translation option 1095 should always be left disabled on the AMI FastDisk. 1096 */ 1097 if (GeometryRegister.All == 0xFF) 1098 return false; 1099 /* 1100 Indicate the Host Adapter Probe completed successfully. 1101 */ 1102 return true; 1103} 1104 1105 1106/* 1107 BusLogic_HardwareResetHostAdapter issues a Hardware Reset to the Host Adapter 1108 and waits for Host Adapter Diagnostics to complete. If HardReset is true, a 1109 Hard Reset is performed which also initiates a SCSI Bus Reset. Otherwise, a 1110 Soft Reset is performed which only resets the Host Adapter without forcing a 1111 SCSI Bus Reset. 1112*/ 1113 1114static bool BusLogic_HardwareResetHostAdapter(struct BusLogic_HostAdapter 1115 *HostAdapter, bool HardReset) 1116{ 1117 union BusLogic_StatusRegister StatusRegister; 1118 int TimeoutCounter; 1119 /* 1120 FlashPoint Host Adapters are Hard Reset by the FlashPoint SCCB Manager. 1121 */ 1122 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) { 1123 struct FlashPoint_Info *FlashPointInfo = &HostAdapter->FlashPointInfo; 1124 FlashPointInfo->HostSoftReset = !HardReset; 1125 FlashPointInfo->ReportDataUnderrun = true; 1126 HostAdapter->CardHandle = FlashPoint_HardwareResetHostAdapter(FlashPointInfo); 1127 if (HostAdapter->CardHandle == FlashPoint_BadCardHandle) 1128 return false; 1129 /* 1130 Indicate the Host Adapter Hard Reset completed successfully. 1131 */ 1132 return true; 1133 } 1134 /* 1135 Issue a Hard Reset or Soft Reset Command to the Host Adapter. The Host 1136 Adapter should respond by setting Diagnostic Active in the Status Register. 1137 */ 1138 if (HardReset) 1139 BusLogic_HardReset(HostAdapter); 1140 else 1141 BusLogic_SoftReset(HostAdapter); 1142 /* 1143 Wait until Diagnostic Active is set in the Status Register. 1144 */ 1145 TimeoutCounter = 5 * 10000; 1146 while (--TimeoutCounter >= 0) { 1147 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 1148 if (StatusRegister.sr.DiagnosticActive) 1149 break; 1150 udelay(100); 1151 } 1152 if (BusLogic_GlobalOptions.TraceHardwareReset) 1153 BusLogic_Notice("BusLogic_HardwareReset(0x%X): Diagnostic Active, " "Status 0x%02X\n", HostAdapter, HostAdapter->IO_Address, StatusRegister.All); 1154 if (TimeoutCounter < 0) 1155 return false; 1156 /* 1157 Wait 100 microseconds to allow completion of any initial diagnostic 1158 activity which might leave the contents of the Status Register 1159 unpredictable. 1160 */ 1161 udelay(100); 1162 /* 1163 Wait until Diagnostic Active is reset in the Status Register. 1164 */ 1165 TimeoutCounter = 10 * 10000; 1166 while (--TimeoutCounter >= 0) { 1167 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 1168 if (!StatusRegister.sr.DiagnosticActive) 1169 break; 1170 udelay(100); 1171 } 1172 if (BusLogic_GlobalOptions.TraceHardwareReset) 1173 BusLogic_Notice("BusLogic_HardwareReset(0x%X): Diagnostic Completed, " "Status 0x%02X\n", HostAdapter, HostAdapter->IO_Address, StatusRegister.All); 1174 if (TimeoutCounter < 0) 1175 return false; 1176 /* 1177 Wait until at least one of the Diagnostic Failure, Host Adapter Ready, 1178 or Data In Register Ready bits is set in the Status Register. 1179 */ 1180 TimeoutCounter = 10000; 1181 while (--TimeoutCounter >= 0) { 1182 StatusRegister.All = BusLogic_ReadStatusRegister(HostAdapter); 1183 if (StatusRegister.sr.DiagnosticFailure || StatusRegister.sr.HostAdapterReady || StatusRegister.sr.DataInRegisterReady) 1184 break; 1185 udelay(100); 1186 } 1187 if (BusLogic_GlobalOptions.TraceHardwareReset) 1188 BusLogic_Notice("BusLogic_HardwareReset(0x%X): Host Adapter Ready, " "Status 0x%02X\n", HostAdapter, HostAdapter->IO_Address, StatusRegister.All); 1189 if (TimeoutCounter < 0) 1190 return false; 1191 /* 1192 If Diagnostic Failure is set or Host Adapter Ready is reset, then an 1193 error occurred during the Host Adapter diagnostics. If Data In Register 1194 Ready is set, then there is an Error Code available. 1195 */ 1196 if (StatusRegister.sr.DiagnosticFailure || !StatusRegister.sr.HostAdapterReady) { 1197 BusLogic_CommandFailureReason = NULL; 1198 BusLogic_Failure(HostAdapter, "HARD RESET DIAGNOSTICS"); 1199 BusLogic_Error("HOST ADAPTER STATUS REGISTER = %02X\n", HostAdapter, StatusRegister.All); 1200 if (StatusRegister.sr.DataInRegisterReady) { 1201 unsigned char ErrorCode = BusLogic_ReadDataInRegister(HostAdapter); 1202 BusLogic_Error("HOST ADAPTER ERROR CODE = %d\n", HostAdapter, ErrorCode); 1203 } 1204 return false; 1205 } 1206 /* 1207 Indicate the Host Adapter Hard Reset completed successfully. 1208 */ 1209 return true; 1210} 1211 1212 1213/* 1214 BusLogic_CheckHostAdapter checks to be sure this really is a BusLogic 1215 Host Adapter. 1216*/ 1217 1218static bool __init BusLogic_CheckHostAdapter(struct BusLogic_HostAdapter *HostAdapter) 1219{ 1220 struct BusLogic_ExtendedSetupInformation ExtendedSetupInformation; 1221 unsigned char RequestedReplyLength; 1222 bool Result = true; 1223 /* 1224 FlashPoint Host Adapters do not require this protection. 1225 */ 1226 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) 1227 return true; 1228 /* 1229 Issue the Inquire Extended Setup Information command. Only genuine 1230 BusLogic Host Adapters and true clones support this command. Adaptec 1542C 1231 series Host Adapters that respond to the Geometry Register I/O port will 1232 fail this command. 1233 */ 1234 RequestedReplyLength = sizeof(ExtendedSetupInformation); 1235 if (BusLogic_Command(HostAdapter, BusLogic_InquireExtendedSetupInformation, &RequestedReplyLength, sizeof(RequestedReplyLength), &ExtendedSetupInformation, sizeof(ExtendedSetupInformation)) 1236 != sizeof(ExtendedSetupInformation)) 1237 Result = false; 1238 /* 1239 Provide tracing information if requested and return. 1240 */ 1241 if (BusLogic_GlobalOptions.TraceProbe) 1242 BusLogic_Notice("BusLogic_Check(0x%X): MultiMaster %s\n", HostAdapter, HostAdapter->IO_Address, (Result ? "Found" : "Not Found")); 1243 return Result; 1244} 1245 1246 1247/* 1248 BusLogic_ReadHostAdapterConfiguration reads the Configuration Information 1249 from Host Adapter and initializes the Host Adapter structure. 1250*/ 1251 1252static bool __init BusLogic_ReadHostAdapterConfiguration(struct BusLogic_HostAdapter 1253 *HostAdapter) 1254{ 1255 struct BusLogic_BoardID BoardID; 1256 struct BusLogic_Configuration Configuration; 1257 struct BusLogic_SetupInformation SetupInformation; 1258 struct BusLogic_ExtendedSetupInformation ExtendedSetupInformation; 1259 unsigned char HostAdapterModelNumber[5]; 1260 unsigned char FirmwareVersion3rdDigit; 1261 unsigned char FirmwareVersionLetter; 1262 struct BusLogic_PCIHostAdapterInformation PCIHostAdapterInformation; 1263 struct BusLogic_FetchHostAdapterLocalRAMRequest FetchHostAdapterLocalRAMRequest; 1264 struct BusLogic_AutoSCSIData AutoSCSIData; 1265 union BusLogic_GeometryRegister GeometryRegister; 1266 unsigned char RequestedReplyLength; 1267 unsigned char *TargetPointer, Character; 1268 int TargetID, i; 1269 /* 1270 Configuration Information for FlashPoint Host Adapters is provided in the 1271 FlashPoint_Info structure by the FlashPoint SCCB Manager's Probe Function. 1272 Initialize fields in the Host Adapter structure from the FlashPoint_Info 1273 structure. 1274 */ 1275 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) { 1276 struct FlashPoint_Info *FlashPointInfo = &HostAdapter->FlashPointInfo; 1277 TargetPointer = HostAdapter->ModelName; 1278 *TargetPointer++ = 'B'; 1279 *TargetPointer++ = 'T'; 1280 *TargetPointer++ = '-'; 1281 for (i = 0; i < sizeof(FlashPointInfo->ModelNumber); i++) 1282 *TargetPointer++ = FlashPointInfo->ModelNumber[i]; 1283 *TargetPointer++ = '\0'; 1284 strcpy(HostAdapter->FirmwareVersion, FlashPoint_FirmwareVersion); 1285 HostAdapter->SCSI_ID = FlashPointInfo->SCSI_ID; 1286 HostAdapter->ExtendedTranslationEnabled = FlashPointInfo->ExtendedTranslationEnabled; 1287 HostAdapter->ParityCheckingEnabled = FlashPointInfo->ParityCheckingEnabled; 1288 HostAdapter->BusResetEnabled = !FlashPointInfo->HostSoftReset; 1289 HostAdapter->LevelSensitiveInterrupt = true; 1290 HostAdapter->HostWideSCSI = FlashPointInfo->HostWideSCSI; 1291 HostAdapter->HostDifferentialSCSI = false; 1292 HostAdapter->HostSupportsSCAM = true; 1293 HostAdapter->HostUltraSCSI = true; 1294 HostAdapter->ExtendedLUNSupport = true; 1295 HostAdapter->TerminationInfoValid = true; 1296 HostAdapter->LowByteTerminated = FlashPointInfo->LowByteTerminated; 1297 HostAdapter->HighByteTerminated = FlashPointInfo->HighByteTerminated; 1298 HostAdapter->SCAM_Enabled = FlashPointInfo->SCAM_Enabled; 1299 HostAdapter->SCAM_Level2 = FlashPointInfo->SCAM_Level2; 1300 HostAdapter->DriverScatterGatherLimit = BusLogic_ScatterGatherLimit; 1301 HostAdapter->MaxTargetDevices = (HostAdapter->HostWideSCSI ? 16 : 8); 1302 HostAdapter->MaxLogicalUnits = 32; 1303 HostAdapter->InitialCCBs = 4 * BusLogic_CCB_AllocationGroupSize; 1304 HostAdapter->IncrementalCCBs = BusLogic_CCB_AllocationGroupSize; 1305 HostAdapter->DriverQueueDepth = 255; 1306 HostAdapter->HostAdapterQueueDepth = HostAdapter->DriverQueueDepth; 1307 HostAdapter->SynchronousPermitted = FlashPointInfo->SynchronousPermitted; 1308 HostAdapter->FastPermitted = FlashPointInfo->FastPermitted; 1309 HostAdapter->UltraPermitted = FlashPointInfo->UltraPermitted; 1310 HostAdapter->WidePermitted = FlashPointInfo->WidePermitted; 1311 HostAdapter->DisconnectPermitted = FlashPointInfo->DisconnectPermitted; 1312 HostAdapter->TaggedQueuingPermitted = 0xFFFF; 1313 goto Common; 1314 } 1315 /* 1316 Issue the Inquire Board ID command. 1317 */ 1318 if (BusLogic_Command(HostAdapter, BusLogic_InquireBoardID, NULL, 0, &BoardID, sizeof(BoardID)) != sizeof(BoardID)) 1319 return BusLogic_Failure(HostAdapter, "INQUIRE BOARD ID"); 1320 /* 1321 Issue the Inquire Configuration command. 1322 */ 1323 if (BusLogic_Command(HostAdapter, BusLogic_InquireConfiguration, NULL, 0, &Configuration, sizeof(Configuration)) 1324 != sizeof(Configuration)) 1325 return BusLogic_Failure(HostAdapter, "INQUIRE CONFIGURATION"); 1326 /* 1327 Issue the Inquire Setup Information command. 1328 */ 1329 RequestedReplyLength = sizeof(SetupInformation); 1330 if (BusLogic_Command(HostAdapter, BusLogic_InquireSetupInformation, &RequestedReplyLength, sizeof(RequestedReplyLength), &SetupInformation, sizeof(SetupInformation)) 1331 != sizeof(SetupInformation)) 1332 return BusLogic_Failure(HostAdapter, "INQUIRE SETUP INFORMATION"); 1333 /* 1334 Issue the Inquire Extended Setup Information command. 1335 */ 1336 RequestedReplyLength = sizeof(ExtendedSetupInformation); 1337 if (BusLogic_Command(HostAdapter, BusLogic_InquireExtendedSetupInformation, &RequestedReplyLength, sizeof(RequestedReplyLength), &ExtendedSetupInformation, sizeof(ExtendedSetupInformation)) 1338 != sizeof(ExtendedSetupInformation)) 1339 return BusLogic_Failure(HostAdapter, "INQUIRE EXTENDED SETUP INFORMATION"); 1340 /* 1341 Issue the Inquire Firmware Version 3rd Digit command. 1342 */ 1343 FirmwareVersion3rdDigit = '\0'; 1344 if (BoardID.FirmwareVersion1stDigit > '0') 1345 if (BusLogic_Command(HostAdapter, BusLogic_InquireFirmwareVersion3rdDigit, NULL, 0, &FirmwareVersion3rdDigit, sizeof(FirmwareVersion3rdDigit)) 1346 != sizeof(FirmwareVersion3rdDigit)) 1347 return BusLogic_Failure(HostAdapter, "INQUIRE FIRMWARE 3RD DIGIT"); 1348 /* 1349 Issue the Inquire Host Adapter Model Number command. 1350 */ 1351 if (ExtendedSetupInformation.BusType == 'A' && BoardID.FirmwareVersion1stDigit == '2') 1352 /* BusLogic BT-542B ISA 2.xx */ 1353 strcpy(HostAdapterModelNumber, "542B"); 1354 else if (ExtendedSetupInformation.BusType == 'E' && BoardID.FirmwareVersion1stDigit == '2' && (BoardID.FirmwareVersion2ndDigit <= '1' || (BoardID.FirmwareVersion2ndDigit == '2' && FirmwareVersion3rdDigit == '0'))) 1355 /* BusLogic BT-742A EISA 2.1x or 2.20 */ 1356 strcpy(HostAdapterModelNumber, "742A"); 1357 else if (ExtendedSetupInformation.BusType == 'E' && BoardID.FirmwareVersion1stDigit == '0') 1358 /* AMI FastDisk EISA Series 441 0.x */ 1359 strcpy(HostAdapterModelNumber, "747A"); 1360 else { 1361 RequestedReplyLength = sizeof(HostAdapterModelNumber); 1362 if (BusLogic_Command(HostAdapter, BusLogic_InquireHostAdapterModelNumber, &RequestedReplyLength, sizeof(RequestedReplyLength), &HostAdapterModelNumber, sizeof(HostAdapterModelNumber)) 1363 != sizeof(HostAdapterModelNumber)) 1364 return BusLogic_Failure(HostAdapter, "INQUIRE HOST ADAPTER MODEL NUMBER"); 1365 } 1366 /* 1367 BusLogic MultiMaster Host Adapters can be identified by their model number 1368 and the major version number of their firmware as follows: 1369 1370 5.xx BusLogic "W" Series Host Adapters: 1371 BT-948/958/958D 1372 4.xx BusLogic "C" Series Host Adapters: 1373 BT-946C/956C/956CD/747C/757C/757CD/445C/545C/540CF 1374 3.xx BusLogic "S" Series Host Adapters: 1375 BT-747S/747D/757S/757D/445S/545S/542D 1376 BT-542B/742A (revision H) 1377 2.xx BusLogic "A" Series Host Adapters: 1378 BT-542B/742A (revision G and below) 1379 0.xx AMI FastDisk VLB/EISA BusLogic Clone Host Adapter 1380 */ 1381 /* 1382 Save the Model Name and Host Adapter Name in the Host Adapter structure. 1383 */ 1384 TargetPointer = HostAdapter->ModelName; 1385 *TargetPointer++ = 'B'; 1386 *TargetPointer++ = 'T'; 1387 *TargetPointer++ = '-'; 1388 for (i = 0; i < sizeof(HostAdapterModelNumber); i++) { 1389 Character = HostAdapterModelNumber[i]; 1390 if (Character == ' ' || Character == '\0') 1391 break; 1392 *TargetPointer++ = Character; 1393 } 1394 *TargetPointer++ = '\0'; 1395 /* 1396 Save the Firmware Version in the Host Adapter structure. 1397 */ 1398 TargetPointer = HostAdapter->FirmwareVersion; 1399 *TargetPointer++ = BoardID.FirmwareVersion1stDigit; 1400 *TargetPointer++ = '.'; 1401 *TargetPointer++ = BoardID.FirmwareVersion2ndDigit; 1402 if (FirmwareVersion3rdDigit != ' ' && FirmwareVersion3rdDigit != '\0') 1403 *TargetPointer++ = FirmwareVersion3rdDigit; 1404 *TargetPointer = '\0'; 1405 /* 1406 Issue the Inquire Firmware Version Letter command. 1407 */ 1408 if (strcmp(HostAdapter->FirmwareVersion, "3.3") >= 0) { 1409 if (BusLogic_Command(HostAdapter, BusLogic_InquireFirmwareVersionLetter, NULL, 0, &FirmwareVersionLetter, sizeof(FirmwareVersionLetter)) 1410 != sizeof(FirmwareVersionLetter)) 1411 return BusLogic_Failure(HostAdapter, "INQUIRE FIRMWARE VERSION LETTER"); 1412 if (FirmwareVersionLetter != ' ' && FirmwareVersionLetter != '\0') 1413 *TargetPointer++ = FirmwareVersionLetter; 1414 *TargetPointer = '\0'; 1415 } 1416 /* 1417 Save the Host Adapter SCSI ID in the Host Adapter structure. 1418 */ 1419 HostAdapter->SCSI_ID = Configuration.HostAdapterID; 1420 /* 1421 Determine the Bus Type and save it in the Host Adapter structure, determine 1422 and save the IRQ Channel if necessary, and determine and save the DMA 1423 Channel for ISA Host Adapters. 1424 */ 1425 HostAdapter->HostAdapterBusType = BusLogic_HostAdapterBusTypes[HostAdapter->ModelName[3] - '4']; 1426 if (HostAdapter->IRQ_Channel == 0) { 1427 if (Configuration.IRQ_Channel9) 1428 HostAdapter->IRQ_Channel = 9; 1429 else if (Configuration.IRQ_Channel10) 1430 HostAdapter->IRQ_Channel = 10; 1431 else if (Configuration.IRQ_Channel11) 1432 HostAdapter->IRQ_Channel = 11; 1433 else if (Configuration.IRQ_Channel12) 1434 HostAdapter->IRQ_Channel = 12; 1435 else if (Configuration.IRQ_Channel14) 1436 HostAdapter->IRQ_Channel = 14; 1437 else if (Configuration.IRQ_Channel15) 1438 HostAdapter->IRQ_Channel = 15; 1439 } 1440 if (HostAdapter->HostAdapterBusType == BusLogic_ISA_Bus) { 1441 if (Configuration.DMA_Channel5) 1442 HostAdapter->DMA_Channel = 5; 1443 else if (Configuration.DMA_Channel6) 1444 HostAdapter->DMA_Channel = 6; 1445 else if (Configuration.DMA_Channel7) 1446 HostAdapter->DMA_Channel = 7; 1447 } 1448 /* 1449 Determine whether Extended Translation is enabled and save it in 1450 the Host Adapter structure. 1451 */ 1452 GeometryRegister.All = BusLogic_ReadGeometryRegister(HostAdapter); 1453 HostAdapter->ExtendedTranslationEnabled = GeometryRegister.gr.ExtendedTranslationEnabled; 1454 /* 1455 Save the Scatter Gather Limits, Level Sensitive Interrupt flag, Wide 1456 SCSI flag, Differential SCSI flag, SCAM Supported flag, and 1457 Ultra SCSI flag in the Host Adapter structure. 1458 */ 1459 HostAdapter->HostAdapterScatterGatherLimit = ExtendedSetupInformation.ScatterGatherLimit; 1460 HostAdapter->DriverScatterGatherLimit = HostAdapter->HostAdapterScatterGatherLimit; 1461 if (HostAdapter->HostAdapterScatterGatherLimit > BusLogic_ScatterGatherLimit) 1462 HostAdapter->DriverScatterGatherLimit = BusLogic_ScatterGatherLimit; 1463 if (ExtendedSetupInformation.Misc.LevelSensitiveInterrupt) 1464 HostAdapter->LevelSensitiveInterrupt = true; 1465 HostAdapter->HostWideSCSI = ExtendedSetupInformation.HostWideSCSI; 1466 HostAdapter->HostDifferentialSCSI = ExtendedSetupInformation.HostDifferentialSCSI; 1467 HostAdapter->HostSupportsSCAM = ExtendedSetupInformation.HostSupportsSCAM; 1468 HostAdapter->HostUltraSCSI = ExtendedSetupInformation.HostUltraSCSI; 1469 /* 1470 Determine whether Extended LUN Format CCBs are supported and save the 1471 information in the Host Adapter structure. 1472 */ 1473 if (HostAdapter->FirmwareVersion[0] == '5' || (HostAdapter->FirmwareVersion[0] == '4' && HostAdapter->HostWideSCSI)) 1474 HostAdapter->ExtendedLUNSupport = true; 1475 /* 1476 Issue the Inquire PCI Host Adapter Information command to read the 1477 Termination Information from "W" series MultiMaster Host Adapters. 1478 */ 1479 if (HostAdapter->FirmwareVersion[0] == '5') { 1480 if (BusLogic_Command(HostAdapter, BusLogic_InquirePCIHostAdapterInformation, NULL, 0, &PCIHostAdapterInformation, sizeof(PCIHostAdapterInformation)) 1481 != sizeof(PCIHostAdapterInformation)) 1482 return BusLogic_Failure(HostAdapter, "INQUIRE PCI HOST ADAPTER INFORMATION"); 1483 /* 1484 Save the Termination Information in the Host Adapter structure. 1485 */ 1486 if (PCIHostAdapterInformation.GenericInfoValid) { 1487 HostAdapter->TerminationInfoValid = true; 1488 HostAdapter->LowByteTerminated = PCIHostAdapterInformation.LowByteTerminated; 1489 HostAdapter->HighByteTerminated = PCIHostAdapterInformation.HighByteTerminated; 1490 } 1491 } 1492 /* 1493 Issue the Fetch Host Adapter Local RAM command to read the AutoSCSI data 1494 from "W" and "C" series MultiMaster Host Adapters. 1495 */ 1496 if (HostAdapter->FirmwareVersion[0] >= '4') { 1497 FetchHostAdapterLocalRAMRequest.ByteOffset = BusLogic_AutoSCSI_BaseOffset; 1498 FetchHostAdapterLocalRAMRequest.ByteCount = sizeof(AutoSCSIData); 1499 if (BusLogic_Command(HostAdapter, BusLogic_FetchHostAdapterLocalRAM, &FetchHostAdapterLocalRAMRequest, sizeof(FetchHostAdapterLocalRAMRequest), &AutoSCSIData, sizeof(AutoSCSIData)) 1500 != sizeof(AutoSCSIData)) 1501 return BusLogic_Failure(HostAdapter, "FETCH HOST ADAPTER LOCAL RAM"); 1502 /* 1503 Save the Parity Checking Enabled, Bus Reset Enabled, and Termination 1504 Information in the Host Adapter structure. 1505 */ 1506 HostAdapter->ParityCheckingEnabled = AutoSCSIData.ParityCheckingEnabled; 1507 HostAdapter->BusResetEnabled = AutoSCSIData.BusResetEnabled; 1508 if (HostAdapter->FirmwareVersion[0] == '4') { 1509 HostAdapter->TerminationInfoValid = true; 1510 HostAdapter->LowByteTerminated = AutoSCSIData.LowByteTerminated; 1511 HostAdapter->HighByteTerminated = AutoSCSIData.HighByteTerminated; 1512 } 1513 /* 1514 Save the Wide Permitted, Fast Permitted, Synchronous Permitted, 1515 Disconnect Permitted, Ultra Permitted, and SCAM Information in the 1516 Host Adapter structure. 1517 */ 1518 HostAdapter->WidePermitted = AutoSCSIData.WidePermitted; 1519 HostAdapter->FastPermitted = AutoSCSIData.FastPermitted; 1520 HostAdapter->SynchronousPermitted = AutoSCSIData.SynchronousPermitted; 1521 HostAdapter->DisconnectPermitted = AutoSCSIData.DisconnectPermitted; 1522 if (HostAdapter->HostUltraSCSI) 1523 HostAdapter->UltraPermitted = AutoSCSIData.UltraPermitted; 1524 if (HostAdapter->HostSupportsSCAM) { 1525 HostAdapter->SCAM_Enabled = AutoSCSIData.SCAM_Enabled; 1526 HostAdapter->SCAM_Level2 = AutoSCSIData.SCAM_Level2; 1527 } 1528 } 1529 /* 1530 Initialize fields in the Host Adapter structure for "S" and "A" series 1531 MultiMaster Host Adapters. 1532 */ 1533 if (HostAdapter->FirmwareVersion[0] < '4') { 1534 if (SetupInformation.SynchronousInitiationEnabled) { 1535 HostAdapter->SynchronousPermitted = 0xFF; 1536 if (HostAdapter->HostAdapterBusType == BusLogic_EISA_Bus) { 1537 if (ExtendedSetupInformation.Misc.FastOnEISA) 1538 HostAdapter->FastPermitted = 0xFF; 1539 if (strcmp(HostAdapter->ModelName, "BT-757") == 0) 1540 HostAdapter->WidePermitted = 0xFF; 1541 } 1542 } 1543 HostAdapter->DisconnectPermitted = 0xFF; 1544 HostAdapter->ParityCheckingEnabled = SetupInformation.ParityCheckingEnabled; 1545 HostAdapter->BusResetEnabled = true; 1546 } 1547 /* 1548 Determine the maximum number of Target IDs and Logical Units supported by 1549 this driver for Wide and Narrow Host Adapters. 1550 */ 1551 HostAdapter->MaxTargetDevices = (HostAdapter->HostWideSCSI ? 16 : 8); 1552 HostAdapter->MaxLogicalUnits = (HostAdapter->ExtendedLUNSupport ? 32 : 8); 1553 /* 1554 Select appropriate values for the Mailbox Count, Driver Queue Depth, 1555 Initial CCBs, and Incremental CCBs variables based on whether or not Strict 1556 Round Robin Mode is supported. If Strict Round Robin Mode is supported, 1557 then there is no performance degradation in using the maximum possible 1558 number of Outgoing and Incoming Mailboxes and allowing the Tagged and 1559 Untagged Queue Depths to determine the actual utilization. If Strict Round 1560 Robin Mode is not supported, then the Host Adapter must scan all the 1561 Outgoing Mailboxes whenever an Outgoing Mailbox entry is made, which can 1562 cause a substantial performance penalty. The host adapters actually have 1563 room to store the following number of CCBs internally; that is, they can 1564 internally queue and manage this many active commands on the SCSI bus 1565 simultaneously. Performance measurements demonstrate that the Driver Queue 1566 Depth should be set to the Mailbox Count, rather than the Host Adapter 1567 Queue Depth (internal CCB capacity), as it is more efficient to have the 1568 queued commands waiting in Outgoing Mailboxes if necessary than to block 1569 the process in the higher levels of the SCSI Subsystem. 1570 1571 192 BT-948/958/958D 1572 100 BT-946C/956C/956CD/747C/757C/757CD/445C 1573 50 BT-545C/540CF 1574 30 BT-747S/747D/757S/757D/445S/545S/542D/542B/742A 1575 */ 1576 if (HostAdapter->FirmwareVersion[0] == '5') 1577 HostAdapter->HostAdapterQueueDepth = 192; 1578 else if (HostAdapter->FirmwareVersion[0] == '4') 1579 HostAdapter->HostAdapterQueueDepth = (HostAdapter->HostAdapterBusType != BusLogic_ISA_Bus ? 100 : 50); 1580 else 1581 HostAdapter->HostAdapterQueueDepth = 30; 1582 if (strcmp(HostAdapter->FirmwareVersion, "3.31") >= 0) { 1583 HostAdapter->StrictRoundRobinModeSupport = true; 1584 HostAdapter->MailboxCount = BusLogic_MaxMailboxes; 1585 } else { 1586 HostAdapter->StrictRoundRobinModeSupport = false; 1587 HostAdapter->MailboxCount = 32; 1588 } 1589 HostAdapter->DriverQueueDepth = HostAdapter->MailboxCount; 1590 HostAdapter->InitialCCBs = 4 * BusLogic_CCB_AllocationGroupSize; 1591 HostAdapter->IncrementalCCBs = BusLogic_CCB_AllocationGroupSize; 1592 /* 1593 Tagged Queuing support is available and operates properly on all "W" series 1594 MultiMaster Host Adapters, on "C" series MultiMaster Host Adapters with 1595 firmware version 4.22 and above, and on "S" series MultiMaster Host 1596 Adapters with firmware version 3.35 and above. 1597 */ 1598 HostAdapter->TaggedQueuingPermitted = 0; 1599 switch (HostAdapter->FirmwareVersion[0]) { 1600 case '5': 1601 HostAdapter->TaggedQueuingPermitted = 0xFFFF; 1602 break; 1603 case '4': 1604 if (strcmp(HostAdapter->FirmwareVersion, "4.22") >= 0) 1605 HostAdapter->TaggedQueuingPermitted = 0xFFFF; 1606 break; 1607 case '3': 1608 if (strcmp(HostAdapter->FirmwareVersion, "3.35") >= 0) 1609 HostAdapter->TaggedQueuingPermitted = 0xFFFF; 1610 break; 1611 } 1612 /* 1613 Determine the Host Adapter BIOS Address if the BIOS is enabled and 1614 save it in the Host Adapter structure. The BIOS is disabled if the 1615 BIOS_Address is 0. 1616 */ 1617 HostAdapter->BIOS_Address = ExtendedSetupInformation.BIOS_Address << 12; 1618 /* 1619 ISA Host Adapters require Bounce Buffers if there is more than 16MB memory. 1620 */ 1621 if (HostAdapter->HostAdapterBusType == BusLogic_ISA_Bus && (void *) high_memory > (void *) MAX_DMA_ADDRESS) 1622 HostAdapter->BounceBuffersRequired = true; 1623 /* 1624 BusLogic BT-445S Host Adapters prior to board revision E have a hardware 1625 bug whereby when the BIOS is enabled, transfers to/from the same address 1626 range the BIOS occupies modulo 16MB are handled incorrectly. Only properly 1627 functioning BT-445S Host Adapters have firmware version 3.37, so require 1628 that ISA Bounce Buffers be used for the buggy BT-445S models if there is 1629 more than 16MB memory. 1630 */ 1631 if (HostAdapter->BIOS_Address > 0 && strcmp(HostAdapter->ModelName, "BT-445S") == 0 && strcmp(HostAdapter->FirmwareVersion, "3.37") < 0 && (void *) high_memory > (void *) MAX_DMA_ADDRESS) 1632 HostAdapter->BounceBuffersRequired = true; 1633 /* 1634 Initialize parameters common to MultiMaster and FlashPoint Host Adapters. 1635 */ 1636 Common: 1637 /* 1638 Initialize the Host Adapter Full Model Name from the Model Name. 1639 */ 1640 strcpy(HostAdapter->FullModelName, "BusLogic "); 1641 strcat(HostAdapter->FullModelName, HostAdapter->ModelName); 1642 /* 1643 Select an appropriate value for the Tagged Queue Depth either from a 1644 BusLogic Driver Options specification, or based on whether this Host 1645 Adapter requires that ISA Bounce Buffers be used. The Tagged Queue Depth 1646 is left at 0 for automatic determination in BusLogic_SelectQueueDepths. 1647 Initialize the Untagged Queue Depth. 1648 */ 1649 for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++) { 1650 unsigned char QueueDepth = 0; 1651 if (HostAdapter->DriverOptions != NULL && HostAdapter->DriverOptions->QueueDepth[TargetID] > 0) 1652 QueueDepth = HostAdapter->DriverOptions->QueueDepth[TargetID]; 1653 else if (HostAdapter->BounceBuffersRequired) 1654 QueueDepth = BusLogic_TaggedQueueDepthBB; 1655 HostAdapter->QueueDepth[TargetID] = QueueDepth; 1656 } 1657 if (HostAdapter->BounceBuffersRequired) 1658 HostAdapter->UntaggedQueueDepth = BusLogic_UntaggedQueueDepthBB; 1659 else 1660 HostAdapter->UntaggedQueueDepth = BusLogic_UntaggedQueueDepth; 1661 if (HostAdapter->DriverOptions != NULL) 1662 HostAdapter->CommonQueueDepth = HostAdapter->DriverOptions->CommonQueueDepth; 1663 if (HostAdapter->CommonQueueDepth > 0 && HostAdapter->CommonQueueDepth < HostAdapter->UntaggedQueueDepth) 1664 HostAdapter->UntaggedQueueDepth = HostAdapter->CommonQueueDepth; 1665 /* 1666 Tagged Queuing is only allowed if Disconnect/Reconnect is permitted. 1667 Therefore, mask the Tagged Queuing Permitted Default bits with the 1668 Disconnect/Reconnect Permitted bits. 1669 */ 1670 HostAdapter->TaggedQueuingPermitted &= HostAdapter->DisconnectPermitted; 1671 /* 1672 Combine the default Tagged Queuing Permitted bits with any BusLogic Driver 1673 Options Tagged Queuing specification. 1674 */ 1675 if (HostAdapter->DriverOptions != NULL) 1676 HostAdapter->TaggedQueuingPermitted = 1677 (HostAdapter->DriverOptions->TaggedQueuingPermitted & HostAdapter->DriverOptions->TaggedQueuingPermittedMask) | (HostAdapter->TaggedQueuingPermitted & ~HostAdapter->DriverOptions->TaggedQueuingPermittedMask); 1678 1679 /* 1680 Select an appropriate value for Bus Settle Time either from a BusLogic 1681 Driver Options specification, or from BusLogic_DefaultBusSettleTime. 1682 */ 1683 if (HostAdapter->DriverOptions != NULL && HostAdapter->DriverOptions->BusSettleTime > 0) 1684 HostAdapter->BusSettleTime = HostAdapter->DriverOptions->BusSettleTime; 1685 else 1686 HostAdapter->BusSettleTime = BusLogic_DefaultBusSettleTime; 1687 /* 1688 Indicate reading the Host Adapter Configuration completed successfully. 1689 */ 1690 return true; 1691} 1692 1693 1694/* 1695 BusLogic_ReportHostAdapterConfiguration reports the configuration of 1696 Host Adapter. 1697*/ 1698 1699static bool __init BusLogic_ReportHostAdapterConfiguration(struct BusLogic_HostAdapter 1700 *HostAdapter) 1701{ 1702 unsigned short AllTargetsMask = (1 << HostAdapter->MaxTargetDevices) - 1; 1703 unsigned short SynchronousPermitted, FastPermitted; 1704 unsigned short UltraPermitted, WidePermitted; 1705 unsigned short DisconnectPermitted, TaggedQueuingPermitted; 1706 bool CommonSynchronousNegotiation, CommonTaggedQueueDepth; 1707 char SynchronousString[BusLogic_MaxTargetDevices + 1]; 1708 char WideString[BusLogic_MaxTargetDevices + 1]; 1709 char DisconnectString[BusLogic_MaxTargetDevices + 1]; 1710 char TaggedQueuingString[BusLogic_MaxTargetDevices + 1]; 1711 char *SynchronousMessage = SynchronousString; 1712 char *WideMessage = WideString; 1713 char *DisconnectMessage = DisconnectString; 1714 char *TaggedQueuingMessage = TaggedQueuingString; 1715 int TargetID; 1716 BusLogic_Info("Configuring BusLogic Model %s %s%s%s%s SCSI Host Adapter\n", 1717 HostAdapter, HostAdapter->ModelName, 1718 BusLogic_HostAdapterBusNames[HostAdapter->HostAdapterBusType], (HostAdapter->HostWideSCSI ? " Wide" : ""), (HostAdapter->HostDifferentialSCSI ? " Differential" : ""), (HostAdapter->HostUltraSCSI ? " Ultra" : "")); 1719 BusLogic_Info(" Firmware Version: %s, I/O Address: 0x%X, " "IRQ Channel: %d/%s\n", HostAdapter, HostAdapter->FirmwareVersion, HostAdapter->IO_Address, HostAdapter->IRQ_Channel, (HostAdapter->LevelSensitiveInterrupt ? "Level" : "Edge")); 1720 if (HostAdapter->HostAdapterBusType != BusLogic_PCI_Bus) { 1721 BusLogic_Info(" DMA Channel: ", HostAdapter); 1722 if (HostAdapter->DMA_Channel > 0) 1723 BusLogic_Info("%d, ", HostAdapter, HostAdapter->DMA_Channel); 1724 else 1725 BusLogic_Info("None, ", HostAdapter); 1726 if (HostAdapter->BIOS_Address > 0) 1727 BusLogic_Info("BIOS Address: 0x%X, ", HostAdapter, HostAdapter->BIOS_Address); 1728 else 1729 BusLogic_Info("BIOS Address: None, ", HostAdapter); 1730 } else { 1731 BusLogic_Info(" PCI Bus: %d, Device: %d, Address: ", HostAdapter, HostAdapter->Bus, HostAdapter->Device); 1732 if (HostAdapter->PCI_Address > 0) 1733 BusLogic_Info("0x%X, ", HostAdapter, HostAdapter->PCI_Address); 1734 else 1735 BusLogic_Info("Unassigned, ", HostAdapter); 1736 } 1737 BusLogic_Info("Host Adapter SCSI ID: %d\n", HostAdapter, HostAdapter->SCSI_ID); 1738 BusLogic_Info(" Parity Checking: %s, Extended Translation: %s\n", HostAdapter, (HostAdapter->ParityCheckingEnabled ? "Enabled" : "Disabled"), (HostAdapter->ExtendedTranslationEnabled ? "Enabled" : "Disabled")); 1739 AllTargetsMask &= ~(1 << HostAdapter->SCSI_ID); 1740 SynchronousPermitted = HostAdapter->SynchronousPermitted & AllTargetsMask; 1741 FastPermitted = HostAdapter->FastPermitted & AllTargetsMask; 1742 UltraPermitted = HostAdapter->UltraPermitted & AllTargetsMask; 1743 if ((BusLogic_MultiMasterHostAdapterP(HostAdapter) && (HostAdapter->FirmwareVersion[0] >= '4' || HostAdapter->HostAdapterBusType == BusLogic_EISA_Bus)) || BusLogic_FlashPointHostAdapterP(HostAdapter)) { 1744 CommonSynchronousNegotiation = false; 1745 if (SynchronousPermitted == 0) { 1746 SynchronousMessage = "Disabled"; 1747 CommonSynchronousNegotiation = true; 1748 } else if (SynchronousPermitted == AllTargetsMask) { 1749 if (FastPermitted == 0) { 1750 SynchronousMessage = "Slow"; 1751 CommonSynchronousNegotiation = true; 1752 } else if (FastPermitted == AllTargetsMask) { 1753 if (UltraPermitted == 0) { 1754 SynchronousMessage = "Fast"; 1755 CommonSynchronousNegotiation = true; 1756 } else if (UltraPermitted == AllTargetsMask) { 1757 SynchronousMessage = "Ultra"; 1758 CommonSynchronousNegotiation = true; 1759 } 1760 } 1761 } 1762 if (!CommonSynchronousNegotiation) { 1763 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 1764 SynchronousString[TargetID] = ((!(SynchronousPermitted & (1 << TargetID))) ? 'N' : (!(FastPermitted & (1 << TargetID)) ? 'S' : (!(UltraPermitted & (1 << TargetID)) ? 'F' : 'U'))); 1765 SynchronousString[HostAdapter->SCSI_ID] = '#'; 1766 SynchronousString[HostAdapter->MaxTargetDevices] = '\0'; 1767 } 1768 } else 1769 SynchronousMessage = (SynchronousPermitted == 0 ? "Disabled" : "Enabled"); 1770 WidePermitted = HostAdapter->WidePermitted & AllTargetsMask; 1771 if (WidePermitted == 0) 1772 WideMessage = "Disabled"; 1773 else if (WidePermitted == AllTargetsMask) 1774 WideMessage = "Enabled"; 1775 else { 1776 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 1777 WideString[TargetID] = ((WidePermitted & (1 << TargetID)) ? 'Y' : 'N'); 1778 WideString[HostAdapter->SCSI_ID] = '#'; 1779 WideString[HostAdapter->MaxTargetDevices] = '\0'; 1780 } 1781 DisconnectPermitted = HostAdapter->DisconnectPermitted & AllTargetsMask; 1782 if (DisconnectPermitted == 0) 1783 DisconnectMessage = "Disabled"; 1784 else if (DisconnectPermitted == AllTargetsMask) 1785 DisconnectMessage = "Enabled"; 1786 else { 1787 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 1788 DisconnectString[TargetID] = ((DisconnectPermitted & (1 << TargetID)) ? 'Y' : 'N'); 1789 DisconnectString[HostAdapter->SCSI_ID] = '#'; 1790 DisconnectString[HostAdapter->MaxTargetDevices] = '\0'; 1791 } 1792 TaggedQueuingPermitted = HostAdapter->TaggedQueuingPermitted & AllTargetsMask; 1793 if (TaggedQueuingPermitted == 0) 1794 TaggedQueuingMessage = "Disabled"; 1795 else if (TaggedQueuingPermitted == AllTargetsMask) 1796 TaggedQueuingMessage = "Enabled"; 1797 else { 1798 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 1799 TaggedQueuingString[TargetID] = ((TaggedQueuingPermitted & (1 << TargetID)) ? 'Y' : 'N'); 1800 TaggedQueuingString[HostAdapter->SCSI_ID] = '#'; 1801 TaggedQueuingString[HostAdapter->MaxTargetDevices] = '\0'; 1802 } 1803 BusLogic_Info(" Synchronous Negotiation: %s, Wide Negotiation: %s\n", HostAdapter, SynchronousMessage, WideMessage); 1804 BusLogic_Info(" Disconnect/Reconnect: %s, Tagged Queuing: %s\n", HostAdapter, DisconnectMessage, TaggedQueuingMessage); 1805 if (BusLogic_MultiMasterHostAdapterP(HostAdapter)) { 1806 BusLogic_Info(" Scatter/Gather Limit: %d of %d segments, " "Mailboxes: %d\n", HostAdapter, HostAdapter->DriverScatterGatherLimit, HostAdapter->HostAdapterScatterGatherLimit, HostAdapter->MailboxCount); 1807 BusLogic_Info(" Driver Queue Depth: %d, " "Host Adapter Queue Depth: %d\n", HostAdapter, HostAdapter->DriverQueueDepth, HostAdapter->HostAdapterQueueDepth); 1808 } else 1809 BusLogic_Info(" Driver Queue Depth: %d, " "Scatter/Gather Limit: %d segments\n", HostAdapter, HostAdapter->DriverQueueDepth, HostAdapter->DriverScatterGatherLimit); 1810 BusLogic_Info(" Tagged Queue Depth: ", HostAdapter); 1811 CommonTaggedQueueDepth = true; 1812 for (TargetID = 1; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 1813 if (HostAdapter->QueueDepth[TargetID] != HostAdapter->QueueDepth[0]) { 1814 CommonTaggedQueueDepth = false; 1815 break; 1816 } 1817 if (CommonTaggedQueueDepth) { 1818 if (HostAdapter->QueueDepth[0] > 0) 1819 BusLogic_Info("%d", HostAdapter, HostAdapter->QueueDepth[0]); 1820 else 1821 BusLogic_Info("Automatic", HostAdapter); 1822 } else 1823 BusLogic_Info("Individual", HostAdapter); 1824 BusLogic_Info(", Untagged Queue Depth: %d\n", HostAdapter, HostAdapter->UntaggedQueueDepth); 1825 if (HostAdapter->TerminationInfoValid) { 1826 if (HostAdapter->HostWideSCSI) 1827 BusLogic_Info(" SCSI Bus Termination: %s", HostAdapter, (HostAdapter->LowByteTerminated ? (HostAdapter->HighByteTerminated ? "Both Enabled" : "Low Enabled") 1828 : (HostAdapter->HighByteTerminated ? "High Enabled" : "Both Disabled"))); 1829 else 1830 BusLogic_Info(" SCSI Bus Termination: %s", HostAdapter, (HostAdapter->LowByteTerminated ? "Enabled" : "Disabled")); 1831 if (HostAdapter->HostSupportsSCAM) 1832 BusLogic_Info(", SCAM: %s", HostAdapter, (HostAdapter->SCAM_Enabled ? (HostAdapter->SCAM_Level2 ? "Enabled, Level 2" : "Enabled, Level 1") 1833 : "Disabled")); 1834 BusLogic_Info("\n", HostAdapter); 1835 } 1836 /* 1837 Indicate reporting the Host Adapter configuration completed successfully. 1838 */ 1839 return true; 1840} 1841 1842 1843/* 1844 BusLogic_AcquireResources acquires the system resources necessary to use 1845 Host Adapter. 1846*/ 1847 1848static bool __init BusLogic_AcquireResources(struct BusLogic_HostAdapter *HostAdapter) 1849{ 1850 if (HostAdapter->IRQ_Channel == 0) { 1851 BusLogic_Error("NO LEGAL INTERRUPT CHANNEL ASSIGNED - DETACHING\n", HostAdapter); 1852 return false; 1853 } 1854 /* 1855 Acquire shared access to the IRQ Channel. 1856 */ 1857 if (request_irq(HostAdapter->IRQ_Channel, BusLogic_InterruptHandler, IRQF_SHARED, HostAdapter->FullModelName, HostAdapter) < 0) { 1858 BusLogic_Error("UNABLE TO ACQUIRE IRQ CHANNEL %d - DETACHING\n", HostAdapter, HostAdapter->IRQ_Channel); 1859 return false; 1860 } 1861 HostAdapter->IRQ_ChannelAcquired = true; 1862 /* 1863 Acquire exclusive access to the DMA Channel. 1864 */ 1865 if (HostAdapter->DMA_Channel > 0) { 1866 if (request_dma(HostAdapter->DMA_Channel, HostAdapter->FullModelName) < 0) { 1867 BusLogic_Error("UNABLE TO ACQUIRE DMA CHANNEL %d - DETACHING\n", HostAdapter, HostAdapter->DMA_Channel); 1868 return false; 1869 } 1870 set_dma_mode(HostAdapter->DMA_Channel, DMA_MODE_CASCADE); 1871 enable_dma(HostAdapter->DMA_Channel); 1872 HostAdapter->DMA_ChannelAcquired = true; 1873 } 1874 /* 1875 Indicate the System Resource Acquisition completed successfully, 1876 */ 1877 return true; 1878} 1879 1880 1881/* 1882 BusLogic_ReleaseResources releases any system resources previously acquired 1883 by BusLogic_AcquireResources. 1884*/ 1885 1886static void BusLogic_ReleaseResources(struct BusLogic_HostAdapter *HostAdapter) 1887{ 1888 /* 1889 Release shared access to the IRQ Channel. 1890 */ 1891 if (HostAdapter->IRQ_ChannelAcquired) 1892 free_irq(HostAdapter->IRQ_Channel, HostAdapter); 1893 /* 1894 Release exclusive access to the DMA Channel. 1895 */ 1896 if (HostAdapter->DMA_ChannelAcquired) 1897 free_dma(HostAdapter->DMA_Channel); 1898 /* 1899 Release any allocated memory structs not released elsewhere 1900 */ 1901 if (HostAdapter->MailboxSpace) 1902 pci_free_consistent(HostAdapter->PCI_Device, HostAdapter->MailboxSize, HostAdapter->MailboxSpace, HostAdapter->MailboxSpaceHandle); 1903 pci_dev_put(HostAdapter->PCI_Device); 1904 HostAdapter->MailboxSpace = NULL; 1905 HostAdapter->MailboxSpaceHandle = 0; 1906 HostAdapter->MailboxSize = 0; 1907} 1908 1909 1910/* 1911 BusLogic_InitializeHostAdapter initializes Host Adapter. This is the only 1912 function called during SCSI Host Adapter detection which modifies the state 1913 of the Host Adapter from its initial power on or hard reset state. 1914*/ 1915 1916static bool BusLogic_InitializeHostAdapter(struct BusLogic_HostAdapter 1917 *HostAdapter) 1918{ 1919 struct BusLogic_ExtendedMailboxRequest ExtendedMailboxRequest; 1920 enum BusLogic_RoundRobinModeRequest RoundRobinModeRequest; 1921 enum BusLogic_SetCCBFormatRequest SetCCBFormatRequest; 1922 int TargetID; 1923 /* 1924 Initialize the pointers to the first and last CCBs that are queued for 1925 completion processing. 1926 */ 1927 HostAdapter->FirstCompletedCCB = NULL; 1928 HostAdapter->LastCompletedCCB = NULL; 1929 /* 1930 Initialize the Bus Device Reset Pending CCB, Tagged Queuing Active, 1931 Command Successful Flag, Active Commands, and Commands Since Reset 1932 for each Target Device. 1933 */ 1934 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 1935 HostAdapter->BusDeviceResetPendingCCB[TargetID] = NULL; 1936 HostAdapter->TargetFlags[TargetID].TaggedQueuingActive = false; 1937 HostAdapter->TargetFlags[TargetID].CommandSuccessfulFlag = false; 1938 HostAdapter->ActiveCommands[TargetID] = 0; 1939 HostAdapter->CommandsSinceReset[TargetID] = 0; 1940 } 1941 /* 1942 FlashPoint Host Adapters do not use Outgoing and Incoming Mailboxes. 1943 */ 1944 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) 1945 goto Done; 1946 /* 1947 Initialize the Outgoing and Incoming Mailbox pointers. 1948 */ 1949 HostAdapter->MailboxSize = HostAdapter->MailboxCount * (sizeof(struct BusLogic_OutgoingMailbox) + sizeof(struct BusLogic_IncomingMailbox)); 1950 HostAdapter->MailboxSpace = pci_alloc_consistent(HostAdapter->PCI_Device, HostAdapter->MailboxSize, &HostAdapter->MailboxSpaceHandle); 1951 if (HostAdapter->MailboxSpace == NULL) 1952 return BusLogic_Failure(HostAdapter, "MAILBOX ALLOCATION"); 1953 HostAdapter->FirstOutgoingMailbox = (struct BusLogic_OutgoingMailbox *) HostAdapter->MailboxSpace; 1954 HostAdapter->LastOutgoingMailbox = HostAdapter->FirstOutgoingMailbox + HostAdapter->MailboxCount - 1; 1955 HostAdapter->NextOutgoingMailbox = HostAdapter->FirstOutgoingMailbox; 1956 HostAdapter->FirstIncomingMailbox = (struct BusLogic_IncomingMailbox *) (HostAdapter->LastOutgoingMailbox + 1); 1957 HostAdapter->LastIncomingMailbox = HostAdapter->FirstIncomingMailbox + HostAdapter->MailboxCount - 1; 1958 HostAdapter->NextIncomingMailbox = HostAdapter->FirstIncomingMailbox; 1959 1960 /* 1961 Initialize the Outgoing and Incoming Mailbox structures. 1962 */ 1963 memset(HostAdapter->FirstOutgoingMailbox, 0, HostAdapter->MailboxCount * sizeof(struct BusLogic_OutgoingMailbox)); 1964 memset(HostAdapter->FirstIncomingMailbox, 0, HostAdapter->MailboxCount * sizeof(struct BusLogic_IncomingMailbox)); 1965 /* 1966 Initialize the Host Adapter's Pointer to the Outgoing/Incoming Mailboxes. 1967 */ 1968 ExtendedMailboxRequest.MailboxCount = HostAdapter->MailboxCount; 1969 ExtendedMailboxRequest.BaseMailboxAddress = (u32) HostAdapter->MailboxSpaceHandle; 1970 if (BusLogic_Command(HostAdapter, BusLogic_InitializeExtendedMailbox, &ExtendedMailboxRequest, sizeof(ExtendedMailboxRequest), NULL, 0) < 0) 1971 return BusLogic_Failure(HostAdapter, "MAILBOX INITIALIZATION"); 1972 /* 1973 Enable Strict Round Robin Mode if supported by the Host Adapter. In 1974 Strict Round Robin Mode, the Host Adapter only looks at the next Outgoing 1975 Mailbox for each new command, rather than scanning through all the 1976 Outgoing Mailboxes to find any that have new commands in them. Strict 1977 Round Robin Mode is significantly more efficient. 1978 */ 1979 if (HostAdapter->StrictRoundRobinModeSupport) { 1980 RoundRobinModeRequest = BusLogic_StrictRoundRobinMode; 1981 if (BusLogic_Command(HostAdapter, BusLogic_EnableStrictRoundRobinMode, &RoundRobinModeRequest, sizeof(RoundRobinModeRequest), NULL, 0) < 0) 1982 return BusLogic_Failure(HostAdapter, "ENABLE STRICT ROUND ROBIN MODE"); 1983 } 1984 /* 1985 For Host Adapters that support Extended LUN Format CCBs, issue the Set CCB 1986 Format command to allow 32 Logical Units per Target Device. 1987 */ 1988 if (HostAdapter->ExtendedLUNSupport) { 1989 SetCCBFormatRequest = BusLogic_ExtendedLUNFormatCCB; 1990 if (BusLogic_Command(HostAdapter, BusLogic_SetCCBFormat, &SetCCBFormatRequest, sizeof(SetCCBFormatRequest), NULL, 0) < 0) 1991 return BusLogic_Failure(HostAdapter, "SET CCB FORMAT"); 1992 } 1993 /* 1994 Announce Successful Initialization. 1995 */ 1996 Done: 1997 if (!HostAdapter->HostAdapterInitialized) { 1998 BusLogic_Info("*** %s Initialized Successfully ***\n", HostAdapter, HostAdapter->FullModelName); 1999 BusLogic_Info("\n", HostAdapter); 2000 } else 2001 BusLogic_Warning("*** %s Initialized Successfully ***\n", HostAdapter, HostAdapter->FullModelName); 2002 HostAdapter->HostAdapterInitialized = true; 2003 /* 2004 Indicate the Host Adapter Initialization completed successfully. 2005 */ 2006 return true; 2007} 2008 2009 2010/* 2011 BusLogic_TargetDeviceInquiry inquires about the Target Devices accessible 2012 through Host Adapter. 2013*/ 2014 2015static bool __init BusLogic_TargetDeviceInquiry(struct BusLogic_HostAdapter 2016 *HostAdapter) 2017{ 2018 u16 InstalledDevices; 2019 u8 InstalledDevicesID0to7[8]; 2020 struct BusLogic_SetupInformation SetupInformation; 2021 u8 SynchronousPeriod[BusLogic_MaxTargetDevices]; 2022 unsigned char RequestedReplyLength; 2023 int TargetID; 2024 /* 2025 Wait a few seconds between the Host Adapter Hard Reset which initiates 2026 a SCSI Bus Reset and issuing any SCSI Commands. Some SCSI devices get 2027 confused if they receive SCSI Commands too soon after a SCSI Bus Reset. 2028 */ 2029 BusLogic_Delay(HostAdapter->BusSettleTime); 2030 /* 2031 FlashPoint Host Adapters do not provide for Target Device Inquiry. 2032 */ 2033 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) 2034 return true; 2035 /* 2036 Inhibit the Target Device Inquiry if requested. 2037 */ 2038 if (HostAdapter->DriverOptions != NULL && HostAdapter->DriverOptions->LocalOptions.InhibitTargetInquiry) 2039 return true; 2040 /* 2041 Issue the Inquire Target Devices command for host adapters with firmware 2042 version 4.25 or later, or the Inquire Installed Devices ID 0 to 7 command 2043 for older host adapters. This is necessary to force Synchronous Transfer 2044 Negotiation so that the Inquire Setup Information and Inquire Synchronous 2045 Period commands will return valid data. The Inquire Target Devices command 2046 is preferable to Inquire Installed Devices ID 0 to 7 since it only probes 2047 Logical Unit 0 of each Target Device. 2048 */ 2049 if (strcmp(HostAdapter->FirmwareVersion, "4.25") >= 0) { 2050 2051 /* 2052 * Issue a Inquire Target Devices command. Inquire Target Devices only 2053 * tests Logical Unit 0 of each Target Device unlike the Inquire Installed 2054 * Devices commands which test Logical Units 0 - 7. Two bytes are 2055 * returned, where byte 0 bit 0 set indicates that Target Device 0 exists, 2056 * and so on. 2057 */ 2058 2059 if (BusLogic_Command(HostAdapter, BusLogic_InquireTargetDevices, NULL, 0, &InstalledDevices, sizeof(InstalledDevices)) 2060 != sizeof(InstalledDevices)) 2061 return BusLogic_Failure(HostAdapter, "INQUIRE TARGET DEVICES"); 2062 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2063 HostAdapter->TargetFlags[TargetID].TargetExists = (InstalledDevices & (1 << TargetID) ? true : false); 2064 } else { 2065 2066 /* 2067 * Issue an Inquire Installed Devices command. For each Target Device, 2068 * a byte is returned where bit 0 set indicates that Logical Unit 0 2069 * exists, bit 1 set indicates that Logical Unit 1 exists, and so on. 2070 */ 2071 2072 if (BusLogic_Command(HostAdapter, BusLogic_InquireInstalledDevicesID0to7, NULL, 0, &InstalledDevicesID0to7, sizeof(InstalledDevicesID0to7)) 2073 != sizeof(InstalledDevicesID0to7)) 2074 return BusLogic_Failure(HostAdapter, "INQUIRE INSTALLED DEVICES ID 0 TO 7"); 2075 for (TargetID = 0; TargetID < 8; TargetID++) 2076 HostAdapter->TargetFlags[TargetID].TargetExists = (InstalledDevicesID0to7[TargetID] != 0 ? true : false); 2077 } 2078 /* 2079 Issue the Inquire Setup Information command. 2080 */ 2081 RequestedReplyLength = sizeof(SetupInformation); 2082 if (BusLogic_Command(HostAdapter, BusLogic_InquireSetupInformation, &RequestedReplyLength, sizeof(RequestedReplyLength), &SetupInformation, sizeof(SetupInformation)) 2083 != sizeof(SetupInformation)) 2084 return BusLogic_Failure(HostAdapter, "INQUIRE SETUP INFORMATION"); 2085 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2086 HostAdapter->SynchronousOffset[TargetID] = (TargetID < 8 ? SetupInformation.SynchronousValuesID0to7[TargetID].Offset : SetupInformation.SynchronousValuesID8to15[TargetID - 8].Offset); 2087 if (strcmp(HostAdapter->FirmwareVersion, "5.06L") >= 0) 2088 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2089 HostAdapter->TargetFlags[TargetID].WideTransfersActive = (TargetID < 8 ? (SetupInformation.WideTransfersActiveID0to7 & (1 << TargetID) 2090 ? true : false) 2091 : (SetupInformation.WideTransfersActiveID8to15 & (1 << (TargetID - 8)) 2092 ? true : false)); 2093 /* 2094 Issue the Inquire Synchronous Period command. 2095 */ 2096 if (HostAdapter->FirmwareVersion[0] >= '3') { 2097 2098 /* Issue a Inquire Synchronous Period command. For each Target Device, 2099 * a byte is returned which represents the Synchronous Transfer Period 2100 * in units of 10 nanoseconds. 2101 */ 2102 2103 RequestedReplyLength = sizeof(SynchronousPeriod); 2104 if (BusLogic_Command(HostAdapter, BusLogic_InquireSynchronousPeriod, &RequestedReplyLength, sizeof(RequestedReplyLength), &SynchronousPeriod, sizeof(SynchronousPeriod)) 2105 != sizeof(SynchronousPeriod)) 2106 return BusLogic_Failure(HostAdapter, "INQUIRE SYNCHRONOUS PERIOD"); 2107 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2108 HostAdapter->SynchronousPeriod[TargetID] = SynchronousPeriod[TargetID]; 2109 } else 2110 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2111 if (SetupInformation.SynchronousValuesID0to7[TargetID].Offset > 0) 2112 HostAdapter->SynchronousPeriod[TargetID] = 20 + 5 * SetupInformation.SynchronousValuesID0to7[TargetID] 2113 .TransferPeriod; 2114 /* 2115 Indicate the Target Device Inquiry completed successfully. 2116 */ 2117 return true; 2118} 2119 2120/* 2121 BusLogic_InitializeHostStructure initializes the fields in the SCSI Host 2122 structure. The base, io_port, n_io_ports, irq, and dma_channel fields in the 2123 SCSI Host structure are intentionally left uninitialized, as this driver 2124 handles acquisition and release of these resources explicitly, as well as 2125 ensuring exclusive access to the Host Adapter hardware and data structures 2126 through explicit acquisition and release of the Host Adapter's Lock. 2127*/ 2128 2129static void __init BusLogic_InitializeHostStructure(struct BusLogic_HostAdapter 2130 *HostAdapter, struct Scsi_Host *Host) 2131{ 2132 Host->max_id = HostAdapter->MaxTargetDevices; 2133 Host->max_lun = HostAdapter->MaxLogicalUnits; 2134 Host->max_channel = 0; 2135 Host->unique_id = HostAdapter->IO_Address; 2136 Host->this_id = HostAdapter->SCSI_ID; 2137 Host->can_queue = HostAdapter->DriverQueueDepth; 2138 Host->sg_tablesize = HostAdapter->DriverScatterGatherLimit; 2139 Host->unchecked_isa_dma = HostAdapter->BounceBuffersRequired; 2140 Host->cmd_per_lun = HostAdapter->UntaggedQueueDepth; 2141} 2142 2143/* 2144 BusLogic_SlaveConfigure will actually set the queue depth on individual 2145 scsi devices as they are permanently added to the device chain. We 2146 shamelessly rip off the SelectQueueDepths code to make this work mostly 2147 like it used to. Since we don't get called once at the end of the scan 2148 but instead get called for each device, we have to do things a bit 2149 differently. 2150*/ 2151static int BusLogic_SlaveConfigure(struct scsi_device *Device) 2152{ 2153 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) Device->host->hostdata; 2154 int TargetID = Device->id; 2155 int QueueDepth = HostAdapter->QueueDepth[TargetID]; 2156 2157 if (HostAdapter->TargetFlags[TargetID].TaggedQueuingSupported && (HostAdapter->TaggedQueuingPermitted & (1 << TargetID))) { 2158 if (QueueDepth == 0) 2159 QueueDepth = BusLogic_MaxAutomaticTaggedQueueDepth; 2160 HostAdapter->QueueDepth[TargetID] = QueueDepth; 2161 scsi_adjust_queue_depth(Device, MSG_SIMPLE_TAG, QueueDepth); 2162 } else { 2163 HostAdapter->TaggedQueuingPermitted &= ~(1 << TargetID); 2164 QueueDepth = HostAdapter->UntaggedQueueDepth; 2165 HostAdapter->QueueDepth[TargetID] = QueueDepth; 2166 scsi_adjust_queue_depth(Device, 0, QueueDepth); 2167 } 2168 QueueDepth = 0; 2169 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) 2170 if (HostAdapter->TargetFlags[TargetID].TargetExists) { 2171 QueueDepth += HostAdapter->QueueDepth[TargetID]; 2172 } 2173 if (QueueDepth > HostAdapter->AllocatedCCBs) 2174 BusLogic_CreateAdditionalCCBs(HostAdapter, QueueDepth - HostAdapter->AllocatedCCBs, false); 2175 return 0; 2176} 2177 2178/* 2179 BusLogic_DetectHostAdapter probes for BusLogic Host Adapters at the standard 2180 I/O Addresses where they may be located, initializing, registering, and 2181 reporting the configuration of each BusLogic Host Adapter it finds. It 2182 returns the number of BusLogic Host Adapters successfully initialized and 2183 registered. 2184*/ 2185 2186static int __init BusLogic_init(void) 2187{ 2188 int BusLogicHostAdapterCount = 0, DriverOptionsIndex = 0, ProbeIndex; 2189 struct BusLogic_HostAdapter *PrototypeHostAdapter; 2190 int ret = 0; 2191 2192#ifdef MODULE 2193 if (BusLogic) 2194 BusLogic_Setup(BusLogic); 2195#endif 2196 2197 if (BusLogic_ProbeOptions.NoProbe) 2198 return -ENODEV; 2199 BusLogic_ProbeInfoList = 2200 kzalloc(BusLogic_MaxHostAdapters * sizeof(struct BusLogic_ProbeInfo), GFP_KERNEL); 2201 if (BusLogic_ProbeInfoList == NULL) { 2202 BusLogic_Error("BusLogic: Unable to allocate Probe Info List\n", NULL); 2203 return -ENOMEM; 2204 } 2205 2206 PrototypeHostAdapter = 2207 kzalloc(sizeof(struct BusLogic_HostAdapter), GFP_KERNEL); 2208 if (PrototypeHostAdapter == NULL) { 2209 kfree(BusLogic_ProbeInfoList); 2210 BusLogic_Error("BusLogic: Unable to allocate Prototype " "Host Adapter\n", NULL); 2211 return -ENOMEM; 2212 } 2213 2214#ifdef MODULE 2215 if (BusLogic != NULL) 2216 BusLogic_Setup(BusLogic); 2217#endif 2218 BusLogic_InitializeProbeInfoList(PrototypeHostAdapter); 2219 for (ProbeIndex = 0; ProbeIndex < BusLogic_ProbeInfoCount; ProbeIndex++) { 2220 struct BusLogic_ProbeInfo *ProbeInfo = &BusLogic_ProbeInfoList[ProbeIndex]; 2221 struct BusLogic_HostAdapter *HostAdapter = PrototypeHostAdapter; 2222 struct Scsi_Host *Host; 2223 if (ProbeInfo->IO_Address == 0) 2224 continue; 2225 memset(HostAdapter, 0, sizeof(struct BusLogic_HostAdapter)); 2226 HostAdapter->HostAdapterType = ProbeInfo->HostAdapterType; 2227 HostAdapter->HostAdapterBusType = ProbeInfo->HostAdapterBusType; 2228 HostAdapter->IO_Address = ProbeInfo->IO_Address; 2229 HostAdapter->PCI_Address = ProbeInfo->PCI_Address; 2230 HostAdapter->Bus = ProbeInfo->Bus; 2231 HostAdapter->Device = ProbeInfo->Device; 2232 HostAdapter->PCI_Device = ProbeInfo->PCI_Device; 2233 HostAdapter->IRQ_Channel = ProbeInfo->IRQ_Channel; 2234 HostAdapter->AddressCount = BusLogic_HostAdapterAddressCount[HostAdapter->HostAdapterType]; 2235 2236 /* 2237 Make sure region is free prior to probing. 2238 */ 2239 if (!request_region(HostAdapter->IO_Address, HostAdapter->AddressCount, 2240 "BusLogic")) 2241 continue; 2242 /* 2243 Probe the Host Adapter. If unsuccessful, abort further initialization. 2244 */ 2245 if (!BusLogic_ProbeHostAdapter(HostAdapter)) { 2246 release_region(HostAdapter->IO_Address, HostAdapter->AddressCount); 2247 continue; 2248 } 2249 /* 2250 Hard Reset the Host Adapter. If unsuccessful, abort further 2251 initialization. 2252 */ 2253 if (!BusLogic_HardwareResetHostAdapter(HostAdapter, true)) { 2254 release_region(HostAdapter->IO_Address, HostAdapter->AddressCount); 2255 continue; 2256 } 2257 /* 2258 Check the Host Adapter. If unsuccessful, abort further initialization. 2259 */ 2260 if (!BusLogic_CheckHostAdapter(HostAdapter)) { 2261 release_region(HostAdapter->IO_Address, HostAdapter->AddressCount); 2262 continue; 2263 } 2264 /* 2265 Initialize the Driver Options field if provided. 2266 */ 2267 if (DriverOptionsIndex < BusLogic_DriverOptionsCount) 2268 HostAdapter->DriverOptions = &BusLogic_DriverOptions[DriverOptionsIndex++]; 2269 /* 2270 Announce the Driver Version and Date, Author's Name, Copyright Notice, 2271 and Electronic Mail Address. 2272 */ 2273 BusLogic_AnnounceDriver(HostAdapter); 2274 /* 2275 Register the SCSI Host structure. 2276 */ 2277 2278 Host = scsi_host_alloc(&Bus_Logic_template, sizeof(struct BusLogic_HostAdapter)); 2279 if (Host == NULL) { 2280 release_region(HostAdapter->IO_Address, HostAdapter->AddressCount); 2281 continue; 2282 } 2283 HostAdapter = (struct BusLogic_HostAdapter *) Host->hostdata; 2284 memcpy(HostAdapter, PrototypeHostAdapter, sizeof(struct BusLogic_HostAdapter)); 2285 HostAdapter->SCSI_Host = Host; 2286 HostAdapter->HostNumber = Host->host_no; 2287 /* 2288 Add Host Adapter to the end of the list of registered BusLogic 2289 Host Adapters. 2290 */ 2291 list_add_tail(&HostAdapter->host_list, &BusLogic_host_list); 2292 2293 /* 2294 Read the Host Adapter Configuration, Configure the Host Adapter, 2295 Acquire the System Resources necessary to use the Host Adapter, then 2296 Create the Initial CCBs, Initialize the Host Adapter, and finally 2297 perform Target Device Inquiry. 2298 2299 From this point onward, any failure will be assumed to be due to a 2300 problem with the Host Adapter, rather than due to having mistakenly 2301 identified this port as belonging to a BusLogic Host Adapter. The 2302 I/O Address range will not be released, thereby preventing it from 2303 being incorrectly identified as any other type of Host Adapter. 2304 */ 2305 if (BusLogic_ReadHostAdapterConfiguration(HostAdapter) && 2306 BusLogic_ReportHostAdapterConfiguration(HostAdapter) && 2307 BusLogic_AcquireResources(HostAdapter) && 2308 BusLogic_CreateInitialCCBs(HostAdapter) && 2309 BusLogic_InitializeHostAdapter(HostAdapter) && 2310 BusLogic_TargetDeviceInquiry(HostAdapter)) { 2311 /* 2312 Initialization has been completed successfully. Release and 2313 re-register usage of the I/O Address range so that the Model 2314 Name of the Host Adapter will appear, and initialize the SCSI 2315 Host structure. 2316 */ 2317 release_region(HostAdapter->IO_Address, 2318 HostAdapter->AddressCount); 2319 if (!request_region(HostAdapter->IO_Address, 2320 HostAdapter->AddressCount, 2321 HostAdapter->FullModelName)) { 2322 printk(KERN_WARNING 2323 "BusLogic: Release and re-register of " 2324 "port 0x%04lx failed \n", 2325 (unsigned long)HostAdapter->IO_Address); 2326 BusLogic_DestroyCCBs(HostAdapter); 2327 BusLogic_ReleaseResources(HostAdapter); 2328 list_del(&HostAdapter->host_list); 2329 scsi_host_put(Host); 2330 ret = -ENOMEM; 2331 } else { 2332 BusLogic_InitializeHostStructure(HostAdapter, 2333 Host); 2334 if (scsi_add_host(Host, HostAdapter->PCI_Device 2335 ? &HostAdapter->PCI_Device->dev 2336 : NULL)) { 2337 printk(KERN_WARNING 2338 "BusLogic: scsi_add_host()" 2339 "failed!\n"); 2340 BusLogic_DestroyCCBs(HostAdapter); 2341 BusLogic_ReleaseResources(HostAdapter); 2342 list_del(&HostAdapter->host_list); 2343 scsi_host_put(Host); 2344 ret = -ENODEV; 2345 } else { 2346 scsi_scan_host(Host); 2347 BusLogicHostAdapterCount++; 2348 } 2349 } 2350 } else { 2351 /* 2352 An error occurred during Host Adapter Configuration Querying, Host 2353 Adapter Configuration, Resource Acquisition, CCB Creation, Host 2354 Adapter Initialization, or Target Device Inquiry, so remove Host 2355 Adapter from the list of registered BusLogic Host Adapters, destroy 2356 the CCBs, Release the System Resources, and Unregister the SCSI 2357 Host. 2358 */ 2359 BusLogic_DestroyCCBs(HostAdapter); 2360 BusLogic_ReleaseResources(HostAdapter); 2361 list_del(&HostAdapter->host_list); 2362 scsi_host_put(Host); 2363 ret = -ENODEV; 2364 } 2365 } 2366 kfree(PrototypeHostAdapter); 2367 kfree(BusLogic_ProbeInfoList); 2368 BusLogic_ProbeInfoList = NULL; 2369 return ret; 2370} 2371 2372 2373/* 2374 BusLogic_ReleaseHostAdapter releases all resources previously acquired to 2375 support a specific Host Adapter, including the I/O Address range, and 2376 unregisters the BusLogic Host Adapter. 2377*/ 2378 2379static int __exit BusLogic_ReleaseHostAdapter(struct BusLogic_HostAdapter *HostAdapter) 2380{ 2381 struct Scsi_Host *Host = HostAdapter->SCSI_Host; 2382 2383 scsi_remove_host(Host); 2384 2385 /* 2386 FlashPoint Host Adapters must first be released by the FlashPoint 2387 SCCB Manager. 2388 */ 2389 if (BusLogic_FlashPointHostAdapterP(HostAdapter)) 2390 FlashPoint_ReleaseHostAdapter(HostAdapter->CardHandle); 2391 /* 2392 Destroy the CCBs and release any system resources acquired to 2393 support Host Adapter. 2394 */ 2395 BusLogic_DestroyCCBs(HostAdapter); 2396 BusLogic_ReleaseResources(HostAdapter); 2397 /* 2398 Release usage of the I/O Address range. 2399 */ 2400 release_region(HostAdapter->IO_Address, HostAdapter->AddressCount); 2401 /* 2402 Remove Host Adapter from the list of registered BusLogic Host Adapters. 2403 */ 2404 list_del(&HostAdapter->host_list); 2405 2406 scsi_host_put(Host); 2407 return 0; 2408} 2409 2410 2411/* 2412 BusLogic_QueueCompletedCCB queues CCB for completion processing. 2413*/ 2414 2415static void BusLogic_QueueCompletedCCB(struct BusLogic_CCB *CCB) 2416{ 2417 struct BusLogic_HostAdapter *HostAdapter = CCB->HostAdapter; 2418 CCB->Status = BusLogic_CCB_Completed; 2419 CCB->Next = NULL; 2420 if (HostAdapter->FirstCompletedCCB == NULL) { 2421 HostAdapter->FirstCompletedCCB = CCB; 2422 HostAdapter->LastCompletedCCB = CCB; 2423 } else { 2424 HostAdapter->LastCompletedCCB->Next = CCB; 2425 HostAdapter->LastCompletedCCB = CCB; 2426 } 2427 HostAdapter->ActiveCommands[CCB->TargetID]--; 2428} 2429 2430 2431/* 2432 BusLogic_ComputeResultCode computes a SCSI Subsystem Result Code from 2433 the Host Adapter Status and Target Device Status. 2434*/ 2435 2436static int BusLogic_ComputeResultCode(struct BusLogic_HostAdapter *HostAdapter, enum BusLogic_HostAdapterStatus HostAdapterStatus, enum BusLogic_TargetDeviceStatus TargetDeviceStatus) 2437{ 2438 int HostStatus; 2439 switch (HostAdapterStatus) { 2440 case BusLogic_CommandCompletedNormally: 2441 case BusLogic_LinkedCommandCompleted: 2442 case BusLogic_LinkedCommandCompletedWithFlag: 2443 HostStatus = DID_OK; 2444 break; 2445 case BusLogic_SCSISelectionTimeout: 2446 HostStatus = DID_TIME_OUT; 2447 break; 2448 case BusLogic_InvalidOutgoingMailboxActionCode: 2449 case BusLogic_InvalidCommandOperationCode: 2450 case BusLogic_InvalidCommandParameter: 2451 BusLogic_Warning("BusLogic Driver Protocol Error 0x%02X\n", HostAdapter, HostAdapterStatus); 2452 case BusLogic_DataUnderRun: 2453 case BusLogic_DataOverRun: 2454 case BusLogic_UnexpectedBusFree: 2455 case BusLogic_LinkedCCBhasInvalidLUN: 2456 case BusLogic_AutoRequestSenseFailed: 2457 case BusLogic_TaggedQueuingMessageRejected: 2458 case BusLogic_UnsupportedMessageReceived: 2459 case BusLogic_HostAdapterHardwareFailed: 2460 case BusLogic_TargetDeviceReconnectedImproperly: 2461 case BusLogic_AbortQueueGenerated: 2462 case BusLogic_HostAdapterSoftwareError: 2463 case BusLogic_HostAdapterHardwareTimeoutError: 2464 case BusLogic_SCSIParityErrorDetected: 2465 HostStatus = DID_ERROR; 2466 break; 2467 case BusLogic_InvalidBusPhaseRequested: 2468 case BusLogic_TargetFailedResponseToATN: 2469 case BusLogic_HostAdapterAssertedRST: 2470 case BusLogic_OtherDeviceAssertedRST: 2471 case BusLogic_HostAdapterAssertedBusDeviceReset: 2472 HostStatus = DID_RESET; 2473 break; 2474 default: 2475 BusLogic_Warning("Unknown Host Adapter Status 0x%02X\n", HostAdapter, HostAdapterStatus); 2476 HostStatus = DID_ERROR; 2477 break; 2478 } 2479 return (HostStatus << 16) | TargetDeviceStatus; 2480} 2481 2482 2483/* 2484 BusLogic_ScanIncomingMailboxes scans the Incoming Mailboxes saving any 2485 Incoming Mailbox entries for completion processing. 2486*/ 2487 2488static void BusLogic_ScanIncomingMailboxes(struct BusLogic_HostAdapter *HostAdapter) 2489{ 2490 /* 2491 Scan through the Incoming Mailboxes in Strict Round Robin fashion, saving 2492 any completed CCBs for further processing. It is essential that for each 2493 CCB and SCSI Command issued, command completion processing is performed 2494 exactly once. Therefore, only Incoming Mailboxes with completion code 2495 Command Completed Without Error, Command Completed With Error, or Command 2496 Aborted At Host Request are saved for completion processing. When an 2497 Incoming Mailbox has a completion code of Aborted Command Not Found, the 2498 CCB had already completed or been aborted before the current Abort request 2499 was processed, and so completion processing has already occurred and no 2500 further action should be taken. 2501 */ 2502 struct BusLogic_IncomingMailbox *NextIncomingMailbox = HostAdapter->NextIncomingMailbox; 2503 enum BusLogic_CompletionCode CompletionCode; 2504 while ((CompletionCode = NextIncomingMailbox->CompletionCode) != BusLogic_IncomingMailboxFree) { 2505 /* 2506 We are only allowed to do this because we limit our architectures we 2507 run on to machines where bus_to_virt() actually works. There *needs* 2508 to be a dma_addr_to_virt() in the new PCI DMA mapping interface to 2509 replace bus_to_virt() or else this code is going to become very 2510 innefficient. 2511 */ 2512 struct BusLogic_CCB *CCB = (struct BusLogic_CCB *) Bus_to_Virtual(NextIncomingMailbox->CCB); 2513 if (CompletionCode != BusLogic_AbortedCommandNotFound) { 2514 if (CCB->Status == BusLogic_CCB_Active || CCB->Status == BusLogic_CCB_Reset) { 2515 /* 2516 Save the Completion Code for this CCB and queue the CCB 2517 for completion processing. 2518 */ 2519 CCB->CompletionCode = CompletionCode; 2520 BusLogic_QueueCompletedCCB(CCB); 2521 } else { 2522 /* 2523 If a CCB ever appears in an Incoming Mailbox and is not marked 2524 as status Active or Reset, then there is most likely a bug in 2525 the Host Adapter firmware. 2526 */ 2527 BusLogic_Warning("Illegal CCB #%ld status %d in " "Incoming Mailbox\n", HostAdapter, CCB->SerialNumber, CCB->Status); 2528 } 2529 } 2530 NextIncomingMailbox->CompletionCode = BusLogic_IncomingMailboxFree; 2531 if (++NextIncomingMailbox > HostAdapter->LastIncomingMailbox) 2532 NextIncomingMailbox = HostAdapter->FirstIncomingMailbox; 2533 } 2534 HostAdapter->NextIncomingMailbox = NextIncomingMailbox; 2535} 2536 2537 2538/* 2539 BusLogic_ProcessCompletedCCBs iterates over the completed CCBs for Host 2540 Adapter setting the SCSI Command Result Codes, deallocating the CCBs, and 2541 calling the SCSI Subsystem Completion Routines. The Host Adapter's Lock 2542 should already have been acquired by the caller. 2543*/ 2544 2545static void BusLogic_ProcessCompletedCCBs(struct BusLogic_HostAdapter *HostAdapter) 2546{ 2547 if (HostAdapter->ProcessCompletedCCBsActive) 2548 return; 2549 HostAdapter->ProcessCompletedCCBsActive = true; 2550 while (HostAdapter->FirstCompletedCCB != NULL) { 2551 struct BusLogic_CCB *CCB = HostAdapter->FirstCompletedCCB; 2552 struct scsi_cmnd *Command = CCB->Command; 2553 HostAdapter->FirstCompletedCCB = CCB->Next; 2554 if (HostAdapter->FirstCompletedCCB == NULL) 2555 HostAdapter->LastCompletedCCB = NULL; 2556 /* 2557 Process the Completed CCB. 2558 */ 2559 if (CCB->Opcode == BusLogic_BusDeviceReset) { 2560 int TargetID = CCB->TargetID; 2561 BusLogic_Warning("Bus Device Reset CCB #%ld to Target " "%d Completed\n", HostAdapter, CCB->SerialNumber, TargetID); 2562 BusLogic_IncrementErrorCounter(&HostAdapter->TargetStatistics[TargetID].BusDeviceResetsCompleted); 2563 HostAdapter->TargetFlags[TargetID].TaggedQueuingActive = false; 2564 HostAdapter->CommandsSinceReset[TargetID] = 0; 2565 HostAdapter->LastResetCompleted[TargetID] = jiffies; 2566 /* 2567 Place CCB back on the Host Adapter's free list. 2568 */ 2569 BusLogic_DeallocateCCB(CCB); 2570 /* 2571 Iterate over the CCBs for this Host Adapter performing completion 2572 processing for any CCBs marked as Reset for this Target. 2573 */ 2574 for (CCB = HostAdapter->All_CCBs; CCB != NULL; CCB = CCB->NextAll) 2575 if (CCB->Status == BusLogic_CCB_Reset && CCB->TargetID == TargetID) { 2576 Command = CCB->Command; 2577 BusLogic_DeallocateCCB(CCB); 2578 HostAdapter->ActiveCommands[TargetID]--; 2579 Command->result = DID_RESET << 16; 2580 Command->scsi_done(Command); 2581 } 2582 HostAdapter->BusDeviceResetPendingCCB[TargetID] = NULL; 2583 } else { 2584 /* 2585 Translate the Completion Code, Host Adapter Status, and Target 2586 Device Status into a SCSI Subsystem Result Code. 2587 */ 2588 switch (CCB->CompletionCode) { 2589 case BusLogic_IncomingMailboxFree: 2590 case BusLogic_AbortedCommandNotFound: 2591 case BusLogic_InvalidCCB: 2592 BusLogic_Warning("CCB #%ld to Target %d Impossible State\n", HostAdapter, CCB->SerialNumber, CCB->TargetID); 2593 break; 2594 case BusLogic_CommandCompletedWithoutError: 2595 HostAdapter->TargetStatistics[CCB->TargetID] 2596 .CommandsCompleted++; 2597 HostAdapter->TargetFlags[CCB->TargetID] 2598 .CommandSuccessfulFlag = true; 2599 Command->result = DID_OK << 16; 2600 break; 2601 case BusLogic_CommandAbortedAtHostRequest: 2602 BusLogic_Warning("CCB #%ld to Target %d Aborted\n", HostAdapter, CCB->SerialNumber, CCB->TargetID); 2603 BusLogic_IncrementErrorCounter(&HostAdapter->TargetStatistics[CCB->TargetID] 2604 .CommandAbortsCompleted); 2605 Command->result = DID_ABORT << 16; 2606 break; 2607 case BusLogic_CommandCompletedWithError: 2608 Command->result = BusLogic_ComputeResultCode(HostAdapter, CCB->HostAdapterStatus, CCB->TargetDeviceStatus); 2609 if (CCB->HostAdapterStatus != BusLogic_SCSISelectionTimeout) { 2610 HostAdapter->TargetStatistics[CCB->TargetID] 2611 .CommandsCompleted++; 2612 if (BusLogic_GlobalOptions.TraceErrors) { 2613 int i; 2614 BusLogic_Notice("CCB #%ld Target %d: Result %X Host " 2615 "Adapter Status %02X " "Target Status %02X\n", HostAdapter, CCB->SerialNumber, CCB->TargetID, Command->result, CCB->HostAdapterStatus, CCB->TargetDeviceStatus); 2616 BusLogic_Notice("CDB ", HostAdapter); 2617 for (i = 0; i < CCB->CDB_Length; i++) 2618 BusLogic_Notice(" %02X", HostAdapter, CCB->CDB[i]); 2619 BusLogic_Notice("\n", HostAdapter); 2620 BusLogic_Notice("Sense ", HostAdapter); 2621 for (i = 0; i < CCB->SenseDataLength; i++) 2622 BusLogic_Notice(" %02X", HostAdapter, Command->sense_buffer[i]); 2623 BusLogic_Notice("\n", HostAdapter); 2624 } 2625 } 2626 break; 2627 } 2628 /* 2629 When an INQUIRY command completes normally, save the 2630 CmdQue (Tagged Queuing Supported) and WBus16 (16 Bit 2631 Wide Data Transfers Supported) bits. 2632 */ 2633 if (CCB->CDB[0] == INQUIRY && CCB->CDB[1] == 0 && CCB->HostAdapterStatus == BusLogic_CommandCompletedNormally) { 2634 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[CCB->TargetID]; 2635 struct SCSI_Inquiry *InquiryResult = (struct SCSI_Inquiry *) Command->request_buffer; 2636 TargetFlags->TargetExists = true; 2637 TargetFlags->TaggedQueuingSupported = InquiryResult->CmdQue; 2638 TargetFlags->WideTransfersSupported = InquiryResult->WBus16; 2639 } 2640 /* 2641 Place CCB back on the Host Adapter's free list. 2642 */ 2643 BusLogic_DeallocateCCB(CCB); 2644 /* 2645 Call the SCSI Command Completion Routine. 2646 */ 2647 Command->scsi_done(Command); 2648 } 2649 } 2650 HostAdapter->ProcessCompletedCCBsActive = false; 2651} 2652 2653 2654/* 2655 BusLogic_InterruptHandler handles hardware interrupts from BusLogic Host 2656 Adapters. 2657*/ 2658 2659static irqreturn_t BusLogic_InterruptHandler(int IRQ_Channel, void *DeviceIdentifier) 2660{ 2661 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) DeviceIdentifier; 2662 unsigned long ProcessorFlags; 2663 /* 2664 Acquire exclusive access to Host Adapter. 2665 */ 2666 spin_lock_irqsave(HostAdapter->SCSI_Host->host_lock, ProcessorFlags); 2667 /* 2668 Handle Interrupts appropriately for each Host Adapter type. 2669 */ 2670 if (BusLogic_MultiMasterHostAdapterP(HostAdapter)) { 2671 union BusLogic_InterruptRegister InterruptRegister; 2672 /* 2673 Read the Host Adapter Interrupt Register. 2674 */ 2675 InterruptRegister.All = BusLogic_ReadInterruptRegister(HostAdapter); 2676 if (InterruptRegister.ir.InterruptValid) { 2677 /* 2678 Acknowledge the interrupt and reset the Host Adapter 2679 Interrupt Register. 2680 */ 2681 BusLogic_InterruptReset(HostAdapter); 2682 /* 2683 Process valid External SCSI Bus Reset and Incoming Mailbox 2684 Loaded Interrupts. Command Complete Interrupts are noted, 2685 and Outgoing Mailbox Available Interrupts are ignored, as 2686 they are never enabled. 2687 */ 2688 if (InterruptRegister.ir.ExternalBusReset) 2689 HostAdapter->HostAdapterExternalReset = true; 2690 else if (InterruptRegister.ir.IncomingMailboxLoaded) 2691 BusLogic_ScanIncomingMailboxes(HostAdapter); 2692 else if (InterruptRegister.ir.CommandComplete) 2693 HostAdapter->HostAdapterCommandCompleted = true; 2694 } 2695 } else { 2696 /* 2697 Check if there is a pending interrupt for this Host Adapter. 2698 */ 2699 if (FlashPoint_InterruptPending(HostAdapter->CardHandle)) 2700 switch (FlashPoint_HandleInterrupt(HostAdapter->CardHandle)) { 2701 case FlashPoint_NormalInterrupt: 2702 break; 2703 case FlashPoint_ExternalBusReset: 2704 HostAdapter->HostAdapterExternalReset = true; 2705 break; 2706 case FlashPoint_InternalError: 2707 BusLogic_Warning("Internal FlashPoint Error detected" " - Resetting Host Adapter\n", HostAdapter); 2708 HostAdapter->HostAdapterInternalError = true; 2709 break; 2710 } 2711 } 2712 /* 2713 Process any completed CCBs. 2714 */ 2715 if (HostAdapter->FirstCompletedCCB != NULL) 2716 BusLogic_ProcessCompletedCCBs(HostAdapter); 2717 /* 2718 Reset the Host Adapter if requested. 2719 */ 2720 if (HostAdapter->HostAdapterExternalReset) { 2721 BusLogic_Warning("Resetting %s due to External SCSI Bus Reset\n", HostAdapter, HostAdapter->FullModelName); 2722 BusLogic_IncrementErrorCounter(&HostAdapter->ExternalHostAdapterResets); 2723 BusLogic_ResetHostAdapter(HostAdapter, false); 2724 HostAdapter->HostAdapterExternalReset = false; 2725 } else if (HostAdapter->HostAdapterInternalError) { 2726 BusLogic_Warning("Resetting %s due to Host Adapter Internal Error\n", HostAdapter, HostAdapter->FullModelName); 2727 BusLogic_IncrementErrorCounter(&HostAdapter->HostAdapterInternalErrors); 2728 BusLogic_ResetHostAdapter(HostAdapter, true); 2729 HostAdapter->HostAdapterInternalError = false; 2730 } 2731 /* 2732 Release exclusive access to Host Adapter. 2733 */ 2734 spin_unlock_irqrestore(HostAdapter->SCSI_Host->host_lock, ProcessorFlags); 2735 return IRQ_HANDLED; 2736} 2737 2738 2739/* 2740 BusLogic_WriteOutgoingMailbox places CCB and Action Code into an Outgoing 2741 Mailbox for execution by Host Adapter. The Host Adapter's Lock should 2742 already have been acquired by the caller. 2743*/ 2744 2745static bool BusLogic_WriteOutgoingMailbox(struct BusLogic_HostAdapter 2746 *HostAdapter, enum BusLogic_ActionCode ActionCode, struct BusLogic_CCB *CCB) 2747{ 2748 struct BusLogic_OutgoingMailbox *NextOutgoingMailbox; 2749 NextOutgoingMailbox = HostAdapter->NextOutgoingMailbox; 2750 if (NextOutgoingMailbox->ActionCode == BusLogic_OutgoingMailboxFree) { 2751 CCB->Status = BusLogic_CCB_Active; 2752 /* 2753 The CCB field must be written before the Action Code field since 2754 the Host Adapter is operating asynchronously and the locking code 2755 does not protect against simultaneous access by the Host Adapter. 2756 */ 2757 NextOutgoingMailbox->CCB = CCB->DMA_Handle; 2758 NextOutgoingMailbox->ActionCode = ActionCode; 2759 BusLogic_StartMailboxCommand(HostAdapter); 2760 if (++NextOutgoingMailbox > HostAdapter->LastOutgoingMailbox) 2761 NextOutgoingMailbox = HostAdapter->FirstOutgoingMailbox; 2762 HostAdapter->NextOutgoingMailbox = NextOutgoingMailbox; 2763 if (ActionCode == BusLogic_MailboxStartCommand) { 2764 HostAdapter->ActiveCommands[CCB->TargetID]++; 2765 if (CCB->Opcode != BusLogic_BusDeviceReset) 2766 HostAdapter->TargetStatistics[CCB->TargetID].CommandsAttempted++; 2767 } 2768 return true; 2769 } 2770 return false; 2771} 2772 2773/* Error Handling (EH) support */ 2774 2775static int BusLogic_host_reset(struct scsi_cmnd * SCpnt) 2776{ 2777 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) SCpnt->device->host->hostdata; 2778 2779 unsigned int id = SCpnt->device->id; 2780 struct BusLogic_TargetStatistics *stats = &HostAdapter->TargetStatistics[id]; 2781 int rc; 2782 2783 spin_lock_irq(SCpnt->device->host->host_lock); 2784 2785 BusLogic_IncrementErrorCounter(&stats->HostAdapterResetsRequested); 2786 2787 rc = BusLogic_ResetHostAdapter(HostAdapter, false); 2788 spin_unlock_irq(SCpnt->device->host->host_lock); 2789 return rc; 2790} 2791 2792/* 2793 BusLogic_QueueCommand creates a CCB for Command and places it into an 2794 Outgoing Mailbox for execution by the associated Host Adapter. 2795*/ 2796 2797static int BusLogic_QueueCommand(struct scsi_cmnd *Command, void (*CompletionRoutine) (struct scsi_cmnd *)) 2798{ 2799 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) Command->device->host->hostdata; 2800 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[Command->device->id]; 2801 struct BusLogic_TargetStatistics *TargetStatistics = HostAdapter->TargetStatistics; 2802 unsigned char *CDB = Command->cmnd; 2803 int CDB_Length = Command->cmd_len; 2804 int TargetID = Command->device->id; 2805 int LogicalUnit = Command->device->lun; 2806 void *BufferPointer = Command->request_buffer; 2807 int BufferLength = Command->request_bufflen; 2808 int SegmentCount = Command->use_sg; 2809 struct BusLogic_CCB *CCB; 2810 /* 2811 SCSI REQUEST_SENSE commands will be executed automatically by the Host 2812 Adapter for any errors, so they should not be executed explicitly unless 2813 the Sense Data is zero indicating that no error occurred. 2814 */ 2815 if (CDB[0] == REQUEST_SENSE && Command->sense_buffer[0] != 0) { 2816 Command->result = DID_OK << 16; 2817 CompletionRoutine(Command); 2818 return 0; 2819 } 2820 /* 2821 Allocate a CCB from the Host Adapter's free list. In the unlikely event 2822 that there are none available and memory allocation fails, wait 1 second 2823 and try again. If that fails, the Host Adapter is probably hung so signal 2824 an error as a Host Adapter Hard Reset should be initiated soon. 2825 */ 2826 CCB = BusLogic_AllocateCCB(HostAdapter); 2827 if (CCB == NULL) { 2828 spin_unlock_irq(HostAdapter->SCSI_Host->host_lock); 2829 BusLogic_Delay(1); 2830 spin_lock_irq(HostAdapter->SCSI_Host->host_lock); 2831 CCB = BusLogic_AllocateCCB(HostAdapter); 2832 if (CCB == NULL) { 2833 Command->result = DID_ERROR << 16; 2834 CompletionRoutine(Command); 2835 return 0; 2836 } 2837 } 2838 /* 2839 Initialize the fields in the BusLogic Command Control Block (CCB). 2840 */ 2841 if (SegmentCount == 0 && BufferLength != 0) { 2842 CCB->Opcode = BusLogic_InitiatorCCB; 2843 CCB->DataLength = BufferLength; 2844 CCB->DataPointer = pci_map_single(HostAdapter->PCI_Device, 2845 BufferPointer, BufferLength, 2846 Command->sc_data_direction); 2847 } else if (SegmentCount != 0) { 2848 struct scatterlist *ScatterList = (struct scatterlist *) BufferPointer; 2849 int Segment, Count; 2850 2851 Count = pci_map_sg(HostAdapter->PCI_Device, ScatterList, SegmentCount, 2852 Command->sc_data_direction); 2853 CCB->Opcode = BusLogic_InitiatorCCB_ScatterGather; 2854 CCB->DataLength = Count * sizeof(struct BusLogic_ScatterGatherSegment); 2855 if (BusLogic_MultiMasterHostAdapterP(HostAdapter)) 2856 CCB->DataPointer = (unsigned int) CCB->DMA_Handle + ((unsigned long) &CCB->ScatterGatherList - (unsigned long) CCB); 2857 else 2858 CCB->DataPointer = Virtual_to_32Bit_Virtual(CCB->ScatterGatherList); 2859 for (Segment = 0; Segment < Count; Segment++) { 2860 CCB->ScatterGatherList[Segment].SegmentByteCount = sg_dma_len(ScatterList + Segment); 2861 CCB->ScatterGatherList[Segment].SegmentDataPointer = sg_dma_address(ScatterList + Segment); 2862 } 2863 } else { 2864 CCB->Opcode = BusLogic_InitiatorCCB; 2865 CCB->DataLength = BufferLength; 2866 CCB->DataPointer = 0; 2867 } 2868 switch (CDB[0]) { 2869 case READ_6: 2870 case READ_10: 2871 CCB->DataDirection = BusLogic_DataInLengthChecked; 2872 TargetStatistics[TargetID].ReadCommands++; 2873 BusLogic_IncrementByteCounter(&TargetStatistics[TargetID].TotalBytesRead, BufferLength); 2874 BusLogic_IncrementSizeBucket(TargetStatistics[TargetID].ReadCommandSizeBuckets, BufferLength); 2875 break; 2876 case WRITE_6: 2877 case WRITE_10: 2878 CCB->DataDirection = BusLogic_DataOutLengthChecked; 2879 TargetStatistics[TargetID].WriteCommands++; 2880 BusLogic_IncrementByteCounter(&TargetStatistics[TargetID].TotalBytesWritten, BufferLength); 2881 BusLogic_IncrementSizeBucket(TargetStatistics[TargetID].WriteCommandSizeBuckets, BufferLength); 2882 break; 2883 default: 2884 CCB->DataDirection = BusLogic_UncheckedDataTransfer; 2885 break; 2886 } 2887 CCB->CDB_Length = CDB_Length; 2888 CCB->HostAdapterStatus = 0; 2889 CCB->TargetDeviceStatus = 0; 2890 CCB->TargetID = TargetID; 2891 CCB->LogicalUnit = LogicalUnit; 2892 CCB->TagEnable = false; 2893 CCB->LegacyTagEnable = false; 2894 /* 2895 BusLogic recommends that after a Reset the first couple of commands that 2896 are sent to a Target Device be sent in a non Tagged Queue fashion so that 2897 the Host Adapter and Target Device can establish Synchronous and Wide 2898 Transfer before Queue Tag messages can interfere with the Synchronous and 2899 Wide Negotiation messages. By waiting to enable Tagged Queuing until after 2900 the first BusLogic_MaxTaggedQueueDepth commands have been queued, it is 2901 assured that after a Reset any pending commands are requeued before Tagged 2902 Queuing is enabled and that the Tagged Queuing message will not occur while 2903 the partition table is being printed. In addition, some devices do not 2904 properly handle the transition from non-tagged to tagged commands, so it is 2905 necessary to wait until there are no pending commands for a target device 2906 before queuing tagged commands. 2907 */ 2908 if (HostAdapter->CommandsSinceReset[TargetID]++ >= 2909 BusLogic_MaxTaggedQueueDepth && !TargetFlags->TaggedQueuingActive && HostAdapter->ActiveCommands[TargetID] == 0 && TargetFlags->TaggedQueuingSupported && (HostAdapter->TaggedQueuingPermitted & (1 << TargetID))) { 2910 TargetFlags->TaggedQueuingActive = true; 2911 BusLogic_Notice("Tagged Queuing now active for Target %d\n", HostAdapter, TargetID); 2912 } 2913 if (TargetFlags->TaggedQueuingActive) { 2914 enum BusLogic_QueueTag QueueTag = BusLogic_SimpleQueueTag; 2915 /* 2916 When using Tagged Queuing with Simple Queue Tags, it appears that disk 2917 drive controllers do not guarantee that a queued command will not 2918 remain in a disconnected state indefinitely if commands that read or 2919 write nearer the head position continue to arrive without interruption. 2920 Therefore, for each Target Device this driver keeps track of the last 2921 time either the queue was empty or an Ordered Queue Tag was issued. If 2922 more than 4 seconds (one fifth of the 20 second disk timeout) have 2923 elapsed since this last sequence point, this command will be issued 2924 with an Ordered Queue Tag rather than a Simple Queue Tag, which forces 2925 the Target Device to complete all previously queued commands before 2926 this command may be executed. 2927 */ 2928 if (HostAdapter->ActiveCommands[TargetID] == 0) 2929 HostAdapter->LastSequencePoint[TargetID] = jiffies; 2930 else if (time_after(jiffies, HostAdapter->LastSequencePoint[TargetID] + 4 * HZ)) { 2931 HostAdapter->LastSequencePoint[TargetID] = jiffies; 2932 QueueTag = BusLogic_OrderedQueueTag; 2933 } 2934 if (HostAdapter->ExtendedLUNSupport) { 2935 CCB->TagEnable = true; 2936 CCB->QueueTag = QueueTag; 2937 } else { 2938 CCB->LegacyTagEnable = true; 2939 CCB->LegacyQueueTag = QueueTag; 2940 } 2941 } 2942 memcpy(CCB->CDB, CDB, CDB_Length); 2943 CCB->SenseDataLength = sizeof(Command->sense_buffer); 2944 CCB->SenseDataPointer = pci_map_single(HostAdapter->PCI_Device, Command->sense_buffer, CCB->SenseDataLength, PCI_DMA_FROMDEVICE); 2945 CCB->Command = Command; 2946 Command->scsi_done = CompletionRoutine; 2947 if (BusLogic_MultiMasterHostAdapterP(HostAdapter)) { 2948 /* 2949 Place the CCB in an Outgoing Mailbox. The higher levels of the SCSI 2950 Subsystem should not attempt to queue more commands than can be placed 2951 in Outgoing Mailboxes, so there should always be one free. In the 2952 unlikely event that there are none available, wait 1 second and try 2953 again. If that fails, the Host Adapter is probably hung so signal an 2954 error as a Host Adapter Hard Reset should be initiated soon. 2955 */ 2956 if (!BusLogic_WriteOutgoingMailbox(HostAdapter, BusLogic_MailboxStartCommand, CCB)) { 2957 spin_unlock_irq(HostAdapter->SCSI_Host->host_lock); 2958 BusLogic_Warning("Unable to write Outgoing Mailbox - " "Pausing for 1 second\n", HostAdapter); 2959 BusLogic_Delay(1); 2960 spin_lock_irq(HostAdapter->SCSI_Host->host_lock); 2961 if (!BusLogic_WriteOutgoingMailbox(HostAdapter, BusLogic_MailboxStartCommand, CCB)) { 2962 BusLogic_Warning("Still unable to write Outgoing Mailbox - " "Host Adapter Dead?\n", HostAdapter); 2963 BusLogic_DeallocateCCB(CCB); 2964 Command->result = DID_ERROR << 16; 2965 Command->scsi_done(Command); 2966 } 2967 } 2968 } else { 2969 /* 2970 Call the FlashPoint SCCB Manager to start execution of the CCB. 2971 */ 2972 CCB->Status = BusLogic_CCB_Active; 2973 HostAdapter->ActiveCommands[TargetID]++; 2974 TargetStatistics[TargetID].CommandsAttempted++; 2975 FlashPoint_StartCCB(HostAdapter->CardHandle, CCB); 2976 /* 2977 The Command may have already completed and BusLogic_QueueCompletedCCB 2978 been called, or it may still be pending. 2979 */ 2980 if (CCB->Status == BusLogic_CCB_Completed) 2981 BusLogic_ProcessCompletedCCBs(HostAdapter); 2982 } 2983 return 0; 2984} 2985 2986 2987/* 2988 BusLogic_ResetHostAdapter resets Host Adapter if possible, marking all 2989 currently executing SCSI Commands as having been Reset. 2990*/ 2991 2992static int BusLogic_ResetHostAdapter(struct BusLogic_HostAdapter *HostAdapter, bool HardReset) 2993{ 2994 struct BusLogic_CCB *CCB; 2995 int TargetID; 2996 2997 /* 2998 * Attempt to Reset and Reinitialize the Host Adapter. 2999 */ 3000 3001 if (!(BusLogic_HardwareResetHostAdapter(HostAdapter, HardReset) && BusLogic_InitializeHostAdapter(HostAdapter))) { 3002 BusLogic_Error("Resetting %s Failed\n", HostAdapter, HostAdapter->FullModelName); 3003 return FAILURE; 3004 } 3005 3006 /* 3007 * Deallocate all currently executing CCBs. 3008 */ 3009 3010 for (CCB = HostAdapter->All_CCBs; CCB != NULL; CCB = CCB->NextAll) 3011 if (CCB->Status == BusLogic_CCB_Active) 3012 BusLogic_DeallocateCCB(CCB); 3013 /* 3014 * Wait a few seconds between the Host Adapter Hard Reset which 3015 * initiates a SCSI Bus Reset and issuing any SCSI Commands. Some 3016 * SCSI devices get confused if they receive SCSI Commands too soon 3017 * after a SCSI Bus Reset. 3018 */ 3019 3020 if (HardReset) { 3021 spin_unlock_irq(HostAdapter->SCSI_Host->host_lock); 3022 BusLogic_Delay(HostAdapter->BusSettleTime); 3023 spin_lock_irq(HostAdapter->SCSI_Host->host_lock); 3024 } 3025 3026 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3027 HostAdapter->LastResetAttempted[TargetID] = jiffies; 3028 HostAdapter->LastResetCompleted[TargetID] = jiffies; 3029 } 3030 return SUCCESS; 3031} 3032 3033/* 3034 BusLogic_BIOSDiskParameters returns the Heads/Sectors/Cylinders BIOS Disk 3035 Parameters for Disk. The default disk geometry is 64 heads, 32 sectors, and 3036 the appropriate number of cylinders so as not to exceed drive capacity. In 3037 order for disks equal to or larger than 1 GB to be addressable by the BIOS 3038 without exceeding the BIOS limitation of 1024 cylinders, Extended Translation 3039 may be enabled in AutoSCSI on FlashPoint Host Adapters and on "W" and "C" 3040 series MultiMaster Host Adapters, or by a dip switch setting on "S" and "A" 3041 series MultiMaster Host Adapters. With Extended Translation enabled, drives 3042 between 1 GB inclusive and 2 GB exclusive are given a disk geometry of 128 3043 heads and 32 sectors, and drives above 2 GB inclusive are given a disk 3044 geometry of 255 heads and 63 sectors. However, if the BIOS detects that the 3045 Extended Translation setting does not match the geometry in the partition 3046 table, then the translation inferred from the partition table will be used by 3047 the BIOS, and a warning may be displayed. 3048*/ 3049 3050static int BusLogic_BIOSDiskParameters(struct scsi_device *sdev, struct block_device *Device, sector_t capacity, int *Parameters) 3051{ 3052 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) sdev->host->hostdata; 3053 struct BIOS_DiskParameters *DiskParameters = (struct BIOS_DiskParameters *) Parameters; 3054 unsigned char *buf; 3055 if (HostAdapter->ExtendedTranslationEnabled && capacity >= 2 * 1024 * 1024 /* 1 GB in 512 byte sectors */ ) { 3056 if (capacity >= 4 * 1024 * 1024 /* 2 GB in 512 byte sectors */ ) { 3057 DiskParameters->Heads = 255; 3058 DiskParameters->Sectors = 63; 3059 } else { 3060 DiskParameters->Heads = 128; 3061 DiskParameters->Sectors = 32; 3062 } 3063 } else { 3064 DiskParameters->Heads = 64; 3065 DiskParameters->Sectors = 32; 3066 } 3067 DiskParameters->Cylinders = (unsigned long) capacity / (DiskParameters->Heads * DiskParameters->Sectors); 3068 buf = scsi_bios_ptable(Device); 3069 if (buf == NULL) 3070 return 0; 3071 /* 3072 If the boot sector partition table flag is valid, search for a partition 3073 table entry whose end_head matches one of the standard BusLogic geometry 3074 translations (64/32, 128/32, or 255/63). 3075 */ 3076 if (*(unsigned short *) (buf + 64) == 0xAA55) { 3077 struct partition *FirstPartitionEntry = (struct partition *) buf; 3078 struct partition *PartitionEntry = FirstPartitionEntry; 3079 int SavedCylinders = DiskParameters->Cylinders, PartitionNumber; 3080 unsigned char PartitionEntryEndHead = 0, PartitionEntryEndSector = 0; 3081 for (PartitionNumber = 0; PartitionNumber < 4; PartitionNumber++) { 3082 PartitionEntryEndHead = PartitionEntry->end_head; 3083 PartitionEntryEndSector = PartitionEntry->end_sector & 0x3F; 3084 if (PartitionEntryEndHead == 64 - 1) { 3085 DiskParameters->Heads = 64; 3086 DiskParameters->Sectors = 32; 3087 break; 3088 } else if (PartitionEntryEndHead == 128 - 1) { 3089 DiskParameters->Heads = 128; 3090 DiskParameters->Sectors = 32; 3091 break; 3092 } else if (PartitionEntryEndHead == 255 - 1) { 3093 DiskParameters->Heads = 255; 3094 DiskParameters->Sectors = 63; 3095 break; 3096 } 3097 PartitionEntry++; 3098 } 3099 if (PartitionNumber == 4) { 3100 PartitionEntryEndHead = FirstPartitionEntry->end_head; 3101 PartitionEntryEndSector = FirstPartitionEntry->end_sector & 0x3F; 3102 } 3103 DiskParameters->Cylinders = (unsigned long) capacity / (DiskParameters->Heads * DiskParameters->Sectors); 3104 if (PartitionNumber < 4 && PartitionEntryEndSector == DiskParameters->Sectors) { 3105 if (DiskParameters->Cylinders != SavedCylinders) 3106 BusLogic_Warning("Adopting Geometry %d/%d from Partition Table\n", HostAdapter, DiskParameters->Heads, DiskParameters->Sectors); 3107 } else if (PartitionEntryEndHead > 0 || PartitionEntryEndSector > 0) { 3108 BusLogic_Warning("Warning: Partition Table appears to " "have Geometry %d/%d which is\n", HostAdapter, PartitionEntryEndHead + 1, PartitionEntryEndSector); 3109 BusLogic_Warning("not compatible with current BusLogic " "Host Adapter Geometry %d/%d\n", HostAdapter, DiskParameters->Heads, DiskParameters->Sectors); 3110 } 3111 } 3112 kfree(buf); 3113 return 0; 3114} 3115 3116 3117/* 3118 BugLogic_ProcDirectoryInfo implements /proc/scsi/BusLogic/<N>. 3119*/ 3120 3121static int BusLogic_ProcDirectoryInfo(struct Scsi_Host *shost, char *ProcBuffer, char **StartPointer, off_t Offset, int BytesAvailable, int WriteFlag) 3122{ 3123 struct BusLogic_HostAdapter *HostAdapter = (struct BusLogic_HostAdapter *) shost->hostdata; 3124 struct BusLogic_TargetStatistics *TargetStatistics; 3125 int TargetID, Length; 3126 char *Buffer; 3127 3128 TargetStatistics = HostAdapter->TargetStatistics; 3129 if (WriteFlag) { 3130 HostAdapter->ExternalHostAdapterResets = 0; 3131 HostAdapter->HostAdapterInternalErrors = 0; 3132 memset(TargetStatistics, 0, BusLogic_MaxTargetDevices * sizeof(struct BusLogic_TargetStatistics)); 3133 return 0; 3134 } 3135 Buffer = HostAdapter->MessageBuffer; 3136 Length = HostAdapter->MessageBufferLength; 3137 Length += sprintf(&Buffer[Length], "\n\ 3138Current Driver Queue Depth: %d\n\ 3139Currently Allocated CCBs: %d\n", HostAdapter->DriverQueueDepth, HostAdapter->AllocatedCCBs); 3140 Length += sprintf(&Buffer[Length], "\n\n\ 3141 DATA TRANSFER STATISTICS\n\ 3142\n\ 3143Target Tagged Queuing Queue Depth Active Attempted Completed\n\ 3144====== ============== =========== ====== ========= =========\n"); 3145 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3146 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[TargetID]; 3147 if (!TargetFlags->TargetExists) 3148 continue; 3149 Length += sprintf(&Buffer[Length], " %2d %s", TargetID, (TargetFlags->TaggedQueuingSupported ? (TargetFlags->TaggedQueuingActive ? " Active" : (HostAdapter->TaggedQueuingPermitted & (1 << TargetID) 3150 ? " Permitted" : " Disabled")) 3151 : "Not Supported")); 3152 Length += sprintf(&Buffer[Length], 3153 " %3d %3u %9u %9u\n", HostAdapter->QueueDepth[TargetID], HostAdapter->ActiveCommands[TargetID], TargetStatistics[TargetID].CommandsAttempted, TargetStatistics[TargetID].CommandsCompleted); 3154 } 3155 Length += sprintf(&Buffer[Length], "\n\ 3156Target Read Commands Write Commands Total Bytes Read Total Bytes Written\n\ 3157====== ============= ============== =================== ===================\n"); 3158 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3159 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[TargetID]; 3160 if (!TargetFlags->TargetExists) 3161 continue; 3162 Length += sprintf(&Buffer[Length], " %2d %9u %9u", TargetID, TargetStatistics[TargetID].ReadCommands, TargetStatistics[TargetID].WriteCommands); 3163 if (TargetStatistics[TargetID].TotalBytesRead.Billions > 0) 3164 Length += sprintf(&Buffer[Length], " %9u%09u", TargetStatistics[TargetID].TotalBytesRead.Billions, TargetStatistics[TargetID].TotalBytesRead.Units); 3165 else 3166 Length += sprintf(&Buffer[Length], " %9u", TargetStatistics[TargetID].TotalBytesRead.Units); 3167 if (TargetStatistics[TargetID].TotalBytesWritten.Billions > 0) 3168 Length += sprintf(&Buffer[Length], " %9u%09u\n", TargetStatistics[TargetID].TotalBytesWritten.Billions, TargetStatistics[TargetID].TotalBytesWritten.Units); 3169 else 3170 Length += sprintf(&Buffer[Length], " %9u\n", TargetStatistics[TargetID].TotalBytesWritten.Units); 3171 } 3172 Length += sprintf(&Buffer[Length], "\n\ 3173Target Command 0-1KB 1-2KB 2-4KB 4-8KB 8-16KB\n\ 3174====== ======= ========= ========= ========= ========= =========\n"); 3175 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3176 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[TargetID]; 3177 if (!TargetFlags->TargetExists) 3178 continue; 3179 Length += 3180 sprintf(&Buffer[Length], 3181 " %2d Read %9u %9u %9u %9u %9u\n", TargetID, 3182 TargetStatistics[TargetID].ReadCommandSizeBuckets[0], 3183 TargetStatistics[TargetID].ReadCommandSizeBuckets[1], TargetStatistics[TargetID].ReadCommandSizeBuckets[2], TargetStatistics[TargetID].ReadCommandSizeBuckets[3], TargetStatistics[TargetID].ReadCommandSizeBuckets[4]); 3184 Length += 3185 sprintf(&Buffer[Length], 3186 " %2d Write %9u %9u %9u %9u %9u\n", TargetID, 3187 TargetStatistics[TargetID].WriteCommandSizeBuckets[0], 3188 TargetStatistics[TargetID].WriteCommandSizeBuckets[1], TargetStatistics[TargetID].WriteCommandSizeBuckets[2], TargetStatistics[TargetID].WriteCommandSizeBuckets[3], TargetStatistics[TargetID].WriteCommandSizeBuckets[4]); 3189 } 3190 Length += sprintf(&Buffer[Length], "\n\ 3191Target Command 16-32KB 32-64KB 64-128KB 128-256KB 256KB+\n\ 3192====== ======= ========= ========= ========= ========= =========\n"); 3193 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3194 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[TargetID]; 3195 if (!TargetFlags->TargetExists) 3196 continue; 3197 Length += 3198 sprintf(&Buffer[Length], 3199 " %2d Read %9u %9u %9u %9u %9u\n", TargetID, 3200 TargetStatistics[TargetID].ReadCommandSizeBuckets[5], 3201 TargetStatistics[TargetID].ReadCommandSizeBuckets[6], TargetStatistics[TargetID].ReadCommandSizeBuckets[7], TargetStatistics[TargetID].ReadCommandSizeBuckets[8], TargetStatistics[TargetID].ReadCommandSizeBuckets[9]); 3202 Length += 3203 sprintf(&Buffer[Length], 3204 " %2d Write %9u %9u %9u %9u %9u\n", TargetID, 3205 TargetStatistics[TargetID].WriteCommandSizeBuckets[5], 3206 TargetStatistics[TargetID].WriteCommandSizeBuckets[6], TargetStatistics[TargetID].WriteCommandSizeBuckets[7], TargetStatistics[TargetID].WriteCommandSizeBuckets[8], TargetStatistics[TargetID].WriteCommandSizeBuckets[9]); 3207 } 3208 Length += sprintf(&Buffer[Length], "\n\n\ 3209 ERROR RECOVERY STATISTICS\n\ 3210\n\ 3211 Command Aborts Bus Device Resets Host Adapter Resets\n\ 3212Target Requested Completed Requested Completed Requested Completed\n\ 3213 ID \\\\\\\\ Attempted //// \\\\\\\\ Attempted //// \\\\\\\\ Attempted ////\n\ 3214====== ===== ===== ===== ===== ===== ===== ===== ===== =====\n"); 3215 for (TargetID = 0; TargetID < HostAdapter->MaxTargetDevices; TargetID++) { 3216 struct BusLogic_TargetFlags *TargetFlags = &HostAdapter->TargetFlags[TargetID]; 3217 if (!TargetFlags->TargetExists) 3218 continue; 3219 Length += sprintf(&Buffer[Length], "\ 3220 %2d %5d %5d %5d %5d %5d %5d %5d %5d %5d\n", TargetID, TargetStatistics[TargetID].CommandAbortsRequested, TargetStatistics[TargetID].CommandAbortsAttempted, TargetStatistics[TargetID].CommandAbortsCompleted, TargetStatistics[TargetID].BusDeviceResetsRequested, TargetStatistics[TargetID].BusDeviceResetsAttempted, TargetStatistics[TargetID].BusDeviceResetsCompleted, TargetStatistics[TargetID].HostAdapterResetsRequested, TargetStatistics[TargetID].HostAdapterResetsAttempted, TargetStatistics[TargetID].HostAdapterResetsCompleted); 3221 } 3222 Length += sprintf(&Buffer[Length], "\nExternal Host Adapter Resets: %d\n", HostAdapter->ExternalHostAdapterResets); 3223 Length += sprintf(&Buffer[Length], "Host Adapter Internal Errors: %d\n", HostAdapter->HostAdapterInternalErrors); 3224 if (Length >= BusLogic_MessageBufferSize) 3225 BusLogic_Error("Message Buffer length %d exceeds size %d\n", HostAdapter, Length, BusLogic_MessageBufferSize); 3226 if ((Length -= Offset) <= 0) 3227 return 0; 3228 if (Length >= BytesAvailable) 3229 Length = BytesAvailable; 3230 memcpy(ProcBuffer, HostAdapter->MessageBuffer + Offset, Length); 3231 *StartPointer = ProcBuffer; 3232 return Length; 3233} 3234 3235 3236/* 3237 BusLogic_Message prints Driver Messages. 3238*/ 3239 3240static void BusLogic_Message(enum BusLogic_MessageLevel MessageLevel, char *Format, struct BusLogic_HostAdapter *HostAdapter, ...) 3241{ 3242 static char Buffer[BusLogic_LineBufferSize]; 3243 static bool BeginningOfLine = true; 3244 va_list Arguments; 3245 int Length = 0; 3246 va_start(Arguments, HostAdapter); 3247 Length = vsprintf(Buffer, Format, Arguments); 3248 va_end(Arguments); 3249 if (MessageLevel == BusLogic_AnnounceLevel) { 3250 static int AnnouncementLines = 0; 3251 strcpy(&HostAdapter->MessageBuffer[HostAdapter->MessageBufferLength], Buffer); 3252 HostAdapter->MessageBufferLength += Length; 3253 if (++AnnouncementLines <= 2) 3254 printk("%sscsi: %s", BusLogic_MessageLevelMap[MessageLevel], Buffer); 3255 } else if (MessageLevel == BusLogic_InfoLevel) { 3256 strcpy(&HostAdapter->MessageBuffer[HostAdapter->MessageBufferLength], Buffer); 3257 HostAdapter->MessageBufferLength += Length; 3258 if (BeginningOfLine) { 3259 if (Buffer[0] != '\n' || Length > 1) 3260 printk("%sscsi%d: %s", BusLogic_MessageLevelMap[MessageLevel], HostAdapter->HostNumber, Buffer); 3261 } else 3262 printk("%s", Buffer); 3263 } else { 3264 if (BeginningOfLine) { 3265 if (HostAdapter != NULL && HostAdapter->HostAdapterInitialized) 3266 printk("%sscsi%d: %s", BusLogic_MessageLevelMap[MessageLevel], HostAdapter->HostNumber, Buffer); 3267 else 3268 printk("%s%s", BusLogic_MessageLevelMap[MessageLevel], Buffer); 3269 } else 3270 printk("%s", Buffer); 3271 } 3272 BeginningOfLine = (Buffer[Length - 1] == '\n'); 3273} 3274 3275 3276/* 3277 BusLogic_ParseKeyword parses an individual option keyword. It returns true 3278 and updates the pointer if the keyword is recognized and false otherwise. 3279*/ 3280 3281static bool __init BusLogic_ParseKeyword(char **StringPointer, char *Keyword) 3282{ 3283 char *Pointer = *StringPointer; 3284 while (*Keyword != '\0') { 3285 char StringChar = *Pointer++; 3286 char KeywordChar = *Keyword++; 3287 if (StringChar >= 'A' && StringChar <= 'Z') 3288 StringChar += 'a' - 'Z'; 3289 if (KeywordChar >= 'A' && KeywordChar <= 'Z') 3290 KeywordChar += 'a' - 'Z'; 3291 if (StringChar != KeywordChar) 3292 return false; 3293 } 3294 *StringPointer = Pointer; 3295 return true; 3296} 3297 3298 3299/* 3300 BusLogic_ParseDriverOptions handles processing of BusLogic Driver Options 3301 specifications. 3302 3303 BusLogic Driver Options may be specified either via the Linux Kernel Command 3304 Line or via the Loadable Kernel Module Installation Facility. Driver Options 3305 for multiple host adapters may be specified either by separating the option 3306 strings by a semicolon, or by specifying multiple "BusLogic=" strings on the 3307 command line. Individual option specifications for a single host adapter are 3308 separated by commas. The Probing and Debugging Options apply to all host 3309 adapters whereas the remaining options apply individually only to the 3310 selected host adapter. 3311 3312 The BusLogic Driver Probing Options are described in 3313 <file:Documentation/scsi/BusLogic.txt>. 3314*/ 3315 3316static int __init BusLogic_ParseDriverOptions(char *OptionsString) 3317{ 3318 while (true) { 3319 struct BusLogic_DriverOptions *DriverOptions = &BusLogic_DriverOptions[BusLogic_DriverOptionsCount++]; 3320 int TargetID; 3321 memset(DriverOptions, 0, sizeof(struct BusLogic_DriverOptions)); 3322 while (*OptionsString != '\0' && *OptionsString != ';') { 3323 /* Probing Options. */ 3324 if (BusLogic_ParseKeyword(&OptionsString, "IO:")) { 3325 unsigned long IO_Address = simple_strtoul(OptionsString, &OptionsString, 0); 3326 BusLogic_ProbeOptions.LimitedProbeISA = true; 3327 switch (IO_Address) { 3328 case 0x330: 3329 BusLogic_ProbeOptions.Probe330 = true; 3330 break; 3331 case 0x334: 3332 BusLogic_ProbeOptions.Probe334 = true; 3333 break; 3334 case 0x230: 3335 BusLogic_ProbeOptions.Probe230 = true; 3336 break; 3337 case 0x234: 3338 BusLogic_ProbeOptions.Probe234 = true; 3339 break; 3340 case 0x130: 3341 BusLogic_ProbeOptions.Probe130 = true; 3342 break; 3343 case 0x134: 3344 BusLogic_ProbeOptions.Probe134 = true; 3345 break; 3346 default: 3347 BusLogic_Error("BusLogic: Invalid Driver Options " "(invalid I/O Address 0x%X)\n", NULL, IO_Address); 3348 return 0; 3349 } 3350 } else if (BusLogic_ParseKeyword(&OptionsString, "NoProbeISA")) 3351 BusLogic_ProbeOptions.NoProbeISA = true; 3352 else if (BusLogic_ParseKeyword(&OptionsString, "NoProbePCI")) 3353 BusLogic_ProbeOptions.NoProbePCI = true; 3354 else if (BusLogic_ParseKeyword(&OptionsString, "NoProbe")) 3355 BusLogic_ProbeOptions.NoProbe = true; 3356 else if (BusLogic_ParseKeyword(&OptionsString, "NoSortPCI")) 3357 BusLogic_ProbeOptions.NoSortPCI = true; 3358 else if (BusLogic_ParseKeyword(&OptionsString, "MultiMasterFirst")) 3359 BusLogic_ProbeOptions.MultiMasterFirst = true; 3360 else if (BusLogic_ParseKeyword(&OptionsString, "FlashPointFirst")) 3361 BusLogic_ProbeOptions.FlashPointFirst = true; 3362 /* Tagged Queuing Options. */ 3363 else if (BusLogic_ParseKeyword(&OptionsString, "QueueDepth:[") || BusLogic_ParseKeyword(&OptionsString, "QD:[")) { 3364 for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++) { 3365 unsigned short QueueDepth = simple_strtoul(OptionsString, &OptionsString, 0); 3366 if (QueueDepth > BusLogic_MaxTaggedQueueDepth) { 3367 BusLogic_Error("BusLogic: Invalid Driver Options " "(invalid Queue Depth %d)\n", NULL, QueueDepth); 3368 return 0; 3369 } 3370 DriverOptions->QueueDepth[TargetID] = QueueDepth; 3371 if (*OptionsString == ',') 3372 OptionsString++; 3373 else if (*OptionsString == ']') 3374 break; 3375 else { 3376 BusLogic_Error("BusLogic: Invalid Driver Options " "(',' or ']' expected at '%s')\n", NULL, OptionsString); 3377 return 0; 3378 } 3379 } 3380 if (*OptionsString != ']') { 3381 BusLogic_Error("BusLogic: Invalid Driver Options " "(']' expected at '%s')\n", NULL, OptionsString); 3382 return 0; 3383 } else 3384 OptionsString++; 3385 } else if (BusLogic_ParseKeyword(&OptionsString, "QueueDepth:") || BusLogic_ParseKeyword(&OptionsString, "QD:")) { 3386 unsigned short QueueDepth = simple_strtoul(OptionsString, &OptionsString, 0); 3387 if (QueueDepth == 0 || QueueDepth > BusLogic_MaxTaggedQueueDepth) { 3388 BusLogic_Error("BusLogic: Invalid Driver Options " "(invalid Queue Depth %d)\n", NULL, QueueDepth); 3389 return 0; 3390 } 3391 DriverOptions->CommonQueueDepth = QueueDepth; 3392 for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++) 3393 DriverOptions->QueueDepth[TargetID] = QueueDepth; 3394 } else if (BusLogic_ParseKeyword(&OptionsString, "TaggedQueuing:") || BusLogic_ParseKeyword(&OptionsString, "TQ:")) { 3395 if (BusLogic_ParseKeyword(&OptionsString, "Default")) { 3396 DriverOptions->TaggedQueuingPermitted = 0x0000; 3397 DriverOptions->TaggedQueuingPermittedMask = 0x0000; 3398 } else if (BusLogic_ParseKeyword(&OptionsString, "Enable")) { 3399 DriverOptions->TaggedQueuingPermitted = 0xFFFF; 3400 DriverOptions->TaggedQueuingPermittedMask = 0xFFFF; 3401 } else if (BusLogic_ParseKeyword(&OptionsString, "Disable")) { 3402 DriverOptions->TaggedQueuingPermitted = 0x0000; 3403 DriverOptions->TaggedQueuingPermittedMask = 0xFFFF; 3404 } else { 3405 unsigned short TargetBit; 3406 for (TargetID = 0, TargetBit = 1; TargetID < BusLogic_MaxTargetDevices; TargetID++, TargetBit <<= 1) 3407 switch (*OptionsString++) { 3408 case 'Y': 3409 DriverOptions->TaggedQueuingPermitted |= TargetBit; 3410 DriverOptions->TaggedQueuingPermittedMask |= TargetBit; 3411 break; 3412 case 'N': 3413 DriverOptions->TaggedQueuingPermitted &= ~TargetBit; 3414 DriverOptions->TaggedQueuingPermittedMask |= TargetBit; 3415 break; 3416 case 'X': 3417 break; 3418 default: 3419 OptionsString--; 3420 TargetID = BusLogic_MaxTargetDevices; 3421 break; 3422 } 3423 } 3424 } 3425 /* Miscellaneous Options. */ 3426 else if (BusLogic_ParseKeyword(&OptionsString, "BusSettleTime:") || BusLogic_ParseKeyword(&OptionsString, "BST:")) { 3427 unsigned short BusSettleTime = simple_strtoul(OptionsString, &OptionsString, 0); 3428 if (BusSettleTime > 5 * 60) { 3429 BusLogic_Error("BusLogic: Invalid Driver Options " "(invalid Bus Settle Time %d)\n", NULL, BusSettleTime); 3430 return 0; 3431 } 3432 DriverOptions->BusSettleTime = BusSettleTime; 3433 } else if (BusLogic_ParseKeyword(&OptionsString, "InhibitTargetInquiry")) 3434 DriverOptions->LocalOptions.InhibitTargetInquiry = true; 3435 /* Debugging Options. */ 3436 else if (BusLogic_ParseKeyword(&OptionsString, "TraceProbe")) 3437 BusLogic_GlobalOptions.TraceProbe = true; 3438 else if (BusLogic_ParseKeyword(&OptionsString, "TraceHardwareReset")) 3439 BusLogic_GlobalOptions.TraceHardwareReset = true; 3440 else if (BusLogic_ParseKeyword(&OptionsString, "TraceConfiguration")) 3441 BusLogic_GlobalOptions.TraceConfiguration = true; 3442 else if (BusLogic_ParseKeyword(&OptionsString, "TraceErrors")) 3443 BusLogic_GlobalOptions.TraceErrors = true; 3444 else if (BusLogic_ParseKeyword(&OptionsString, "Debug")) { 3445 BusLogic_GlobalOptions.TraceProbe = true; 3446 BusLogic_GlobalOptions.TraceHardwareReset = true; 3447 BusLogic_GlobalOptions.TraceConfiguration = true; 3448 BusLogic_GlobalOptions.TraceErrors = true; 3449 } 3450 if (*OptionsString == ',') 3451 OptionsString++; 3452 else if (*OptionsString != ';' && *OptionsString != '\0') { 3453 BusLogic_Error("BusLogic: Unexpected Driver Option '%s' " "ignored\n", NULL, OptionsString); 3454 *OptionsString = '\0'; 3455 } 3456 } 3457 if (!(BusLogic_DriverOptionsCount == 0 || BusLogic_ProbeInfoCount == 0 || BusLogic_DriverOptionsCount == BusLogic_ProbeInfoCount)) { 3458 BusLogic_Error("BusLogic: Invalid Driver Options " "(all or no I/O Addresses must be specified)\n", NULL); 3459 return 0; 3460 } 3461 /* 3462 Tagged Queuing is disabled when the Queue Depth is 1 since queuing 3463 multiple commands is not possible. 3464 */ 3465 for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++) 3466 if (DriverOptions->QueueDepth[TargetID] == 1) { 3467 unsigned short TargetBit = 1 << TargetID; 3468 DriverOptions->TaggedQueuingPermitted &= ~TargetBit; 3469 DriverOptions->TaggedQueuingPermittedMask |= TargetBit; 3470 } 3471 if (*OptionsString == ';') 3472 OptionsString++; 3473 if (*OptionsString == '\0') 3474 return 0; 3475 } 3476 return 1; 3477} 3478 3479/* 3480 Get it all started 3481*/ 3482 3483static struct scsi_host_template Bus_Logic_template = { 3484 .module = THIS_MODULE, 3485 .proc_name = "BusLogic", 3486 .proc_info = BusLogic_ProcDirectoryInfo, 3487 .name = "BusLogic", 3488 .info = BusLogic_DriverInfo, 3489 .queuecommand = BusLogic_QueueCommand, 3490 .slave_configure = BusLogic_SlaveConfigure, 3491 .bios_param = BusLogic_BIOSDiskParameters, 3492 .eh_host_reset_handler = BusLogic_host_reset, 3493 .unchecked_isa_dma = 1, 3494 .max_sectors = 128, 3495 .use_clustering = ENABLE_CLUSTERING, 3496}; 3497 3498/* 3499 BusLogic_Setup handles processing of Kernel Command Line Arguments. 3500*/ 3501 3502static int __init BusLogic_Setup(char *str) 3503{ 3504 int ints[3]; 3505 3506 (void) get_options(str, ARRAY_SIZE(ints), ints); 3507 3508 if (ints[0] != 0) { 3509 BusLogic_Error("BusLogic: Obsolete Command Line Entry " "Format Ignored\n", NULL); 3510 return 0; 3511 } 3512 if (str == NULL || *str == '\0') 3513 return 0; 3514 return BusLogic_ParseDriverOptions(str); 3515} 3516 3517/* 3518 * Exit function. Deletes all hosts associated with this driver. 3519 */ 3520 3521static void __exit BusLogic_exit(void) 3522{ 3523 struct BusLogic_HostAdapter *ha, *next; 3524 3525 list_for_each_entry_safe(ha, next, &BusLogic_host_list, host_list) 3526 BusLogic_ReleaseHostAdapter(ha); 3527} 3528 3529__setup("BusLogic=", BusLogic_Setup); 3530 3531#ifdef MODULE 3532static struct pci_device_id BusLogic_pci_tbl[] __devinitdata = { 3533 { PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_MULTIMASTER, 3534 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, 3535 { PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_MULTIMASTER_NC, 3536 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, 3537 { PCI_VENDOR_ID_BUSLOGIC, PCI_DEVICE_ID_BUSLOGIC_FLASHPOINT, 3538 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, 3539 { } 3540}; 3541#endif 3542MODULE_DEVICE_TABLE(pci, BusLogic_pci_tbl); 3543 3544module_init(BusLogic_init); 3545module_exit(BusLogic_exit); 3546