ux500: remove ambiguous irq macros
[linux-2.6/linux-acpi-2.6/ibm-acpi-2.6.git] / drivers / block / DAC960.c
blob1f286ab461d3d62471dbaa5323cd468b1080a842
1 /*
3 Linux Driver for Mylex DAC960/AcceleRAID/eXtremeRAID PCI RAID Controllers
5 Copyright 1998-2001 by Leonard N. Zubkoff <lnz@dandelion.com>
6 Portions Copyright 2002 by Mylex (An IBM Business Unit)
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.
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.
20 #define DAC960_DriverVersion "2.5.49"
21 #define DAC960_DriverDate "21 Aug 2007"
24 #include <linux/module.h>
25 #include <linux/types.h>
26 #include <linux/miscdevice.h>
27 #include <linux/blkdev.h>
28 #include <linux/bio.h>
29 #include <linux/completion.h>
30 #include <linux/delay.h>
31 #include <linux/genhd.h>
32 #include <linux/hdreg.h>
33 #include <linux/blkpg.h>
34 #include <linux/dma-mapping.h>
35 #include <linux/interrupt.h>
36 #include <linux/ioport.h>
37 #include <linux/mm.h>
38 #include <linux/slab.h>
39 #include <linux/mutex.h>
40 #include <linux/proc_fs.h>
41 #include <linux/seq_file.h>
42 #include <linux/reboot.h>
43 #include <linux/spinlock.h>
44 #include <linux/timer.h>
45 #include <linux/pci.h>
46 #include <linux/init.h>
47 #include <linux/jiffies.h>
48 #include <linux/random.h>
49 #include <linux/scatterlist.h>
50 #include <asm/io.h>
51 #include <asm/uaccess.h>
52 #include "DAC960.h"
54 #define DAC960_GAM_MINOR 252
57 static DEFINE_MUTEX(DAC960_mutex);
58 static DAC960_Controller_T *DAC960_Controllers[DAC960_MaxControllers];
59 static int DAC960_ControllerCount;
60 static struct proc_dir_entry *DAC960_ProcDirectoryEntry;
62 static long disk_size(DAC960_Controller_T *p, int drive_nr)
64 if (p->FirmwareType == DAC960_V1_Controller) {
65 if (drive_nr >= p->LogicalDriveCount)
66 return 0;
67 return p->V1.LogicalDriveInformation[drive_nr].
68 LogicalDriveSize;
69 } else {
70 DAC960_V2_LogicalDeviceInfo_T *i =
71 p->V2.LogicalDeviceInformation[drive_nr];
72 if (i == NULL)
73 return 0;
74 return i->ConfigurableDeviceSize;
78 static int DAC960_open(struct block_device *bdev, fmode_t mode)
80 struct gendisk *disk = bdev->bd_disk;
81 DAC960_Controller_T *p = disk->queue->queuedata;
82 int drive_nr = (long)disk->private_data;
83 int ret = -ENXIO;
85 mutex_lock(&DAC960_mutex);
86 if (p->FirmwareType == DAC960_V1_Controller) {
87 if (p->V1.LogicalDriveInformation[drive_nr].
88 LogicalDriveState == DAC960_V1_LogicalDrive_Offline)
89 goto out;
90 } else {
91 DAC960_V2_LogicalDeviceInfo_T *i =
92 p->V2.LogicalDeviceInformation[drive_nr];
93 if (!i || i->LogicalDeviceState == DAC960_V2_LogicalDevice_Offline)
94 goto out;
97 check_disk_change(bdev);
99 if (!get_capacity(p->disks[drive_nr]))
100 goto out;
101 ret = 0;
102 out:
103 mutex_unlock(&DAC960_mutex);
104 return ret;
107 static int DAC960_getgeo(struct block_device *bdev, struct hd_geometry *geo)
109 struct gendisk *disk = bdev->bd_disk;
110 DAC960_Controller_T *p = disk->queue->queuedata;
111 int drive_nr = (long)disk->private_data;
113 if (p->FirmwareType == DAC960_V1_Controller) {
114 geo->heads = p->V1.GeometryTranslationHeads;
115 geo->sectors = p->V1.GeometryTranslationSectors;
116 geo->cylinders = p->V1.LogicalDriveInformation[drive_nr].
117 LogicalDriveSize / (geo->heads * geo->sectors);
118 } else {
119 DAC960_V2_LogicalDeviceInfo_T *i =
120 p->V2.LogicalDeviceInformation[drive_nr];
121 switch (i->DriveGeometry) {
122 case DAC960_V2_Geometry_128_32:
123 geo->heads = 128;
124 geo->sectors = 32;
125 break;
126 case DAC960_V2_Geometry_255_63:
127 geo->heads = 255;
128 geo->sectors = 63;
129 break;
130 default:
131 DAC960_Error("Illegal Logical Device Geometry %d\n",
132 p, i->DriveGeometry);
133 return -EINVAL;
136 geo->cylinders = i->ConfigurableDeviceSize /
137 (geo->heads * geo->sectors);
140 return 0;
143 static int DAC960_media_changed(struct gendisk *disk)
145 DAC960_Controller_T *p = disk->queue->queuedata;
146 int drive_nr = (long)disk->private_data;
148 if (!p->LogicalDriveInitiallyAccessible[drive_nr])
149 return 1;
150 return 0;
153 static int DAC960_revalidate_disk(struct gendisk *disk)
155 DAC960_Controller_T *p = disk->queue->queuedata;
156 int unit = (long)disk->private_data;
158 set_capacity(disk, disk_size(p, unit));
159 return 0;
162 static const struct block_device_operations DAC960_BlockDeviceOperations = {
163 .owner = THIS_MODULE,
164 .open = DAC960_open,
165 .getgeo = DAC960_getgeo,
166 .media_changed = DAC960_media_changed,
167 .revalidate_disk = DAC960_revalidate_disk,
172 DAC960_AnnounceDriver announces the Driver Version and Date, Author's Name,
173 Copyright Notice, and Electronic Mail Address.
176 static void DAC960_AnnounceDriver(DAC960_Controller_T *Controller)
178 DAC960_Announce("***** DAC960 RAID Driver Version "
179 DAC960_DriverVersion " of "
180 DAC960_DriverDate " *****\n", Controller);
181 DAC960_Announce("Copyright 1998-2001 by Leonard N. Zubkoff "
182 "<lnz@dandelion.com>\n", Controller);
187 DAC960_Failure prints a standardized error message, and then returns false.
190 static bool DAC960_Failure(DAC960_Controller_T *Controller,
191 unsigned char *ErrorMessage)
193 DAC960_Error("While configuring DAC960 PCI RAID Controller at\n",
194 Controller);
195 if (Controller->IO_Address == 0)
196 DAC960_Error("PCI Bus %d Device %d Function %d I/O Address N/A "
197 "PCI Address 0x%X\n", Controller,
198 Controller->Bus, Controller->Device,
199 Controller->Function, Controller->PCI_Address);
200 else DAC960_Error("PCI Bus %d Device %d Function %d I/O Address "
201 "0x%X PCI Address 0x%X\n", Controller,
202 Controller->Bus, Controller->Device,
203 Controller->Function, Controller->IO_Address,
204 Controller->PCI_Address);
205 DAC960_Error("%s FAILED - DETACHING\n", Controller, ErrorMessage);
206 return false;
210 init_dma_loaf() and slice_dma_loaf() are helper functions for
211 aggregating the dma-mapped memory for a well-known collection of
212 data structures that are of different lengths.
214 These routines don't guarantee any alignment. The caller must
215 include any space needed for alignment in the sizes of the structures
216 that are passed in.
219 static bool init_dma_loaf(struct pci_dev *dev, struct dma_loaf *loaf,
220 size_t len)
222 void *cpu_addr;
223 dma_addr_t dma_handle;
225 cpu_addr = pci_alloc_consistent(dev, len, &dma_handle);
226 if (cpu_addr == NULL)
227 return false;
229 loaf->cpu_free = loaf->cpu_base = cpu_addr;
230 loaf->dma_free =loaf->dma_base = dma_handle;
231 loaf->length = len;
232 memset(cpu_addr, 0, len);
233 return true;
236 static void *slice_dma_loaf(struct dma_loaf *loaf, size_t len,
237 dma_addr_t *dma_handle)
239 void *cpu_end = loaf->cpu_free + len;
240 void *cpu_addr = loaf->cpu_free;
242 BUG_ON(cpu_end > loaf->cpu_base + loaf->length);
243 *dma_handle = loaf->dma_free;
244 loaf->cpu_free = cpu_end;
245 loaf->dma_free += len;
246 return cpu_addr;
249 static void free_dma_loaf(struct pci_dev *dev, struct dma_loaf *loaf_handle)
251 if (loaf_handle->cpu_base != NULL)
252 pci_free_consistent(dev, loaf_handle->length,
253 loaf_handle->cpu_base, loaf_handle->dma_base);
258 DAC960_CreateAuxiliaryStructures allocates and initializes the auxiliary
259 data structures for Controller. It returns true on success and false on
260 failure.
263 static bool DAC960_CreateAuxiliaryStructures(DAC960_Controller_T *Controller)
265 int CommandAllocationLength, CommandAllocationGroupSize;
266 int CommandsRemaining = 0, CommandIdentifier, CommandGroupByteCount;
267 void *AllocationPointer = NULL;
268 void *ScatterGatherCPU = NULL;
269 dma_addr_t ScatterGatherDMA;
270 struct pci_pool *ScatterGatherPool;
271 void *RequestSenseCPU = NULL;
272 dma_addr_t RequestSenseDMA;
273 struct pci_pool *RequestSensePool = NULL;
275 if (Controller->FirmwareType == DAC960_V1_Controller)
277 CommandAllocationLength = offsetof(DAC960_Command_T, V1.EndMarker);
278 CommandAllocationGroupSize = DAC960_V1_CommandAllocationGroupSize;
279 ScatterGatherPool = pci_pool_create("DAC960_V1_ScatterGather",
280 Controller->PCIDevice,
281 DAC960_V1_ScatterGatherLimit * sizeof(DAC960_V1_ScatterGatherSegment_T),
282 sizeof(DAC960_V1_ScatterGatherSegment_T), 0);
283 if (ScatterGatherPool == NULL)
284 return DAC960_Failure(Controller,
285 "AUXILIARY STRUCTURE CREATION (SG)");
286 Controller->ScatterGatherPool = ScatterGatherPool;
288 else
290 CommandAllocationLength = offsetof(DAC960_Command_T, V2.EndMarker);
291 CommandAllocationGroupSize = DAC960_V2_CommandAllocationGroupSize;
292 ScatterGatherPool = pci_pool_create("DAC960_V2_ScatterGather",
293 Controller->PCIDevice,
294 DAC960_V2_ScatterGatherLimit * sizeof(DAC960_V2_ScatterGatherSegment_T),
295 sizeof(DAC960_V2_ScatterGatherSegment_T), 0);
296 if (ScatterGatherPool == NULL)
297 return DAC960_Failure(Controller,
298 "AUXILIARY STRUCTURE CREATION (SG)");
299 RequestSensePool = pci_pool_create("DAC960_V2_RequestSense",
300 Controller->PCIDevice, sizeof(DAC960_SCSI_RequestSense_T),
301 sizeof(int), 0);
302 if (RequestSensePool == NULL) {
303 pci_pool_destroy(ScatterGatherPool);
304 return DAC960_Failure(Controller,
305 "AUXILIARY STRUCTURE CREATION (SG)");
307 Controller->ScatterGatherPool = ScatterGatherPool;
308 Controller->V2.RequestSensePool = RequestSensePool;
310 Controller->CommandAllocationGroupSize = CommandAllocationGroupSize;
311 Controller->FreeCommands = NULL;
312 for (CommandIdentifier = 1;
313 CommandIdentifier <= Controller->DriverQueueDepth;
314 CommandIdentifier++)
316 DAC960_Command_T *Command;
317 if (--CommandsRemaining <= 0)
319 CommandsRemaining =
320 Controller->DriverQueueDepth - CommandIdentifier + 1;
321 if (CommandsRemaining > CommandAllocationGroupSize)
322 CommandsRemaining = CommandAllocationGroupSize;
323 CommandGroupByteCount =
324 CommandsRemaining * CommandAllocationLength;
325 AllocationPointer = kzalloc(CommandGroupByteCount, GFP_ATOMIC);
326 if (AllocationPointer == NULL)
327 return DAC960_Failure(Controller,
328 "AUXILIARY STRUCTURE CREATION");
330 Command = (DAC960_Command_T *) AllocationPointer;
331 AllocationPointer += CommandAllocationLength;
332 Command->CommandIdentifier = CommandIdentifier;
333 Command->Controller = Controller;
334 Command->Next = Controller->FreeCommands;
335 Controller->FreeCommands = Command;
336 Controller->Commands[CommandIdentifier-1] = Command;
337 ScatterGatherCPU = pci_pool_alloc(ScatterGatherPool, GFP_ATOMIC,
338 &ScatterGatherDMA);
339 if (ScatterGatherCPU == NULL)
340 return DAC960_Failure(Controller, "AUXILIARY STRUCTURE CREATION");
342 if (RequestSensePool != NULL) {
343 RequestSenseCPU = pci_pool_alloc(RequestSensePool, GFP_ATOMIC,
344 &RequestSenseDMA);
345 if (RequestSenseCPU == NULL) {
346 pci_pool_free(ScatterGatherPool, ScatterGatherCPU,
347 ScatterGatherDMA);
348 return DAC960_Failure(Controller,
349 "AUXILIARY STRUCTURE CREATION");
352 if (Controller->FirmwareType == DAC960_V1_Controller) {
353 Command->cmd_sglist = Command->V1.ScatterList;
354 Command->V1.ScatterGatherList =
355 (DAC960_V1_ScatterGatherSegment_T *)ScatterGatherCPU;
356 Command->V1.ScatterGatherListDMA = ScatterGatherDMA;
357 sg_init_table(Command->cmd_sglist, DAC960_V1_ScatterGatherLimit);
358 } else {
359 Command->cmd_sglist = Command->V2.ScatterList;
360 Command->V2.ScatterGatherList =
361 (DAC960_V2_ScatterGatherSegment_T *)ScatterGatherCPU;
362 Command->V2.ScatterGatherListDMA = ScatterGatherDMA;
363 Command->V2.RequestSense =
364 (DAC960_SCSI_RequestSense_T *)RequestSenseCPU;
365 Command->V2.RequestSenseDMA = RequestSenseDMA;
366 sg_init_table(Command->cmd_sglist, DAC960_V2_ScatterGatherLimit);
369 return true;
374 DAC960_DestroyAuxiliaryStructures deallocates the auxiliary data
375 structures for Controller.
378 static void DAC960_DestroyAuxiliaryStructures(DAC960_Controller_T *Controller)
380 int i;
381 struct pci_pool *ScatterGatherPool = Controller->ScatterGatherPool;
382 struct pci_pool *RequestSensePool = NULL;
383 void *ScatterGatherCPU;
384 dma_addr_t ScatterGatherDMA;
385 void *RequestSenseCPU;
386 dma_addr_t RequestSenseDMA;
387 DAC960_Command_T *CommandGroup = NULL;
390 if (Controller->FirmwareType == DAC960_V2_Controller)
391 RequestSensePool = Controller->V2.RequestSensePool;
393 Controller->FreeCommands = NULL;
394 for (i = 0; i < Controller->DriverQueueDepth; i++)
396 DAC960_Command_T *Command = Controller->Commands[i];
398 if (Command == NULL)
399 continue;
401 if (Controller->FirmwareType == DAC960_V1_Controller) {
402 ScatterGatherCPU = (void *)Command->V1.ScatterGatherList;
403 ScatterGatherDMA = Command->V1.ScatterGatherListDMA;
404 RequestSenseCPU = NULL;
405 RequestSenseDMA = (dma_addr_t)0;
406 } else {
407 ScatterGatherCPU = (void *)Command->V2.ScatterGatherList;
408 ScatterGatherDMA = Command->V2.ScatterGatherListDMA;
409 RequestSenseCPU = (void *)Command->V2.RequestSense;
410 RequestSenseDMA = Command->V2.RequestSenseDMA;
412 if (ScatterGatherCPU != NULL)
413 pci_pool_free(ScatterGatherPool, ScatterGatherCPU, ScatterGatherDMA);
414 if (RequestSenseCPU != NULL)
415 pci_pool_free(RequestSensePool, RequestSenseCPU, RequestSenseDMA);
417 if ((Command->CommandIdentifier
418 % Controller->CommandAllocationGroupSize) == 1) {
420 * We can't free the group of commands until all of the
421 * request sense and scatter gather dma structures are free.
422 * Remember the beginning of the group, but don't free it
423 * until we've reached the beginning of the next group.
425 kfree(CommandGroup);
426 CommandGroup = Command;
428 Controller->Commands[i] = NULL;
430 kfree(CommandGroup);
432 if (Controller->CombinedStatusBuffer != NULL)
434 kfree(Controller->CombinedStatusBuffer);
435 Controller->CombinedStatusBuffer = NULL;
436 Controller->CurrentStatusBuffer = NULL;
439 if (ScatterGatherPool != NULL)
440 pci_pool_destroy(ScatterGatherPool);
441 if (Controller->FirmwareType == DAC960_V1_Controller)
442 return;
444 if (RequestSensePool != NULL)
445 pci_pool_destroy(RequestSensePool);
447 for (i = 0; i < DAC960_MaxLogicalDrives; i++) {
448 kfree(Controller->V2.LogicalDeviceInformation[i]);
449 Controller->V2.LogicalDeviceInformation[i] = NULL;
452 for (i = 0; i < DAC960_V2_MaxPhysicalDevices; i++)
454 kfree(Controller->V2.PhysicalDeviceInformation[i]);
455 Controller->V2.PhysicalDeviceInformation[i] = NULL;
456 kfree(Controller->V2.InquiryUnitSerialNumber[i]);
457 Controller->V2.InquiryUnitSerialNumber[i] = NULL;
463 DAC960_V1_ClearCommand clears critical fields of Command for DAC960 V1
464 Firmware Controllers.
467 static inline void DAC960_V1_ClearCommand(DAC960_Command_T *Command)
469 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
470 memset(CommandMailbox, 0, sizeof(DAC960_V1_CommandMailbox_T));
471 Command->V1.CommandStatus = 0;
476 DAC960_V2_ClearCommand clears critical fields of Command for DAC960 V2
477 Firmware Controllers.
480 static inline void DAC960_V2_ClearCommand(DAC960_Command_T *Command)
482 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
483 memset(CommandMailbox, 0, sizeof(DAC960_V2_CommandMailbox_T));
484 Command->V2.CommandStatus = 0;
489 DAC960_AllocateCommand allocates a Command structure from Controller's
490 free list. During driver initialization, a special initialization command
491 has been placed on the free list to guarantee that command allocation can
492 never fail.
495 static inline DAC960_Command_T *DAC960_AllocateCommand(DAC960_Controller_T
496 *Controller)
498 DAC960_Command_T *Command = Controller->FreeCommands;
499 if (Command == NULL) return NULL;
500 Controller->FreeCommands = Command->Next;
501 Command->Next = NULL;
502 return Command;
507 DAC960_DeallocateCommand deallocates Command, returning it to Controller's
508 free list.
511 static inline void DAC960_DeallocateCommand(DAC960_Command_T *Command)
513 DAC960_Controller_T *Controller = Command->Controller;
515 Command->Request = NULL;
516 Command->Next = Controller->FreeCommands;
517 Controller->FreeCommands = Command;
522 DAC960_WaitForCommand waits for a wake_up on Controller's Command Wait Queue.
525 static void DAC960_WaitForCommand(DAC960_Controller_T *Controller)
527 spin_unlock_irq(&Controller->queue_lock);
528 __wait_event(Controller->CommandWaitQueue, Controller->FreeCommands);
529 spin_lock_irq(&Controller->queue_lock);
533 DAC960_GEM_QueueCommand queues Command for DAC960 GEM Series Controllers.
536 static void DAC960_GEM_QueueCommand(DAC960_Command_T *Command)
538 DAC960_Controller_T *Controller = Command->Controller;
539 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
540 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
541 DAC960_V2_CommandMailbox_T *NextCommandMailbox =
542 Controller->V2.NextCommandMailbox;
544 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
545 DAC960_GEM_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
547 if (Controller->V2.PreviousCommandMailbox1->Words[0] == 0 ||
548 Controller->V2.PreviousCommandMailbox2->Words[0] == 0)
549 DAC960_GEM_MemoryMailboxNewCommand(ControllerBaseAddress);
551 Controller->V2.PreviousCommandMailbox2 =
552 Controller->V2.PreviousCommandMailbox1;
553 Controller->V2.PreviousCommandMailbox1 = NextCommandMailbox;
555 if (++NextCommandMailbox > Controller->V2.LastCommandMailbox)
556 NextCommandMailbox = Controller->V2.FirstCommandMailbox;
558 Controller->V2.NextCommandMailbox = NextCommandMailbox;
562 DAC960_BA_QueueCommand queues Command for DAC960 BA Series Controllers.
565 static void DAC960_BA_QueueCommand(DAC960_Command_T *Command)
567 DAC960_Controller_T *Controller = Command->Controller;
568 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
569 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
570 DAC960_V2_CommandMailbox_T *NextCommandMailbox =
571 Controller->V2.NextCommandMailbox;
572 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
573 DAC960_BA_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
574 if (Controller->V2.PreviousCommandMailbox1->Words[0] == 0 ||
575 Controller->V2.PreviousCommandMailbox2->Words[0] == 0)
576 DAC960_BA_MemoryMailboxNewCommand(ControllerBaseAddress);
577 Controller->V2.PreviousCommandMailbox2 =
578 Controller->V2.PreviousCommandMailbox1;
579 Controller->V2.PreviousCommandMailbox1 = NextCommandMailbox;
580 if (++NextCommandMailbox > Controller->V2.LastCommandMailbox)
581 NextCommandMailbox = Controller->V2.FirstCommandMailbox;
582 Controller->V2.NextCommandMailbox = NextCommandMailbox;
587 DAC960_LP_QueueCommand queues Command for DAC960 LP Series Controllers.
590 static void DAC960_LP_QueueCommand(DAC960_Command_T *Command)
592 DAC960_Controller_T *Controller = Command->Controller;
593 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
594 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
595 DAC960_V2_CommandMailbox_T *NextCommandMailbox =
596 Controller->V2.NextCommandMailbox;
597 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
598 DAC960_LP_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
599 if (Controller->V2.PreviousCommandMailbox1->Words[0] == 0 ||
600 Controller->V2.PreviousCommandMailbox2->Words[0] == 0)
601 DAC960_LP_MemoryMailboxNewCommand(ControllerBaseAddress);
602 Controller->V2.PreviousCommandMailbox2 =
603 Controller->V2.PreviousCommandMailbox1;
604 Controller->V2.PreviousCommandMailbox1 = NextCommandMailbox;
605 if (++NextCommandMailbox > Controller->V2.LastCommandMailbox)
606 NextCommandMailbox = Controller->V2.FirstCommandMailbox;
607 Controller->V2.NextCommandMailbox = NextCommandMailbox;
612 DAC960_LA_QueueCommandDualMode queues Command for DAC960 LA Series
613 Controllers with Dual Mode Firmware.
616 static void DAC960_LA_QueueCommandDualMode(DAC960_Command_T *Command)
618 DAC960_Controller_T *Controller = Command->Controller;
619 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
620 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
621 DAC960_V1_CommandMailbox_T *NextCommandMailbox =
622 Controller->V1.NextCommandMailbox;
623 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
624 DAC960_LA_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
625 if (Controller->V1.PreviousCommandMailbox1->Words[0] == 0 ||
626 Controller->V1.PreviousCommandMailbox2->Words[0] == 0)
627 DAC960_LA_MemoryMailboxNewCommand(ControllerBaseAddress);
628 Controller->V1.PreviousCommandMailbox2 =
629 Controller->V1.PreviousCommandMailbox1;
630 Controller->V1.PreviousCommandMailbox1 = NextCommandMailbox;
631 if (++NextCommandMailbox > Controller->V1.LastCommandMailbox)
632 NextCommandMailbox = Controller->V1.FirstCommandMailbox;
633 Controller->V1.NextCommandMailbox = NextCommandMailbox;
638 DAC960_LA_QueueCommandSingleMode queues Command for DAC960 LA Series
639 Controllers with Single Mode Firmware.
642 static void DAC960_LA_QueueCommandSingleMode(DAC960_Command_T *Command)
644 DAC960_Controller_T *Controller = Command->Controller;
645 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
646 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
647 DAC960_V1_CommandMailbox_T *NextCommandMailbox =
648 Controller->V1.NextCommandMailbox;
649 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
650 DAC960_LA_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
651 if (Controller->V1.PreviousCommandMailbox1->Words[0] == 0 ||
652 Controller->V1.PreviousCommandMailbox2->Words[0] == 0)
653 DAC960_LA_HardwareMailboxNewCommand(ControllerBaseAddress);
654 Controller->V1.PreviousCommandMailbox2 =
655 Controller->V1.PreviousCommandMailbox1;
656 Controller->V1.PreviousCommandMailbox1 = NextCommandMailbox;
657 if (++NextCommandMailbox > Controller->V1.LastCommandMailbox)
658 NextCommandMailbox = Controller->V1.FirstCommandMailbox;
659 Controller->V1.NextCommandMailbox = NextCommandMailbox;
664 DAC960_PG_QueueCommandDualMode queues Command for DAC960 PG Series
665 Controllers with Dual Mode Firmware.
668 static void DAC960_PG_QueueCommandDualMode(DAC960_Command_T *Command)
670 DAC960_Controller_T *Controller = Command->Controller;
671 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
672 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
673 DAC960_V1_CommandMailbox_T *NextCommandMailbox =
674 Controller->V1.NextCommandMailbox;
675 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
676 DAC960_PG_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
677 if (Controller->V1.PreviousCommandMailbox1->Words[0] == 0 ||
678 Controller->V1.PreviousCommandMailbox2->Words[0] == 0)
679 DAC960_PG_MemoryMailboxNewCommand(ControllerBaseAddress);
680 Controller->V1.PreviousCommandMailbox2 =
681 Controller->V1.PreviousCommandMailbox1;
682 Controller->V1.PreviousCommandMailbox1 = NextCommandMailbox;
683 if (++NextCommandMailbox > Controller->V1.LastCommandMailbox)
684 NextCommandMailbox = Controller->V1.FirstCommandMailbox;
685 Controller->V1.NextCommandMailbox = NextCommandMailbox;
690 DAC960_PG_QueueCommandSingleMode queues Command for DAC960 PG Series
691 Controllers with Single Mode Firmware.
694 static void DAC960_PG_QueueCommandSingleMode(DAC960_Command_T *Command)
696 DAC960_Controller_T *Controller = Command->Controller;
697 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
698 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
699 DAC960_V1_CommandMailbox_T *NextCommandMailbox =
700 Controller->V1.NextCommandMailbox;
701 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
702 DAC960_PG_WriteCommandMailbox(NextCommandMailbox, CommandMailbox);
703 if (Controller->V1.PreviousCommandMailbox1->Words[0] == 0 ||
704 Controller->V1.PreviousCommandMailbox2->Words[0] == 0)
705 DAC960_PG_HardwareMailboxNewCommand(ControllerBaseAddress);
706 Controller->V1.PreviousCommandMailbox2 =
707 Controller->V1.PreviousCommandMailbox1;
708 Controller->V1.PreviousCommandMailbox1 = NextCommandMailbox;
709 if (++NextCommandMailbox > Controller->V1.LastCommandMailbox)
710 NextCommandMailbox = Controller->V1.FirstCommandMailbox;
711 Controller->V1.NextCommandMailbox = NextCommandMailbox;
716 DAC960_PD_QueueCommand queues Command for DAC960 PD Series Controllers.
719 static void DAC960_PD_QueueCommand(DAC960_Command_T *Command)
721 DAC960_Controller_T *Controller = Command->Controller;
722 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
723 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
724 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
725 while (DAC960_PD_MailboxFullP(ControllerBaseAddress))
726 udelay(1);
727 DAC960_PD_WriteCommandMailbox(ControllerBaseAddress, CommandMailbox);
728 DAC960_PD_NewCommand(ControllerBaseAddress);
733 DAC960_P_QueueCommand queues Command for DAC960 P Series Controllers.
736 static void DAC960_P_QueueCommand(DAC960_Command_T *Command)
738 DAC960_Controller_T *Controller = Command->Controller;
739 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
740 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
741 CommandMailbox->Common.CommandIdentifier = Command->CommandIdentifier;
742 switch (CommandMailbox->Common.CommandOpcode)
744 case DAC960_V1_Enquiry:
745 CommandMailbox->Common.CommandOpcode = DAC960_V1_Enquiry_Old;
746 break;
747 case DAC960_V1_GetDeviceState:
748 CommandMailbox->Common.CommandOpcode = DAC960_V1_GetDeviceState_Old;
749 break;
750 case DAC960_V1_Read:
751 CommandMailbox->Common.CommandOpcode = DAC960_V1_Read_Old;
752 DAC960_PD_To_P_TranslateReadWriteCommand(CommandMailbox);
753 break;
754 case DAC960_V1_Write:
755 CommandMailbox->Common.CommandOpcode = DAC960_V1_Write_Old;
756 DAC960_PD_To_P_TranslateReadWriteCommand(CommandMailbox);
757 break;
758 case DAC960_V1_ReadWithScatterGather:
759 CommandMailbox->Common.CommandOpcode =
760 DAC960_V1_ReadWithScatterGather_Old;
761 DAC960_PD_To_P_TranslateReadWriteCommand(CommandMailbox);
762 break;
763 case DAC960_V1_WriteWithScatterGather:
764 CommandMailbox->Common.CommandOpcode =
765 DAC960_V1_WriteWithScatterGather_Old;
766 DAC960_PD_To_P_TranslateReadWriteCommand(CommandMailbox);
767 break;
768 default:
769 break;
771 while (DAC960_PD_MailboxFullP(ControllerBaseAddress))
772 udelay(1);
773 DAC960_PD_WriteCommandMailbox(ControllerBaseAddress, CommandMailbox);
774 DAC960_PD_NewCommand(ControllerBaseAddress);
779 DAC960_ExecuteCommand executes Command and waits for completion.
782 static void DAC960_ExecuteCommand(DAC960_Command_T *Command)
784 DAC960_Controller_T *Controller = Command->Controller;
785 DECLARE_COMPLETION_ONSTACK(Completion);
786 unsigned long flags;
787 Command->Completion = &Completion;
789 spin_lock_irqsave(&Controller->queue_lock, flags);
790 DAC960_QueueCommand(Command);
791 spin_unlock_irqrestore(&Controller->queue_lock, flags);
793 if (in_interrupt())
794 return;
795 wait_for_completion(&Completion);
800 DAC960_V1_ExecuteType3 executes a DAC960 V1 Firmware Controller Type 3
801 Command and waits for completion. It returns true on success and false
802 on failure.
805 static bool DAC960_V1_ExecuteType3(DAC960_Controller_T *Controller,
806 DAC960_V1_CommandOpcode_T CommandOpcode,
807 dma_addr_t DataDMA)
809 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
810 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
811 DAC960_V1_CommandStatus_T CommandStatus;
812 DAC960_V1_ClearCommand(Command);
813 Command->CommandType = DAC960_ImmediateCommand;
814 CommandMailbox->Type3.CommandOpcode = CommandOpcode;
815 CommandMailbox->Type3.BusAddress = DataDMA;
816 DAC960_ExecuteCommand(Command);
817 CommandStatus = Command->V1.CommandStatus;
818 DAC960_DeallocateCommand(Command);
819 return (CommandStatus == DAC960_V1_NormalCompletion);
824 DAC960_V1_ExecuteTypeB executes a DAC960 V1 Firmware Controller Type 3B
825 Command and waits for completion. It returns true on success and false
826 on failure.
829 static bool DAC960_V1_ExecuteType3B(DAC960_Controller_T *Controller,
830 DAC960_V1_CommandOpcode_T CommandOpcode,
831 unsigned char CommandOpcode2,
832 dma_addr_t DataDMA)
834 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
835 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
836 DAC960_V1_CommandStatus_T CommandStatus;
837 DAC960_V1_ClearCommand(Command);
838 Command->CommandType = DAC960_ImmediateCommand;
839 CommandMailbox->Type3B.CommandOpcode = CommandOpcode;
840 CommandMailbox->Type3B.CommandOpcode2 = CommandOpcode2;
841 CommandMailbox->Type3B.BusAddress = DataDMA;
842 DAC960_ExecuteCommand(Command);
843 CommandStatus = Command->V1.CommandStatus;
844 DAC960_DeallocateCommand(Command);
845 return (CommandStatus == DAC960_V1_NormalCompletion);
850 DAC960_V1_ExecuteType3D executes a DAC960 V1 Firmware Controller Type 3D
851 Command and waits for completion. It returns true on success and false
852 on failure.
855 static bool DAC960_V1_ExecuteType3D(DAC960_Controller_T *Controller,
856 DAC960_V1_CommandOpcode_T CommandOpcode,
857 unsigned char Channel,
858 unsigned char TargetID,
859 dma_addr_t DataDMA)
861 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
862 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
863 DAC960_V1_CommandStatus_T CommandStatus;
864 DAC960_V1_ClearCommand(Command);
865 Command->CommandType = DAC960_ImmediateCommand;
866 CommandMailbox->Type3D.CommandOpcode = CommandOpcode;
867 CommandMailbox->Type3D.Channel = Channel;
868 CommandMailbox->Type3D.TargetID = TargetID;
869 CommandMailbox->Type3D.BusAddress = DataDMA;
870 DAC960_ExecuteCommand(Command);
871 CommandStatus = Command->V1.CommandStatus;
872 DAC960_DeallocateCommand(Command);
873 return (CommandStatus == DAC960_V1_NormalCompletion);
878 DAC960_V2_GeneralInfo executes a DAC960 V2 Firmware General Information
879 Reading IOCTL Command and waits for completion. It returns true on success
880 and false on failure.
882 Return data in The controller's HealthStatusBuffer, which is dma-able memory
885 static bool DAC960_V2_GeneralInfo(DAC960_Controller_T *Controller)
887 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
888 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
889 DAC960_V2_CommandStatus_T CommandStatus;
890 DAC960_V2_ClearCommand(Command);
891 Command->CommandType = DAC960_ImmediateCommand;
892 CommandMailbox->Common.CommandOpcode = DAC960_V2_IOCTL;
893 CommandMailbox->Common.CommandControlBits
894 .DataTransferControllerToHost = true;
895 CommandMailbox->Common.CommandControlBits
896 .NoAutoRequestSense = true;
897 CommandMailbox->Common.DataTransferSize = sizeof(DAC960_V2_HealthStatusBuffer_T);
898 CommandMailbox->Common.IOCTL_Opcode = DAC960_V2_GetHealthStatus;
899 CommandMailbox->Common.DataTransferMemoryAddress
900 .ScatterGatherSegments[0]
901 .SegmentDataPointer =
902 Controller->V2.HealthStatusBufferDMA;
903 CommandMailbox->Common.DataTransferMemoryAddress
904 .ScatterGatherSegments[0]
905 .SegmentByteCount =
906 CommandMailbox->Common.DataTransferSize;
907 DAC960_ExecuteCommand(Command);
908 CommandStatus = Command->V2.CommandStatus;
909 DAC960_DeallocateCommand(Command);
910 return (CommandStatus == DAC960_V2_NormalCompletion);
915 DAC960_V2_ControllerInfo executes a DAC960 V2 Firmware Controller
916 Information Reading IOCTL Command and waits for completion. It returns
917 true on success and false on failure.
919 Data is returned in the controller's V2.NewControllerInformation dma-able
920 memory buffer.
923 static bool DAC960_V2_NewControllerInfo(DAC960_Controller_T *Controller)
925 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
926 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
927 DAC960_V2_CommandStatus_T CommandStatus;
928 DAC960_V2_ClearCommand(Command);
929 Command->CommandType = DAC960_ImmediateCommand;
930 CommandMailbox->ControllerInfo.CommandOpcode = DAC960_V2_IOCTL;
931 CommandMailbox->ControllerInfo.CommandControlBits
932 .DataTransferControllerToHost = true;
933 CommandMailbox->ControllerInfo.CommandControlBits
934 .NoAutoRequestSense = true;
935 CommandMailbox->ControllerInfo.DataTransferSize = sizeof(DAC960_V2_ControllerInfo_T);
936 CommandMailbox->ControllerInfo.ControllerNumber = 0;
937 CommandMailbox->ControllerInfo.IOCTL_Opcode = DAC960_V2_GetControllerInfo;
938 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
939 .ScatterGatherSegments[0]
940 .SegmentDataPointer =
941 Controller->V2.NewControllerInformationDMA;
942 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
943 .ScatterGatherSegments[0]
944 .SegmentByteCount =
945 CommandMailbox->ControllerInfo.DataTransferSize;
946 DAC960_ExecuteCommand(Command);
947 CommandStatus = Command->V2.CommandStatus;
948 DAC960_DeallocateCommand(Command);
949 return (CommandStatus == DAC960_V2_NormalCompletion);
954 DAC960_V2_LogicalDeviceInfo executes a DAC960 V2 Firmware Controller Logical
955 Device Information Reading IOCTL Command and waits for completion. It
956 returns true on success and false on failure.
958 Data is returned in the controller's V2.NewLogicalDeviceInformation
961 static bool DAC960_V2_NewLogicalDeviceInfo(DAC960_Controller_T *Controller,
962 unsigned short LogicalDeviceNumber)
964 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
965 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
966 DAC960_V2_CommandStatus_T CommandStatus;
968 DAC960_V2_ClearCommand(Command);
969 Command->CommandType = DAC960_ImmediateCommand;
970 CommandMailbox->LogicalDeviceInfo.CommandOpcode =
971 DAC960_V2_IOCTL;
972 CommandMailbox->LogicalDeviceInfo.CommandControlBits
973 .DataTransferControllerToHost = true;
974 CommandMailbox->LogicalDeviceInfo.CommandControlBits
975 .NoAutoRequestSense = true;
976 CommandMailbox->LogicalDeviceInfo.DataTransferSize =
977 sizeof(DAC960_V2_LogicalDeviceInfo_T);
978 CommandMailbox->LogicalDeviceInfo.LogicalDevice.LogicalDeviceNumber =
979 LogicalDeviceNumber;
980 CommandMailbox->LogicalDeviceInfo.IOCTL_Opcode = DAC960_V2_GetLogicalDeviceInfoValid;
981 CommandMailbox->LogicalDeviceInfo.DataTransferMemoryAddress
982 .ScatterGatherSegments[0]
983 .SegmentDataPointer =
984 Controller->V2.NewLogicalDeviceInformationDMA;
985 CommandMailbox->LogicalDeviceInfo.DataTransferMemoryAddress
986 .ScatterGatherSegments[0]
987 .SegmentByteCount =
988 CommandMailbox->LogicalDeviceInfo.DataTransferSize;
989 DAC960_ExecuteCommand(Command);
990 CommandStatus = Command->V2.CommandStatus;
991 DAC960_DeallocateCommand(Command);
992 return (CommandStatus == DAC960_V2_NormalCompletion);
997 DAC960_V2_PhysicalDeviceInfo executes a DAC960 V2 Firmware Controller "Read
998 Physical Device Information" IOCTL Command and waits for completion. It
999 returns true on success and false on failure.
1001 The Channel, TargetID, LogicalUnit arguments should be 0 the first time
1002 this function is called for a given controller. This will return data
1003 for the "first" device on that controller. The returned data includes a
1004 Channel, TargetID, LogicalUnit that can be passed in to this routine to
1005 get data for the NEXT device on that controller.
1007 Data is stored in the controller's V2.NewPhysicalDeviceInfo dma-able
1008 memory buffer.
1012 static bool DAC960_V2_NewPhysicalDeviceInfo(DAC960_Controller_T *Controller,
1013 unsigned char Channel,
1014 unsigned char TargetID,
1015 unsigned char LogicalUnit)
1017 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
1018 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
1019 DAC960_V2_CommandStatus_T CommandStatus;
1021 DAC960_V2_ClearCommand(Command);
1022 Command->CommandType = DAC960_ImmediateCommand;
1023 CommandMailbox->PhysicalDeviceInfo.CommandOpcode = DAC960_V2_IOCTL;
1024 CommandMailbox->PhysicalDeviceInfo.CommandControlBits
1025 .DataTransferControllerToHost = true;
1026 CommandMailbox->PhysicalDeviceInfo.CommandControlBits
1027 .NoAutoRequestSense = true;
1028 CommandMailbox->PhysicalDeviceInfo.DataTransferSize =
1029 sizeof(DAC960_V2_PhysicalDeviceInfo_T);
1030 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.LogicalUnit = LogicalUnit;
1031 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.TargetID = TargetID;
1032 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.Channel = Channel;
1033 CommandMailbox->PhysicalDeviceInfo.IOCTL_Opcode =
1034 DAC960_V2_GetPhysicalDeviceInfoValid;
1035 CommandMailbox->PhysicalDeviceInfo.DataTransferMemoryAddress
1036 .ScatterGatherSegments[0]
1037 .SegmentDataPointer =
1038 Controller->V2.NewPhysicalDeviceInformationDMA;
1039 CommandMailbox->PhysicalDeviceInfo.DataTransferMemoryAddress
1040 .ScatterGatherSegments[0]
1041 .SegmentByteCount =
1042 CommandMailbox->PhysicalDeviceInfo.DataTransferSize;
1043 DAC960_ExecuteCommand(Command);
1044 CommandStatus = Command->V2.CommandStatus;
1045 DAC960_DeallocateCommand(Command);
1046 return (CommandStatus == DAC960_V2_NormalCompletion);
1050 static void DAC960_V2_ConstructNewUnitSerialNumber(
1051 DAC960_Controller_T *Controller,
1052 DAC960_V2_CommandMailbox_T *CommandMailbox, int Channel, int TargetID,
1053 int LogicalUnit)
1055 CommandMailbox->SCSI_10.CommandOpcode = DAC960_V2_SCSI_10_Passthru;
1056 CommandMailbox->SCSI_10.CommandControlBits
1057 .DataTransferControllerToHost = true;
1058 CommandMailbox->SCSI_10.CommandControlBits
1059 .NoAutoRequestSense = true;
1060 CommandMailbox->SCSI_10.DataTransferSize =
1061 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
1062 CommandMailbox->SCSI_10.PhysicalDevice.LogicalUnit = LogicalUnit;
1063 CommandMailbox->SCSI_10.PhysicalDevice.TargetID = TargetID;
1064 CommandMailbox->SCSI_10.PhysicalDevice.Channel = Channel;
1065 CommandMailbox->SCSI_10.CDBLength = 6;
1066 CommandMailbox->SCSI_10.SCSI_CDB[0] = 0x12; /* INQUIRY */
1067 CommandMailbox->SCSI_10.SCSI_CDB[1] = 1; /* EVPD = 1 */
1068 CommandMailbox->SCSI_10.SCSI_CDB[2] = 0x80; /* Page Code */
1069 CommandMailbox->SCSI_10.SCSI_CDB[3] = 0; /* Reserved */
1070 CommandMailbox->SCSI_10.SCSI_CDB[4] =
1071 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
1072 CommandMailbox->SCSI_10.SCSI_CDB[5] = 0; /* Control */
1073 CommandMailbox->SCSI_10.DataTransferMemoryAddress
1074 .ScatterGatherSegments[0]
1075 .SegmentDataPointer =
1076 Controller->V2.NewInquiryUnitSerialNumberDMA;
1077 CommandMailbox->SCSI_10.DataTransferMemoryAddress
1078 .ScatterGatherSegments[0]
1079 .SegmentByteCount =
1080 CommandMailbox->SCSI_10.DataTransferSize;
1085 DAC960_V2_NewUnitSerialNumber executes an SCSI pass-through
1086 Inquiry command to a SCSI device identified by Channel number,
1087 Target id, Logical Unit Number. This function Waits for completion
1088 of the command.
1090 The return data includes Unit Serial Number information for the
1091 specified device.
1093 Data is stored in the controller's V2.NewPhysicalDeviceInfo dma-able
1094 memory buffer.
1097 static bool DAC960_V2_NewInquiryUnitSerialNumber(DAC960_Controller_T *Controller,
1098 int Channel, int TargetID, int LogicalUnit)
1100 DAC960_Command_T *Command;
1101 DAC960_V2_CommandMailbox_T *CommandMailbox;
1102 DAC960_V2_CommandStatus_T CommandStatus;
1104 Command = DAC960_AllocateCommand(Controller);
1105 CommandMailbox = &Command->V2.CommandMailbox;
1106 DAC960_V2_ClearCommand(Command);
1107 Command->CommandType = DAC960_ImmediateCommand;
1109 DAC960_V2_ConstructNewUnitSerialNumber(Controller, CommandMailbox,
1110 Channel, TargetID, LogicalUnit);
1112 DAC960_ExecuteCommand(Command);
1113 CommandStatus = Command->V2.CommandStatus;
1114 DAC960_DeallocateCommand(Command);
1115 return (CommandStatus == DAC960_V2_NormalCompletion);
1120 DAC960_V2_DeviceOperation executes a DAC960 V2 Firmware Controller Device
1121 Operation IOCTL Command and waits for completion. It returns true on
1122 success and false on failure.
1125 static bool DAC960_V2_DeviceOperation(DAC960_Controller_T *Controller,
1126 DAC960_V2_IOCTL_Opcode_T IOCTL_Opcode,
1127 DAC960_V2_OperationDevice_T
1128 OperationDevice)
1130 DAC960_Command_T *Command = DAC960_AllocateCommand(Controller);
1131 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
1132 DAC960_V2_CommandStatus_T CommandStatus;
1133 DAC960_V2_ClearCommand(Command);
1134 Command->CommandType = DAC960_ImmediateCommand;
1135 CommandMailbox->DeviceOperation.CommandOpcode = DAC960_V2_IOCTL;
1136 CommandMailbox->DeviceOperation.CommandControlBits
1137 .DataTransferControllerToHost = true;
1138 CommandMailbox->DeviceOperation.CommandControlBits
1139 .NoAutoRequestSense = true;
1140 CommandMailbox->DeviceOperation.IOCTL_Opcode = IOCTL_Opcode;
1141 CommandMailbox->DeviceOperation.OperationDevice = OperationDevice;
1142 DAC960_ExecuteCommand(Command);
1143 CommandStatus = Command->V2.CommandStatus;
1144 DAC960_DeallocateCommand(Command);
1145 return (CommandStatus == DAC960_V2_NormalCompletion);
1150 DAC960_V1_EnableMemoryMailboxInterface enables the Memory Mailbox Interface
1151 for DAC960 V1 Firmware Controllers.
1153 PD and P controller types have no memory mailbox, but still need the
1154 other dma mapped memory.
1157 static bool DAC960_V1_EnableMemoryMailboxInterface(DAC960_Controller_T
1158 *Controller)
1160 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
1161 DAC960_HardwareType_T hw_type = Controller->HardwareType;
1162 struct pci_dev *PCI_Device = Controller->PCIDevice;
1163 struct dma_loaf *DmaPages = &Controller->DmaPages;
1164 size_t DmaPagesSize;
1165 size_t CommandMailboxesSize;
1166 size_t StatusMailboxesSize;
1168 DAC960_V1_CommandMailbox_T *CommandMailboxesMemory;
1169 dma_addr_t CommandMailboxesMemoryDMA;
1171 DAC960_V1_StatusMailbox_T *StatusMailboxesMemory;
1172 dma_addr_t StatusMailboxesMemoryDMA;
1174 DAC960_V1_CommandMailbox_T CommandMailbox;
1175 DAC960_V1_CommandStatus_T CommandStatus;
1176 int TimeoutCounter;
1177 int i;
1180 if (pci_set_dma_mask(Controller->PCIDevice, DMA_BIT_MASK(32)))
1181 return DAC960_Failure(Controller, "DMA mask out of range");
1182 Controller->BounceBufferLimit = DMA_BIT_MASK(32);
1184 if ((hw_type == DAC960_PD_Controller) || (hw_type == DAC960_P_Controller)) {
1185 CommandMailboxesSize = 0;
1186 StatusMailboxesSize = 0;
1187 } else {
1188 CommandMailboxesSize = DAC960_V1_CommandMailboxCount * sizeof(DAC960_V1_CommandMailbox_T);
1189 StatusMailboxesSize = DAC960_V1_StatusMailboxCount * sizeof(DAC960_V1_StatusMailbox_T);
1191 DmaPagesSize = CommandMailboxesSize + StatusMailboxesSize +
1192 sizeof(DAC960_V1_DCDB_T) + sizeof(DAC960_V1_Enquiry_T) +
1193 sizeof(DAC960_V1_ErrorTable_T) + sizeof(DAC960_V1_EventLogEntry_T) +
1194 sizeof(DAC960_V1_RebuildProgress_T) +
1195 sizeof(DAC960_V1_LogicalDriveInformationArray_T) +
1196 sizeof(DAC960_V1_BackgroundInitializationStatus_T) +
1197 sizeof(DAC960_V1_DeviceState_T) + sizeof(DAC960_SCSI_Inquiry_T) +
1198 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
1200 if (!init_dma_loaf(PCI_Device, DmaPages, DmaPagesSize))
1201 return false;
1204 if ((hw_type == DAC960_PD_Controller) || (hw_type == DAC960_P_Controller))
1205 goto skip_mailboxes;
1207 CommandMailboxesMemory = slice_dma_loaf(DmaPages,
1208 CommandMailboxesSize, &CommandMailboxesMemoryDMA);
1210 /* These are the base addresses for the command memory mailbox array */
1211 Controller->V1.FirstCommandMailbox = CommandMailboxesMemory;
1212 Controller->V1.FirstCommandMailboxDMA = CommandMailboxesMemoryDMA;
1214 CommandMailboxesMemory += DAC960_V1_CommandMailboxCount - 1;
1215 Controller->V1.LastCommandMailbox = CommandMailboxesMemory;
1216 Controller->V1.NextCommandMailbox = Controller->V1.FirstCommandMailbox;
1217 Controller->V1.PreviousCommandMailbox1 = Controller->V1.LastCommandMailbox;
1218 Controller->V1.PreviousCommandMailbox2 =
1219 Controller->V1.LastCommandMailbox - 1;
1221 /* These are the base addresses for the status memory mailbox array */
1222 StatusMailboxesMemory = slice_dma_loaf(DmaPages,
1223 StatusMailboxesSize, &StatusMailboxesMemoryDMA);
1225 Controller->V1.FirstStatusMailbox = StatusMailboxesMemory;
1226 Controller->V1.FirstStatusMailboxDMA = StatusMailboxesMemoryDMA;
1227 StatusMailboxesMemory += DAC960_V1_StatusMailboxCount - 1;
1228 Controller->V1.LastStatusMailbox = StatusMailboxesMemory;
1229 Controller->V1.NextStatusMailbox = Controller->V1.FirstStatusMailbox;
1231 skip_mailboxes:
1232 Controller->V1.MonitoringDCDB = slice_dma_loaf(DmaPages,
1233 sizeof(DAC960_V1_DCDB_T),
1234 &Controller->V1.MonitoringDCDB_DMA);
1236 Controller->V1.NewEnquiry = slice_dma_loaf(DmaPages,
1237 sizeof(DAC960_V1_Enquiry_T),
1238 &Controller->V1.NewEnquiryDMA);
1240 Controller->V1.NewErrorTable = slice_dma_loaf(DmaPages,
1241 sizeof(DAC960_V1_ErrorTable_T),
1242 &Controller->V1.NewErrorTableDMA);
1244 Controller->V1.EventLogEntry = slice_dma_loaf(DmaPages,
1245 sizeof(DAC960_V1_EventLogEntry_T),
1246 &Controller->V1.EventLogEntryDMA);
1248 Controller->V1.RebuildProgress = slice_dma_loaf(DmaPages,
1249 sizeof(DAC960_V1_RebuildProgress_T),
1250 &Controller->V1.RebuildProgressDMA);
1252 Controller->V1.NewLogicalDriveInformation = slice_dma_loaf(DmaPages,
1253 sizeof(DAC960_V1_LogicalDriveInformationArray_T),
1254 &Controller->V1.NewLogicalDriveInformationDMA);
1256 Controller->V1.BackgroundInitializationStatus = slice_dma_loaf(DmaPages,
1257 sizeof(DAC960_V1_BackgroundInitializationStatus_T),
1258 &Controller->V1.BackgroundInitializationStatusDMA);
1260 Controller->V1.NewDeviceState = slice_dma_loaf(DmaPages,
1261 sizeof(DAC960_V1_DeviceState_T),
1262 &Controller->V1.NewDeviceStateDMA);
1264 Controller->V1.NewInquiryStandardData = slice_dma_loaf(DmaPages,
1265 sizeof(DAC960_SCSI_Inquiry_T),
1266 &Controller->V1.NewInquiryStandardDataDMA);
1268 Controller->V1.NewInquiryUnitSerialNumber = slice_dma_loaf(DmaPages,
1269 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T),
1270 &Controller->V1.NewInquiryUnitSerialNumberDMA);
1272 if ((hw_type == DAC960_PD_Controller) || (hw_type == DAC960_P_Controller))
1273 return true;
1275 /* Enable the Memory Mailbox Interface. */
1276 Controller->V1.DualModeMemoryMailboxInterface = true;
1277 CommandMailbox.TypeX.CommandOpcode = 0x2B;
1278 CommandMailbox.TypeX.CommandIdentifier = 0;
1279 CommandMailbox.TypeX.CommandOpcode2 = 0x14;
1280 CommandMailbox.TypeX.CommandMailboxesBusAddress =
1281 Controller->V1.FirstCommandMailboxDMA;
1282 CommandMailbox.TypeX.StatusMailboxesBusAddress =
1283 Controller->V1.FirstStatusMailboxDMA;
1284 #define TIMEOUT_COUNT 1000000
1286 for (i = 0; i < 2; i++)
1287 switch (Controller->HardwareType)
1289 case DAC960_LA_Controller:
1290 TimeoutCounter = TIMEOUT_COUNT;
1291 while (--TimeoutCounter >= 0)
1293 if (!DAC960_LA_HardwareMailboxFullP(ControllerBaseAddress))
1294 break;
1295 udelay(10);
1297 if (TimeoutCounter < 0) return false;
1298 DAC960_LA_WriteHardwareMailbox(ControllerBaseAddress, &CommandMailbox);
1299 DAC960_LA_HardwareMailboxNewCommand(ControllerBaseAddress);
1300 TimeoutCounter = TIMEOUT_COUNT;
1301 while (--TimeoutCounter >= 0)
1303 if (DAC960_LA_HardwareMailboxStatusAvailableP(
1304 ControllerBaseAddress))
1305 break;
1306 udelay(10);
1308 if (TimeoutCounter < 0) return false;
1309 CommandStatus = DAC960_LA_ReadStatusRegister(ControllerBaseAddress);
1310 DAC960_LA_AcknowledgeHardwareMailboxInterrupt(ControllerBaseAddress);
1311 DAC960_LA_AcknowledgeHardwareMailboxStatus(ControllerBaseAddress);
1312 if (CommandStatus == DAC960_V1_NormalCompletion) return true;
1313 Controller->V1.DualModeMemoryMailboxInterface = false;
1314 CommandMailbox.TypeX.CommandOpcode2 = 0x10;
1315 break;
1316 case DAC960_PG_Controller:
1317 TimeoutCounter = TIMEOUT_COUNT;
1318 while (--TimeoutCounter >= 0)
1320 if (!DAC960_PG_HardwareMailboxFullP(ControllerBaseAddress))
1321 break;
1322 udelay(10);
1324 if (TimeoutCounter < 0) return false;
1325 DAC960_PG_WriteHardwareMailbox(ControllerBaseAddress, &CommandMailbox);
1326 DAC960_PG_HardwareMailboxNewCommand(ControllerBaseAddress);
1328 TimeoutCounter = TIMEOUT_COUNT;
1329 while (--TimeoutCounter >= 0)
1331 if (DAC960_PG_HardwareMailboxStatusAvailableP(
1332 ControllerBaseAddress))
1333 break;
1334 udelay(10);
1336 if (TimeoutCounter < 0) return false;
1337 CommandStatus = DAC960_PG_ReadStatusRegister(ControllerBaseAddress);
1338 DAC960_PG_AcknowledgeHardwareMailboxInterrupt(ControllerBaseAddress);
1339 DAC960_PG_AcknowledgeHardwareMailboxStatus(ControllerBaseAddress);
1340 if (CommandStatus == DAC960_V1_NormalCompletion) return true;
1341 Controller->V1.DualModeMemoryMailboxInterface = false;
1342 CommandMailbox.TypeX.CommandOpcode2 = 0x10;
1343 break;
1344 default:
1345 DAC960_Failure(Controller, "Unknown Controller Type\n");
1346 break;
1348 return false;
1353 DAC960_V2_EnableMemoryMailboxInterface enables the Memory Mailbox Interface
1354 for DAC960 V2 Firmware Controllers.
1356 Aggregate the space needed for the controller's memory mailbox and
1357 the other data structures that will be targets of dma transfers with
1358 the controller. Allocate a dma-mapped region of memory to hold these
1359 structures. Then, save CPU pointers and dma_addr_t values to reference
1360 the structures that are contained in that region.
1363 static bool DAC960_V2_EnableMemoryMailboxInterface(DAC960_Controller_T
1364 *Controller)
1366 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
1367 struct pci_dev *PCI_Device = Controller->PCIDevice;
1368 struct dma_loaf *DmaPages = &Controller->DmaPages;
1369 size_t DmaPagesSize;
1370 size_t CommandMailboxesSize;
1371 size_t StatusMailboxesSize;
1373 DAC960_V2_CommandMailbox_T *CommandMailboxesMemory;
1374 dma_addr_t CommandMailboxesMemoryDMA;
1376 DAC960_V2_StatusMailbox_T *StatusMailboxesMemory;
1377 dma_addr_t StatusMailboxesMemoryDMA;
1379 DAC960_V2_CommandMailbox_T *CommandMailbox;
1380 dma_addr_t CommandMailboxDMA;
1381 DAC960_V2_CommandStatus_T CommandStatus;
1383 if (!pci_set_dma_mask(Controller->PCIDevice, DMA_BIT_MASK(64)))
1384 Controller->BounceBufferLimit = DMA_BIT_MASK(64);
1385 else if (!pci_set_dma_mask(Controller->PCIDevice, DMA_BIT_MASK(32)))
1386 Controller->BounceBufferLimit = DMA_BIT_MASK(32);
1387 else
1388 return DAC960_Failure(Controller, "DMA mask out of range");
1390 /* This is a temporary dma mapping, used only in the scope of this function */
1391 CommandMailbox = pci_alloc_consistent(PCI_Device,
1392 sizeof(DAC960_V2_CommandMailbox_T), &CommandMailboxDMA);
1393 if (CommandMailbox == NULL)
1394 return false;
1396 CommandMailboxesSize = DAC960_V2_CommandMailboxCount * sizeof(DAC960_V2_CommandMailbox_T);
1397 StatusMailboxesSize = DAC960_V2_StatusMailboxCount * sizeof(DAC960_V2_StatusMailbox_T);
1398 DmaPagesSize =
1399 CommandMailboxesSize + StatusMailboxesSize +
1400 sizeof(DAC960_V2_HealthStatusBuffer_T) +
1401 sizeof(DAC960_V2_ControllerInfo_T) +
1402 sizeof(DAC960_V2_LogicalDeviceInfo_T) +
1403 sizeof(DAC960_V2_PhysicalDeviceInfo_T) +
1404 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T) +
1405 sizeof(DAC960_V2_Event_T) +
1406 sizeof(DAC960_V2_PhysicalToLogicalDevice_T);
1408 if (!init_dma_loaf(PCI_Device, DmaPages, DmaPagesSize)) {
1409 pci_free_consistent(PCI_Device, sizeof(DAC960_V2_CommandMailbox_T),
1410 CommandMailbox, CommandMailboxDMA);
1411 return false;
1414 CommandMailboxesMemory = slice_dma_loaf(DmaPages,
1415 CommandMailboxesSize, &CommandMailboxesMemoryDMA);
1417 /* These are the base addresses for the command memory mailbox array */
1418 Controller->V2.FirstCommandMailbox = CommandMailboxesMemory;
1419 Controller->V2.FirstCommandMailboxDMA = CommandMailboxesMemoryDMA;
1421 CommandMailboxesMemory += DAC960_V2_CommandMailboxCount - 1;
1422 Controller->V2.LastCommandMailbox = CommandMailboxesMemory;
1423 Controller->V2.NextCommandMailbox = Controller->V2.FirstCommandMailbox;
1424 Controller->V2.PreviousCommandMailbox1 = Controller->V2.LastCommandMailbox;
1425 Controller->V2.PreviousCommandMailbox2 =
1426 Controller->V2.LastCommandMailbox - 1;
1428 /* These are the base addresses for the status memory mailbox array */
1429 StatusMailboxesMemory = slice_dma_loaf(DmaPages,
1430 StatusMailboxesSize, &StatusMailboxesMemoryDMA);
1432 Controller->V2.FirstStatusMailbox = StatusMailboxesMemory;
1433 Controller->V2.FirstStatusMailboxDMA = StatusMailboxesMemoryDMA;
1434 StatusMailboxesMemory += DAC960_V2_StatusMailboxCount - 1;
1435 Controller->V2.LastStatusMailbox = StatusMailboxesMemory;
1436 Controller->V2.NextStatusMailbox = Controller->V2.FirstStatusMailbox;
1438 Controller->V2.HealthStatusBuffer = slice_dma_loaf(DmaPages,
1439 sizeof(DAC960_V2_HealthStatusBuffer_T),
1440 &Controller->V2.HealthStatusBufferDMA);
1442 Controller->V2.NewControllerInformation = slice_dma_loaf(DmaPages,
1443 sizeof(DAC960_V2_ControllerInfo_T),
1444 &Controller->V2.NewControllerInformationDMA);
1446 Controller->V2.NewLogicalDeviceInformation = slice_dma_loaf(DmaPages,
1447 sizeof(DAC960_V2_LogicalDeviceInfo_T),
1448 &Controller->V2.NewLogicalDeviceInformationDMA);
1450 Controller->V2.NewPhysicalDeviceInformation = slice_dma_loaf(DmaPages,
1451 sizeof(DAC960_V2_PhysicalDeviceInfo_T),
1452 &Controller->V2.NewPhysicalDeviceInformationDMA);
1454 Controller->V2.NewInquiryUnitSerialNumber = slice_dma_loaf(DmaPages,
1455 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T),
1456 &Controller->V2.NewInquiryUnitSerialNumberDMA);
1458 Controller->V2.Event = slice_dma_loaf(DmaPages,
1459 sizeof(DAC960_V2_Event_T),
1460 &Controller->V2.EventDMA);
1462 Controller->V2.PhysicalToLogicalDevice = slice_dma_loaf(DmaPages,
1463 sizeof(DAC960_V2_PhysicalToLogicalDevice_T),
1464 &Controller->V2.PhysicalToLogicalDeviceDMA);
1467 Enable the Memory Mailbox Interface.
1469 I don't know why we can't just use one of the memory mailboxes
1470 we just allocated to do this, instead of using this temporary one.
1471 Try this change later.
1473 memset(CommandMailbox, 0, sizeof(DAC960_V2_CommandMailbox_T));
1474 CommandMailbox->SetMemoryMailbox.CommandIdentifier = 1;
1475 CommandMailbox->SetMemoryMailbox.CommandOpcode = DAC960_V2_IOCTL;
1476 CommandMailbox->SetMemoryMailbox.CommandControlBits.NoAutoRequestSense = true;
1477 CommandMailbox->SetMemoryMailbox.FirstCommandMailboxSizeKB =
1478 (DAC960_V2_CommandMailboxCount * sizeof(DAC960_V2_CommandMailbox_T)) >> 10;
1479 CommandMailbox->SetMemoryMailbox.FirstStatusMailboxSizeKB =
1480 (DAC960_V2_StatusMailboxCount * sizeof(DAC960_V2_StatusMailbox_T)) >> 10;
1481 CommandMailbox->SetMemoryMailbox.SecondCommandMailboxSizeKB = 0;
1482 CommandMailbox->SetMemoryMailbox.SecondStatusMailboxSizeKB = 0;
1483 CommandMailbox->SetMemoryMailbox.RequestSenseSize = 0;
1484 CommandMailbox->SetMemoryMailbox.IOCTL_Opcode = DAC960_V2_SetMemoryMailbox;
1485 CommandMailbox->SetMemoryMailbox.HealthStatusBufferSizeKB = 1;
1486 CommandMailbox->SetMemoryMailbox.HealthStatusBufferBusAddress =
1487 Controller->V2.HealthStatusBufferDMA;
1488 CommandMailbox->SetMemoryMailbox.FirstCommandMailboxBusAddress =
1489 Controller->V2.FirstCommandMailboxDMA;
1490 CommandMailbox->SetMemoryMailbox.FirstStatusMailboxBusAddress =
1491 Controller->V2.FirstStatusMailboxDMA;
1492 switch (Controller->HardwareType)
1494 case DAC960_GEM_Controller:
1495 while (DAC960_GEM_HardwareMailboxFullP(ControllerBaseAddress))
1496 udelay(1);
1497 DAC960_GEM_WriteHardwareMailbox(ControllerBaseAddress, CommandMailboxDMA);
1498 DAC960_GEM_HardwareMailboxNewCommand(ControllerBaseAddress);
1499 while (!DAC960_GEM_HardwareMailboxStatusAvailableP(ControllerBaseAddress))
1500 udelay(1);
1501 CommandStatus = DAC960_GEM_ReadCommandStatus(ControllerBaseAddress);
1502 DAC960_GEM_AcknowledgeHardwareMailboxInterrupt(ControllerBaseAddress);
1503 DAC960_GEM_AcknowledgeHardwareMailboxStatus(ControllerBaseAddress);
1504 break;
1505 case DAC960_BA_Controller:
1506 while (DAC960_BA_HardwareMailboxFullP(ControllerBaseAddress))
1507 udelay(1);
1508 DAC960_BA_WriteHardwareMailbox(ControllerBaseAddress, CommandMailboxDMA);
1509 DAC960_BA_HardwareMailboxNewCommand(ControllerBaseAddress);
1510 while (!DAC960_BA_HardwareMailboxStatusAvailableP(ControllerBaseAddress))
1511 udelay(1);
1512 CommandStatus = DAC960_BA_ReadCommandStatus(ControllerBaseAddress);
1513 DAC960_BA_AcknowledgeHardwareMailboxInterrupt(ControllerBaseAddress);
1514 DAC960_BA_AcknowledgeHardwareMailboxStatus(ControllerBaseAddress);
1515 break;
1516 case DAC960_LP_Controller:
1517 while (DAC960_LP_HardwareMailboxFullP(ControllerBaseAddress))
1518 udelay(1);
1519 DAC960_LP_WriteHardwareMailbox(ControllerBaseAddress, CommandMailboxDMA);
1520 DAC960_LP_HardwareMailboxNewCommand(ControllerBaseAddress);
1521 while (!DAC960_LP_HardwareMailboxStatusAvailableP(ControllerBaseAddress))
1522 udelay(1);
1523 CommandStatus = DAC960_LP_ReadCommandStatus(ControllerBaseAddress);
1524 DAC960_LP_AcknowledgeHardwareMailboxInterrupt(ControllerBaseAddress);
1525 DAC960_LP_AcknowledgeHardwareMailboxStatus(ControllerBaseAddress);
1526 break;
1527 default:
1528 DAC960_Failure(Controller, "Unknown Controller Type\n");
1529 CommandStatus = DAC960_V2_AbormalCompletion;
1530 break;
1532 pci_free_consistent(PCI_Device, sizeof(DAC960_V2_CommandMailbox_T),
1533 CommandMailbox, CommandMailboxDMA);
1534 return (CommandStatus == DAC960_V2_NormalCompletion);
1539 DAC960_V1_ReadControllerConfiguration reads the Configuration Information
1540 from DAC960 V1 Firmware Controllers and initializes the Controller structure.
1543 static bool DAC960_V1_ReadControllerConfiguration(DAC960_Controller_T
1544 *Controller)
1546 DAC960_V1_Enquiry2_T *Enquiry2;
1547 dma_addr_t Enquiry2DMA;
1548 DAC960_V1_Config2_T *Config2;
1549 dma_addr_t Config2DMA;
1550 int LogicalDriveNumber, Channel, TargetID;
1551 struct dma_loaf local_dma;
1553 if (!init_dma_loaf(Controller->PCIDevice, &local_dma,
1554 sizeof(DAC960_V1_Enquiry2_T) + sizeof(DAC960_V1_Config2_T)))
1555 return DAC960_Failure(Controller, "LOGICAL DEVICE ALLOCATION");
1557 Enquiry2 = slice_dma_loaf(&local_dma, sizeof(DAC960_V1_Enquiry2_T), &Enquiry2DMA);
1558 Config2 = slice_dma_loaf(&local_dma, sizeof(DAC960_V1_Config2_T), &Config2DMA);
1560 if (!DAC960_V1_ExecuteType3(Controller, DAC960_V1_Enquiry,
1561 Controller->V1.NewEnquiryDMA)) {
1562 free_dma_loaf(Controller->PCIDevice, &local_dma);
1563 return DAC960_Failure(Controller, "ENQUIRY");
1565 memcpy(&Controller->V1.Enquiry, Controller->V1.NewEnquiry,
1566 sizeof(DAC960_V1_Enquiry_T));
1568 if (!DAC960_V1_ExecuteType3(Controller, DAC960_V1_Enquiry2, Enquiry2DMA)) {
1569 free_dma_loaf(Controller->PCIDevice, &local_dma);
1570 return DAC960_Failure(Controller, "ENQUIRY2");
1573 if (!DAC960_V1_ExecuteType3(Controller, DAC960_V1_ReadConfig2, Config2DMA)) {
1574 free_dma_loaf(Controller->PCIDevice, &local_dma);
1575 return DAC960_Failure(Controller, "READ CONFIG2");
1578 if (!DAC960_V1_ExecuteType3(Controller, DAC960_V1_GetLogicalDriveInformation,
1579 Controller->V1.NewLogicalDriveInformationDMA)) {
1580 free_dma_loaf(Controller->PCIDevice, &local_dma);
1581 return DAC960_Failure(Controller, "GET LOGICAL DRIVE INFORMATION");
1583 memcpy(&Controller->V1.LogicalDriveInformation,
1584 Controller->V1.NewLogicalDriveInformation,
1585 sizeof(DAC960_V1_LogicalDriveInformationArray_T));
1587 for (Channel = 0; Channel < Enquiry2->ActualChannels; Channel++)
1588 for (TargetID = 0; TargetID < Enquiry2->MaxTargets; TargetID++) {
1589 if (!DAC960_V1_ExecuteType3D(Controller, DAC960_V1_GetDeviceState,
1590 Channel, TargetID,
1591 Controller->V1.NewDeviceStateDMA)) {
1592 free_dma_loaf(Controller->PCIDevice, &local_dma);
1593 return DAC960_Failure(Controller, "GET DEVICE STATE");
1595 memcpy(&Controller->V1.DeviceState[Channel][TargetID],
1596 Controller->V1.NewDeviceState, sizeof(DAC960_V1_DeviceState_T));
1599 Initialize the Controller Model Name and Full Model Name fields.
1601 switch (Enquiry2->HardwareID.SubModel)
1603 case DAC960_V1_P_PD_PU:
1604 if (Enquiry2->SCSICapability.BusSpeed == DAC960_V1_Ultra)
1605 strcpy(Controller->ModelName, "DAC960PU");
1606 else strcpy(Controller->ModelName, "DAC960PD");
1607 break;
1608 case DAC960_V1_PL:
1609 strcpy(Controller->ModelName, "DAC960PL");
1610 break;
1611 case DAC960_V1_PG:
1612 strcpy(Controller->ModelName, "DAC960PG");
1613 break;
1614 case DAC960_V1_PJ:
1615 strcpy(Controller->ModelName, "DAC960PJ");
1616 break;
1617 case DAC960_V1_PR:
1618 strcpy(Controller->ModelName, "DAC960PR");
1619 break;
1620 case DAC960_V1_PT:
1621 strcpy(Controller->ModelName, "DAC960PT");
1622 break;
1623 case DAC960_V1_PTL0:
1624 strcpy(Controller->ModelName, "DAC960PTL0");
1625 break;
1626 case DAC960_V1_PRL:
1627 strcpy(Controller->ModelName, "DAC960PRL");
1628 break;
1629 case DAC960_V1_PTL1:
1630 strcpy(Controller->ModelName, "DAC960PTL1");
1631 break;
1632 case DAC960_V1_1164P:
1633 strcpy(Controller->ModelName, "DAC1164P");
1634 break;
1635 default:
1636 free_dma_loaf(Controller->PCIDevice, &local_dma);
1637 return DAC960_Failure(Controller, "MODEL VERIFICATION");
1639 strcpy(Controller->FullModelName, "Mylex ");
1640 strcat(Controller->FullModelName, Controller->ModelName);
1642 Initialize the Controller Firmware Version field and verify that it
1643 is a supported firmware version. The supported firmware versions are:
1645 DAC1164P 5.06 and above
1646 DAC960PTL/PRL/PJ/PG 4.06 and above
1647 DAC960PU/PD/PL 3.51 and above
1648 DAC960PU/PD/PL/P 2.73 and above
1650 #if defined(CONFIG_ALPHA)
1652 DEC Alpha machines were often equipped with DAC960 cards that were
1653 OEMed from Mylex, and had their own custom firmware. Version 2.70,
1654 the last custom FW revision to be released by DEC for these older
1655 controllers, appears to work quite well with this driver.
1657 Cards tested successfully were several versions each of the PD and
1658 PU, called by DEC the KZPSC and KZPAC, respectively, and having
1659 the Manufacturer Numbers (from Mylex), usually on a sticker on the
1660 back of the board, of:
1662 KZPSC: D040347 (1-channel) or D040348 (2-channel) or D040349 (3-channel)
1663 KZPAC: D040395 (1-channel) or D040396 (2-channel) or D040397 (3-channel)
1665 # define FIRMWARE_27X "2.70"
1666 #else
1667 # define FIRMWARE_27X "2.73"
1668 #endif
1670 if (Enquiry2->FirmwareID.MajorVersion == 0)
1672 Enquiry2->FirmwareID.MajorVersion =
1673 Controller->V1.Enquiry.MajorFirmwareVersion;
1674 Enquiry2->FirmwareID.MinorVersion =
1675 Controller->V1.Enquiry.MinorFirmwareVersion;
1676 Enquiry2->FirmwareID.FirmwareType = '0';
1677 Enquiry2->FirmwareID.TurnID = 0;
1679 sprintf(Controller->FirmwareVersion, "%d.%02d-%c-%02d",
1680 Enquiry2->FirmwareID.MajorVersion, Enquiry2->FirmwareID.MinorVersion,
1681 Enquiry2->FirmwareID.FirmwareType, Enquiry2->FirmwareID.TurnID);
1682 if (!((Controller->FirmwareVersion[0] == '5' &&
1683 strcmp(Controller->FirmwareVersion, "5.06") >= 0) ||
1684 (Controller->FirmwareVersion[0] == '4' &&
1685 strcmp(Controller->FirmwareVersion, "4.06") >= 0) ||
1686 (Controller->FirmwareVersion[0] == '3' &&
1687 strcmp(Controller->FirmwareVersion, "3.51") >= 0) ||
1688 (Controller->FirmwareVersion[0] == '2' &&
1689 strcmp(Controller->FirmwareVersion, FIRMWARE_27X) >= 0)))
1691 DAC960_Failure(Controller, "FIRMWARE VERSION VERIFICATION");
1692 DAC960_Error("Firmware Version = '%s'\n", Controller,
1693 Controller->FirmwareVersion);
1694 free_dma_loaf(Controller->PCIDevice, &local_dma);
1695 return false;
1698 Initialize the Controller Channels, Targets, Memory Size, and SAF-TE
1699 Enclosure Management Enabled fields.
1701 Controller->Channels = Enquiry2->ActualChannels;
1702 Controller->Targets = Enquiry2->MaxTargets;
1703 Controller->MemorySize = Enquiry2->MemorySize >> 20;
1704 Controller->V1.SAFTE_EnclosureManagementEnabled =
1705 (Enquiry2->FaultManagementType == DAC960_V1_SAFTE);
1707 Initialize the Controller Queue Depth, Driver Queue Depth, Logical Drive
1708 Count, Maximum Blocks per Command, Controller Scatter/Gather Limit, and
1709 Driver Scatter/Gather Limit. The Driver Queue Depth must be at most one
1710 less than the Controller Queue Depth to allow for an automatic drive
1711 rebuild operation.
1713 Controller->ControllerQueueDepth = Controller->V1.Enquiry.MaxCommands;
1714 Controller->DriverQueueDepth = Controller->ControllerQueueDepth - 1;
1715 if (Controller->DriverQueueDepth > DAC960_MaxDriverQueueDepth)
1716 Controller->DriverQueueDepth = DAC960_MaxDriverQueueDepth;
1717 Controller->LogicalDriveCount =
1718 Controller->V1.Enquiry.NumberOfLogicalDrives;
1719 Controller->MaxBlocksPerCommand = Enquiry2->MaxBlocksPerCommand;
1720 Controller->ControllerScatterGatherLimit = Enquiry2->MaxScatterGatherEntries;
1721 Controller->DriverScatterGatherLimit =
1722 Controller->ControllerScatterGatherLimit;
1723 if (Controller->DriverScatterGatherLimit > DAC960_V1_ScatterGatherLimit)
1724 Controller->DriverScatterGatherLimit = DAC960_V1_ScatterGatherLimit;
1726 Initialize the Stripe Size, Segment Size, and Geometry Translation.
1728 Controller->V1.StripeSize = Config2->BlocksPerStripe * Config2->BlockFactor
1729 >> (10 - DAC960_BlockSizeBits);
1730 Controller->V1.SegmentSize = Config2->BlocksPerCacheLine * Config2->BlockFactor
1731 >> (10 - DAC960_BlockSizeBits);
1732 switch (Config2->DriveGeometry)
1734 case DAC960_V1_Geometry_128_32:
1735 Controller->V1.GeometryTranslationHeads = 128;
1736 Controller->V1.GeometryTranslationSectors = 32;
1737 break;
1738 case DAC960_V1_Geometry_255_63:
1739 Controller->V1.GeometryTranslationHeads = 255;
1740 Controller->V1.GeometryTranslationSectors = 63;
1741 break;
1742 default:
1743 free_dma_loaf(Controller->PCIDevice, &local_dma);
1744 return DAC960_Failure(Controller, "CONFIG2 DRIVE GEOMETRY");
1747 Initialize the Background Initialization Status.
1749 if ((Controller->FirmwareVersion[0] == '4' &&
1750 strcmp(Controller->FirmwareVersion, "4.08") >= 0) ||
1751 (Controller->FirmwareVersion[0] == '5' &&
1752 strcmp(Controller->FirmwareVersion, "5.08") >= 0))
1754 Controller->V1.BackgroundInitializationStatusSupported = true;
1755 DAC960_V1_ExecuteType3B(Controller,
1756 DAC960_V1_BackgroundInitializationControl, 0x20,
1757 Controller->
1758 V1.BackgroundInitializationStatusDMA);
1759 memcpy(&Controller->V1.LastBackgroundInitializationStatus,
1760 Controller->V1.BackgroundInitializationStatus,
1761 sizeof(DAC960_V1_BackgroundInitializationStatus_T));
1764 Initialize the Logical Drive Initially Accessible flag.
1766 for (LogicalDriveNumber = 0;
1767 LogicalDriveNumber < Controller->LogicalDriveCount;
1768 LogicalDriveNumber++)
1769 if (Controller->V1.LogicalDriveInformation
1770 [LogicalDriveNumber].LogicalDriveState !=
1771 DAC960_V1_LogicalDrive_Offline)
1772 Controller->LogicalDriveInitiallyAccessible[LogicalDriveNumber] = true;
1773 Controller->V1.LastRebuildStatus = DAC960_V1_NoRebuildOrCheckInProgress;
1774 free_dma_loaf(Controller->PCIDevice, &local_dma);
1775 return true;
1780 DAC960_V2_ReadControllerConfiguration reads the Configuration Information
1781 from DAC960 V2 Firmware Controllers and initializes the Controller structure.
1784 static bool DAC960_V2_ReadControllerConfiguration(DAC960_Controller_T
1785 *Controller)
1787 DAC960_V2_ControllerInfo_T *ControllerInfo =
1788 &Controller->V2.ControllerInformation;
1789 unsigned short LogicalDeviceNumber = 0;
1790 int ModelNameLength;
1792 /* Get data into dma-able area, then copy into permanant location */
1793 if (!DAC960_V2_NewControllerInfo(Controller))
1794 return DAC960_Failure(Controller, "GET CONTROLLER INFO");
1795 memcpy(ControllerInfo, Controller->V2.NewControllerInformation,
1796 sizeof(DAC960_V2_ControllerInfo_T));
1799 if (!DAC960_V2_GeneralInfo(Controller))
1800 return DAC960_Failure(Controller, "GET HEALTH STATUS");
1803 Initialize the Controller Model Name and Full Model Name fields.
1805 ModelNameLength = sizeof(ControllerInfo->ControllerName);
1806 if (ModelNameLength > sizeof(Controller->ModelName)-1)
1807 ModelNameLength = sizeof(Controller->ModelName)-1;
1808 memcpy(Controller->ModelName, ControllerInfo->ControllerName,
1809 ModelNameLength);
1810 ModelNameLength--;
1811 while (Controller->ModelName[ModelNameLength] == ' ' ||
1812 Controller->ModelName[ModelNameLength] == '\0')
1813 ModelNameLength--;
1814 Controller->ModelName[++ModelNameLength] = '\0';
1815 strcpy(Controller->FullModelName, "Mylex ");
1816 strcat(Controller->FullModelName, Controller->ModelName);
1818 Initialize the Controller Firmware Version field.
1820 sprintf(Controller->FirmwareVersion, "%d.%02d-%02d",
1821 ControllerInfo->FirmwareMajorVersion,
1822 ControllerInfo->FirmwareMinorVersion,
1823 ControllerInfo->FirmwareTurnNumber);
1824 if (ControllerInfo->FirmwareMajorVersion == 6 &&
1825 ControllerInfo->FirmwareMinorVersion == 0 &&
1826 ControllerInfo->FirmwareTurnNumber < 1)
1828 DAC960_Info("FIRMWARE VERSION %s DOES NOT PROVIDE THE CONTROLLER\n",
1829 Controller, Controller->FirmwareVersion);
1830 DAC960_Info("STATUS MONITORING FUNCTIONALITY NEEDED BY THIS DRIVER.\n",
1831 Controller);
1832 DAC960_Info("PLEASE UPGRADE TO VERSION 6.00-01 OR ABOVE.\n",
1833 Controller);
1836 Initialize the Controller Channels, Targets, and Memory Size.
1838 Controller->Channels = ControllerInfo->NumberOfPhysicalChannelsPresent;
1839 Controller->Targets =
1840 ControllerInfo->MaximumTargetsPerChannel
1841 [ControllerInfo->NumberOfPhysicalChannelsPresent-1];
1842 Controller->MemorySize = ControllerInfo->MemorySizeMB;
1844 Initialize the Controller Queue Depth, Driver Queue Depth, Logical Drive
1845 Count, Maximum Blocks per Command, Controller Scatter/Gather Limit, and
1846 Driver Scatter/Gather Limit. The Driver Queue Depth must be at most one
1847 less than the Controller Queue Depth to allow for an automatic drive
1848 rebuild operation.
1850 Controller->ControllerQueueDepth = ControllerInfo->MaximumParallelCommands;
1851 Controller->DriverQueueDepth = Controller->ControllerQueueDepth - 1;
1852 if (Controller->DriverQueueDepth > DAC960_MaxDriverQueueDepth)
1853 Controller->DriverQueueDepth = DAC960_MaxDriverQueueDepth;
1854 Controller->LogicalDriveCount = ControllerInfo->LogicalDevicesPresent;
1855 Controller->MaxBlocksPerCommand =
1856 ControllerInfo->MaximumDataTransferSizeInBlocks;
1857 Controller->ControllerScatterGatherLimit =
1858 ControllerInfo->MaximumScatterGatherEntries;
1859 Controller->DriverScatterGatherLimit =
1860 Controller->ControllerScatterGatherLimit;
1861 if (Controller->DriverScatterGatherLimit > DAC960_V2_ScatterGatherLimit)
1862 Controller->DriverScatterGatherLimit = DAC960_V2_ScatterGatherLimit;
1864 Initialize the Logical Device Information.
1866 while (true)
1868 DAC960_V2_LogicalDeviceInfo_T *NewLogicalDeviceInfo =
1869 Controller->V2.NewLogicalDeviceInformation;
1870 DAC960_V2_LogicalDeviceInfo_T *LogicalDeviceInfo;
1871 DAC960_V2_PhysicalDevice_T PhysicalDevice;
1873 if (!DAC960_V2_NewLogicalDeviceInfo(Controller, LogicalDeviceNumber))
1874 break;
1875 LogicalDeviceNumber = NewLogicalDeviceInfo->LogicalDeviceNumber;
1876 if (LogicalDeviceNumber >= DAC960_MaxLogicalDrives) {
1877 DAC960_Error("DAC960: Logical Drive Number %d not supported\n",
1878 Controller, LogicalDeviceNumber);
1879 break;
1881 if (NewLogicalDeviceInfo->DeviceBlockSizeInBytes != DAC960_BlockSize) {
1882 DAC960_Error("DAC960: Logical Drive Block Size %d not supported\n",
1883 Controller, NewLogicalDeviceInfo->DeviceBlockSizeInBytes);
1884 LogicalDeviceNumber++;
1885 continue;
1887 PhysicalDevice.Controller = 0;
1888 PhysicalDevice.Channel = NewLogicalDeviceInfo->Channel;
1889 PhysicalDevice.TargetID = NewLogicalDeviceInfo->TargetID;
1890 PhysicalDevice.LogicalUnit = NewLogicalDeviceInfo->LogicalUnit;
1891 Controller->V2.LogicalDriveToVirtualDevice[LogicalDeviceNumber] =
1892 PhysicalDevice;
1893 if (NewLogicalDeviceInfo->LogicalDeviceState !=
1894 DAC960_V2_LogicalDevice_Offline)
1895 Controller->LogicalDriveInitiallyAccessible[LogicalDeviceNumber] = true;
1896 LogicalDeviceInfo = kmalloc(sizeof(DAC960_V2_LogicalDeviceInfo_T),
1897 GFP_ATOMIC);
1898 if (LogicalDeviceInfo == NULL)
1899 return DAC960_Failure(Controller, "LOGICAL DEVICE ALLOCATION");
1900 Controller->V2.LogicalDeviceInformation[LogicalDeviceNumber] =
1901 LogicalDeviceInfo;
1902 memcpy(LogicalDeviceInfo, NewLogicalDeviceInfo,
1903 sizeof(DAC960_V2_LogicalDeviceInfo_T));
1904 LogicalDeviceNumber++;
1906 return true;
1911 DAC960_ReportControllerConfiguration reports the Configuration Information
1912 for Controller.
1915 static bool DAC960_ReportControllerConfiguration(DAC960_Controller_T
1916 *Controller)
1918 DAC960_Info("Configuring Mylex %s PCI RAID Controller\n",
1919 Controller, Controller->ModelName);
1920 DAC960_Info(" Firmware Version: %s, Channels: %d, Memory Size: %dMB\n",
1921 Controller, Controller->FirmwareVersion,
1922 Controller->Channels, Controller->MemorySize);
1923 DAC960_Info(" PCI Bus: %d, Device: %d, Function: %d, I/O Address: ",
1924 Controller, Controller->Bus,
1925 Controller->Device, Controller->Function);
1926 if (Controller->IO_Address == 0)
1927 DAC960_Info("Unassigned\n", Controller);
1928 else DAC960_Info("0x%X\n", Controller, Controller->IO_Address);
1929 DAC960_Info(" PCI Address: 0x%X mapped at 0x%lX, IRQ Channel: %d\n",
1930 Controller, Controller->PCI_Address,
1931 (unsigned long) Controller->BaseAddress,
1932 Controller->IRQ_Channel);
1933 DAC960_Info(" Controller Queue Depth: %d, "
1934 "Maximum Blocks per Command: %d\n",
1935 Controller, Controller->ControllerQueueDepth,
1936 Controller->MaxBlocksPerCommand);
1937 DAC960_Info(" Driver Queue Depth: %d, "
1938 "Scatter/Gather Limit: %d of %d Segments\n",
1939 Controller, Controller->DriverQueueDepth,
1940 Controller->DriverScatterGatherLimit,
1941 Controller->ControllerScatterGatherLimit);
1942 if (Controller->FirmwareType == DAC960_V1_Controller)
1944 DAC960_Info(" Stripe Size: %dKB, Segment Size: %dKB, "
1945 "BIOS Geometry: %d/%d\n", Controller,
1946 Controller->V1.StripeSize,
1947 Controller->V1.SegmentSize,
1948 Controller->V1.GeometryTranslationHeads,
1949 Controller->V1.GeometryTranslationSectors);
1950 if (Controller->V1.SAFTE_EnclosureManagementEnabled)
1951 DAC960_Info(" SAF-TE Enclosure Management Enabled\n", Controller);
1953 return true;
1958 DAC960_V1_ReadDeviceConfiguration reads the Device Configuration Information
1959 for DAC960 V1 Firmware Controllers by requesting the SCSI Inquiry and SCSI
1960 Inquiry Unit Serial Number information for each device connected to
1961 Controller.
1964 static bool DAC960_V1_ReadDeviceConfiguration(DAC960_Controller_T
1965 *Controller)
1967 struct dma_loaf local_dma;
1969 dma_addr_t DCDBs_dma[DAC960_V1_MaxChannels];
1970 DAC960_V1_DCDB_T *DCDBs_cpu[DAC960_V1_MaxChannels];
1972 dma_addr_t SCSI_Inquiry_dma[DAC960_V1_MaxChannels];
1973 DAC960_SCSI_Inquiry_T *SCSI_Inquiry_cpu[DAC960_V1_MaxChannels];
1975 dma_addr_t SCSI_NewInquiryUnitSerialNumberDMA[DAC960_V1_MaxChannels];
1976 DAC960_SCSI_Inquiry_UnitSerialNumber_T *SCSI_NewInquiryUnitSerialNumberCPU[DAC960_V1_MaxChannels];
1978 struct completion Completions[DAC960_V1_MaxChannels];
1979 unsigned long flags;
1980 int Channel, TargetID;
1982 if (!init_dma_loaf(Controller->PCIDevice, &local_dma,
1983 DAC960_V1_MaxChannels*(sizeof(DAC960_V1_DCDB_T) +
1984 sizeof(DAC960_SCSI_Inquiry_T) +
1985 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T))))
1986 return DAC960_Failure(Controller,
1987 "DMA ALLOCATION FAILED IN ReadDeviceConfiguration");
1989 for (Channel = 0; Channel < Controller->Channels; Channel++) {
1990 DCDBs_cpu[Channel] = slice_dma_loaf(&local_dma,
1991 sizeof(DAC960_V1_DCDB_T), DCDBs_dma + Channel);
1992 SCSI_Inquiry_cpu[Channel] = slice_dma_loaf(&local_dma,
1993 sizeof(DAC960_SCSI_Inquiry_T),
1994 SCSI_Inquiry_dma + Channel);
1995 SCSI_NewInquiryUnitSerialNumberCPU[Channel] = slice_dma_loaf(&local_dma,
1996 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T),
1997 SCSI_NewInquiryUnitSerialNumberDMA + Channel);
2000 for (TargetID = 0; TargetID < Controller->Targets; TargetID++)
2003 * For each channel, submit a probe for a device on that channel.
2004 * The timeout interval for a device that is present is 10 seconds.
2005 * With this approach, the timeout periods can elapse in parallel
2006 * on each channel.
2008 for (Channel = 0; Channel < Controller->Channels; Channel++)
2010 dma_addr_t NewInquiryStandardDataDMA = SCSI_Inquiry_dma[Channel];
2011 DAC960_V1_DCDB_T *DCDB = DCDBs_cpu[Channel];
2012 dma_addr_t DCDB_dma = DCDBs_dma[Channel];
2013 DAC960_Command_T *Command = Controller->Commands[Channel];
2014 struct completion *Completion = &Completions[Channel];
2016 init_completion(Completion);
2017 DAC960_V1_ClearCommand(Command);
2018 Command->CommandType = DAC960_ImmediateCommand;
2019 Command->Completion = Completion;
2020 Command->V1.CommandMailbox.Type3.CommandOpcode = DAC960_V1_DCDB;
2021 Command->V1.CommandMailbox.Type3.BusAddress = DCDB_dma;
2022 DCDB->Channel = Channel;
2023 DCDB->TargetID = TargetID;
2024 DCDB->Direction = DAC960_V1_DCDB_DataTransferDeviceToSystem;
2025 DCDB->EarlyStatus = false;
2026 DCDB->Timeout = DAC960_V1_DCDB_Timeout_10_seconds;
2027 DCDB->NoAutomaticRequestSense = false;
2028 DCDB->DisconnectPermitted = true;
2029 DCDB->TransferLength = sizeof(DAC960_SCSI_Inquiry_T);
2030 DCDB->BusAddress = NewInquiryStandardDataDMA;
2031 DCDB->CDBLength = 6;
2032 DCDB->TransferLengthHigh4 = 0;
2033 DCDB->SenseLength = sizeof(DCDB->SenseData);
2034 DCDB->CDB[0] = 0x12; /* INQUIRY */
2035 DCDB->CDB[1] = 0; /* EVPD = 0 */
2036 DCDB->CDB[2] = 0; /* Page Code */
2037 DCDB->CDB[3] = 0; /* Reserved */
2038 DCDB->CDB[4] = sizeof(DAC960_SCSI_Inquiry_T);
2039 DCDB->CDB[5] = 0; /* Control */
2041 spin_lock_irqsave(&Controller->queue_lock, flags);
2042 DAC960_QueueCommand(Command);
2043 spin_unlock_irqrestore(&Controller->queue_lock, flags);
2046 * Wait for the problems submitted in the previous loop
2047 * to complete. On the probes that are successful,
2048 * get the serial number of the device that was found.
2050 for (Channel = 0; Channel < Controller->Channels; Channel++)
2052 DAC960_SCSI_Inquiry_T *InquiryStandardData =
2053 &Controller->V1.InquiryStandardData[Channel][TargetID];
2054 DAC960_SCSI_Inquiry_T *NewInquiryStandardData = SCSI_Inquiry_cpu[Channel];
2055 dma_addr_t NewInquiryUnitSerialNumberDMA =
2056 SCSI_NewInquiryUnitSerialNumberDMA[Channel];
2057 DAC960_SCSI_Inquiry_UnitSerialNumber_T *NewInquiryUnitSerialNumber =
2058 SCSI_NewInquiryUnitSerialNumberCPU[Channel];
2059 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
2060 &Controller->V1.InquiryUnitSerialNumber[Channel][TargetID];
2061 DAC960_Command_T *Command = Controller->Commands[Channel];
2062 DAC960_V1_DCDB_T *DCDB = DCDBs_cpu[Channel];
2063 struct completion *Completion = &Completions[Channel];
2065 wait_for_completion(Completion);
2067 if (Command->V1.CommandStatus != DAC960_V1_NormalCompletion) {
2068 memset(InquiryStandardData, 0, sizeof(DAC960_SCSI_Inquiry_T));
2069 InquiryStandardData->PeripheralDeviceType = 0x1F;
2070 continue;
2071 } else
2072 memcpy(InquiryStandardData, NewInquiryStandardData, sizeof(DAC960_SCSI_Inquiry_T));
2074 /* Preserve Channel and TargetID values from the previous loop */
2075 Command->Completion = Completion;
2076 DCDB->TransferLength = sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
2077 DCDB->BusAddress = NewInquiryUnitSerialNumberDMA;
2078 DCDB->SenseLength = sizeof(DCDB->SenseData);
2079 DCDB->CDB[0] = 0x12; /* INQUIRY */
2080 DCDB->CDB[1] = 1; /* EVPD = 1 */
2081 DCDB->CDB[2] = 0x80; /* Page Code */
2082 DCDB->CDB[3] = 0; /* Reserved */
2083 DCDB->CDB[4] = sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
2084 DCDB->CDB[5] = 0; /* Control */
2086 spin_lock_irqsave(&Controller->queue_lock, flags);
2087 DAC960_QueueCommand(Command);
2088 spin_unlock_irqrestore(&Controller->queue_lock, flags);
2089 wait_for_completion(Completion);
2091 if (Command->V1.CommandStatus != DAC960_V1_NormalCompletion) {
2092 memset(InquiryUnitSerialNumber, 0,
2093 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
2094 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
2095 } else
2096 memcpy(InquiryUnitSerialNumber, NewInquiryUnitSerialNumber,
2097 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
2100 free_dma_loaf(Controller->PCIDevice, &local_dma);
2101 return true;
2106 DAC960_V2_ReadDeviceConfiguration reads the Device Configuration Information
2107 for DAC960 V2 Firmware Controllers by requesting the Physical Device
2108 Information and SCSI Inquiry Unit Serial Number information for each
2109 device connected to Controller.
2112 static bool DAC960_V2_ReadDeviceConfiguration(DAC960_Controller_T
2113 *Controller)
2115 unsigned char Channel = 0, TargetID = 0, LogicalUnit = 0;
2116 unsigned short PhysicalDeviceIndex = 0;
2118 while (true)
2120 DAC960_V2_PhysicalDeviceInfo_T *NewPhysicalDeviceInfo =
2121 Controller->V2.NewPhysicalDeviceInformation;
2122 DAC960_V2_PhysicalDeviceInfo_T *PhysicalDeviceInfo;
2123 DAC960_SCSI_Inquiry_UnitSerialNumber_T *NewInquiryUnitSerialNumber =
2124 Controller->V2.NewInquiryUnitSerialNumber;
2125 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber;
2127 if (!DAC960_V2_NewPhysicalDeviceInfo(Controller, Channel, TargetID, LogicalUnit))
2128 break;
2130 PhysicalDeviceInfo = kmalloc(sizeof(DAC960_V2_PhysicalDeviceInfo_T),
2131 GFP_ATOMIC);
2132 if (PhysicalDeviceInfo == NULL)
2133 return DAC960_Failure(Controller, "PHYSICAL DEVICE ALLOCATION");
2134 Controller->V2.PhysicalDeviceInformation[PhysicalDeviceIndex] =
2135 PhysicalDeviceInfo;
2136 memcpy(PhysicalDeviceInfo, NewPhysicalDeviceInfo,
2137 sizeof(DAC960_V2_PhysicalDeviceInfo_T));
2139 InquiryUnitSerialNumber = kmalloc(
2140 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T), GFP_ATOMIC);
2141 if (InquiryUnitSerialNumber == NULL) {
2142 kfree(PhysicalDeviceInfo);
2143 return DAC960_Failure(Controller, "SERIAL NUMBER ALLOCATION");
2145 Controller->V2.InquiryUnitSerialNumber[PhysicalDeviceIndex] =
2146 InquiryUnitSerialNumber;
2148 Channel = NewPhysicalDeviceInfo->Channel;
2149 TargetID = NewPhysicalDeviceInfo->TargetID;
2150 LogicalUnit = NewPhysicalDeviceInfo->LogicalUnit;
2153 Some devices do NOT have Unit Serial Numbers.
2154 This command fails for them. But, we still want to
2155 remember those devices are there. Construct a
2156 UnitSerialNumber structure for the failure case.
2158 if (!DAC960_V2_NewInquiryUnitSerialNumber(Controller, Channel, TargetID, LogicalUnit)) {
2159 memset(InquiryUnitSerialNumber, 0,
2160 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
2161 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
2162 } else
2163 memcpy(InquiryUnitSerialNumber, NewInquiryUnitSerialNumber,
2164 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
2166 PhysicalDeviceIndex++;
2167 LogicalUnit++;
2169 return true;
2174 DAC960_SanitizeInquiryData sanitizes the Vendor, Model, Revision, and
2175 Product Serial Number fields of the Inquiry Standard Data and Inquiry
2176 Unit Serial Number structures.
2179 static void DAC960_SanitizeInquiryData(DAC960_SCSI_Inquiry_T
2180 *InquiryStandardData,
2181 DAC960_SCSI_Inquiry_UnitSerialNumber_T
2182 *InquiryUnitSerialNumber,
2183 unsigned char *Vendor,
2184 unsigned char *Model,
2185 unsigned char *Revision,
2186 unsigned char *SerialNumber)
2188 int SerialNumberLength, i;
2189 if (InquiryStandardData->PeripheralDeviceType == 0x1F) return;
2190 for (i = 0; i < sizeof(InquiryStandardData->VendorIdentification); i++)
2192 unsigned char VendorCharacter =
2193 InquiryStandardData->VendorIdentification[i];
2194 Vendor[i] = (VendorCharacter >= ' ' && VendorCharacter <= '~'
2195 ? VendorCharacter : ' ');
2197 Vendor[sizeof(InquiryStandardData->VendorIdentification)] = '\0';
2198 for (i = 0; i < sizeof(InquiryStandardData->ProductIdentification); i++)
2200 unsigned char ModelCharacter =
2201 InquiryStandardData->ProductIdentification[i];
2202 Model[i] = (ModelCharacter >= ' ' && ModelCharacter <= '~'
2203 ? ModelCharacter : ' ');
2205 Model[sizeof(InquiryStandardData->ProductIdentification)] = '\0';
2206 for (i = 0; i < sizeof(InquiryStandardData->ProductRevisionLevel); i++)
2208 unsigned char RevisionCharacter =
2209 InquiryStandardData->ProductRevisionLevel[i];
2210 Revision[i] = (RevisionCharacter >= ' ' && RevisionCharacter <= '~'
2211 ? RevisionCharacter : ' ');
2213 Revision[sizeof(InquiryStandardData->ProductRevisionLevel)] = '\0';
2214 if (InquiryUnitSerialNumber->PeripheralDeviceType == 0x1F) return;
2215 SerialNumberLength = InquiryUnitSerialNumber->PageLength;
2216 if (SerialNumberLength >
2217 sizeof(InquiryUnitSerialNumber->ProductSerialNumber))
2218 SerialNumberLength = sizeof(InquiryUnitSerialNumber->ProductSerialNumber);
2219 for (i = 0; i < SerialNumberLength; i++)
2221 unsigned char SerialNumberCharacter =
2222 InquiryUnitSerialNumber->ProductSerialNumber[i];
2223 SerialNumber[i] =
2224 (SerialNumberCharacter >= ' ' && SerialNumberCharacter <= '~'
2225 ? SerialNumberCharacter : ' ');
2227 SerialNumber[SerialNumberLength] = '\0';
2232 DAC960_V1_ReportDeviceConfiguration reports the Device Configuration
2233 Information for DAC960 V1 Firmware Controllers.
2236 static bool DAC960_V1_ReportDeviceConfiguration(DAC960_Controller_T
2237 *Controller)
2239 int LogicalDriveNumber, Channel, TargetID;
2240 DAC960_Info(" Physical Devices:\n", Controller);
2241 for (Channel = 0; Channel < Controller->Channels; Channel++)
2242 for (TargetID = 0; TargetID < Controller->Targets; TargetID++)
2244 DAC960_SCSI_Inquiry_T *InquiryStandardData =
2245 &Controller->V1.InquiryStandardData[Channel][TargetID];
2246 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
2247 &Controller->V1.InquiryUnitSerialNumber[Channel][TargetID];
2248 DAC960_V1_DeviceState_T *DeviceState =
2249 &Controller->V1.DeviceState[Channel][TargetID];
2250 DAC960_V1_ErrorTableEntry_T *ErrorEntry =
2251 &Controller->V1.ErrorTable.ErrorTableEntries[Channel][TargetID];
2252 char Vendor[1+sizeof(InquiryStandardData->VendorIdentification)];
2253 char Model[1+sizeof(InquiryStandardData->ProductIdentification)];
2254 char Revision[1+sizeof(InquiryStandardData->ProductRevisionLevel)];
2255 char SerialNumber[1+sizeof(InquiryUnitSerialNumber
2256 ->ProductSerialNumber)];
2257 if (InquiryStandardData->PeripheralDeviceType == 0x1F) continue;
2258 DAC960_SanitizeInquiryData(InquiryStandardData, InquiryUnitSerialNumber,
2259 Vendor, Model, Revision, SerialNumber);
2260 DAC960_Info(" %d:%d%s Vendor: %s Model: %s Revision: %s\n",
2261 Controller, Channel, TargetID, (TargetID < 10 ? " " : ""),
2262 Vendor, Model, Revision);
2263 if (InquiryUnitSerialNumber->PeripheralDeviceType != 0x1F)
2264 DAC960_Info(" Serial Number: %s\n", Controller, SerialNumber);
2265 if (DeviceState->Present &&
2266 DeviceState->DeviceType == DAC960_V1_DiskType)
2268 if (Controller->V1.DeviceResetCount[Channel][TargetID] > 0)
2269 DAC960_Info(" Disk Status: %s, %u blocks, %d resets\n",
2270 Controller,
2271 (DeviceState->DeviceState == DAC960_V1_Device_Dead
2272 ? "Dead"
2273 : DeviceState->DeviceState
2274 == DAC960_V1_Device_WriteOnly
2275 ? "Write-Only"
2276 : DeviceState->DeviceState
2277 == DAC960_V1_Device_Online
2278 ? "Online" : "Standby"),
2279 DeviceState->DiskSize,
2280 Controller->V1.DeviceResetCount[Channel][TargetID]);
2281 else
2282 DAC960_Info(" Disk Status: %s, %u blocks\n", Controller,
2283 (DeviceState->DeviceState == DAC960_V1_Device_Dead
2284 ? "Dead"
2285 : DeviceState->DeviceState
2286 == DAC960_V1_Device_WriteOnly
2287 ? "Write-Only"
2288 : DeviceState->DeviceState
2289 == DAC960_V1_Device_Online
2290 ? "Online" : "Standby"),
2291 DeviceState->DiskSize);
2293 if (ErrorEntry->ParityErrorCount > 0 ||
2294 ErrorEntry->SoftErrorCount > 0 ||
2295 ErrorEntry->HardErrorCount > 0 ||
2296 ErrorEntry->MiscErrorCount > 0)
2297 DAC960_Info(" Errors - Parity: %d, Soft: %d, "
2298 "Hard: %d, Misc: %d\n", Controller,
2299 ErrorEntry->ParityErrorCount,
2300 ErrorEntry->SoftErrorCount,
2301 ErrorEntry->HardErrorCount,
2302 ErrorEntry->MiscErrorCount);
2304 DAC960_Info(" Logical Drives:\n", Controller);
2305 for (LogicalDriveNumber = 0;
2306 LogicalDriveNumber < Controller->LogicalDriveCount;
2307 LogicalDriveNumber++)
2309 DAC960_V1_LogicalDriveInformation_T *LogicalDriveInformation =
2310 &Controller->V1.LogicalDriveInformation[LogicalDriveNumber];
2311 DAC960_Info(" /dev/rd/c%dd%d: RAID-%d, %s, %u blocks, %s\n",
2312 Controller, Controller->ControllerNumber, LogicalDriveNumber,
2313 LogicalDriveInformation->RAIDLevel,
2314 (LogicalDriveInformation->LogicalDriveState
2315 == DAC960_V1_LogicalDrive_Online
2316 ? "Online"
2317 : LogicalDriveInformation->LogicalDriveState
2318 == DAC960_V1_LogicalDrive_Critical
2319 ? "Critical" : "Offline"),
2320 LogicalDriveInformation->LogicalDriveSize,
2321 (LogicalDriveInformation->WriteBack
2322 ? "Write Back" : "Write Thru"));
2324 return true;
2329 DAC960_V2_ReportDeviceConfiguration reports the Device Configuration
2330 Information for DAC960 V2 Firmware Controllers.
2333 static bool DAC960_V2_ReportDeviceConfiguration(DAC960_Controller_T
2334 *Controller)
2336 int PhysicalDeviceIndex, LogicalDriveNumber;
2337 DAC960_Info(" Physical Devices:\n", Controller);
2338 for (PhysicalDeviceIndex = 0;
2339 PhysicalDeviceIndex < DAC960_V2_MaxPhysicalDevices;
2340 PhysicalDeviceIndex++)
2342 DAC960_V2_PhysicalDeviceInfo_T *PhysicalDeviceInfo =
2343 Controller->V2.PhysicalDeviceInformation[PhysicalDeviceIndex];
2344 DAC960_SCSI_Inquiry_T *InquiryStandardData =
2345 (DAC960_SCSI_Inquiry_T *) &PhysicalDeviceInfo->SCSI_InquiryData;
2346 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
2347 Controller->V2.InquiryUnitSerialNumber[PhysicalDeviceIndex];
2348 char Vendor[1+sizeof(InquiryStandardData->VendorIdentification)];
2349 char Model[1+sizeof(InquiryStandardData->ProductIdentification)];
2350 char Revision[1+sizeof(InquiryStandardData->ProductRevisionLevel)];
2351 char SerialNumber[1+sizeof(InquiryUnitSerialNumber->ProductSerialNumber)];
2352 if (PhysicalDeviceInfo == NULL) break;
2353 DAC960_SanitizeInquiryData(InquiryStandardData, InquiryUnitSerialNumber,
2354 Vendor, Model, Revision, SerialNumber);
2355 DAC960_Info(" %d:%d%s Vendor: %s Model: %s Revision: %s\n",
2356 Controller,
2357 PhysicalDeviceInfo->Channel,
2358 PhysicalDeviceInfo->TargetID,
2359 (PhysicalDeviceInfo->TargetID < 10 ? " " : ""),
2360 Vendor, Model, Revision);
2361 if (PhysicalDeviceInfo->NegotiatedSynchronousMegaTransfers == 0)
2362 DAC960_Info(" %sAsynchronous\n", Controller,
2363 (PhysicalDeviceInfo->NegotiatedDataWidthBits == 16
2364 ? "Wide " :""));
2365 else
2366 DAC960_Info(" %sSynchronous at %d MB/sec\n", Controller,
2367 (PhysicalDeviceInfo->NegotiatedDataWidthBits == 16
2368 ? "Wide " :""),
2369 (PhysicalDeviceInfo->NegotiatedSynchronousMegaTransfers
2370 * PhysicalDeviceInfo->NegotiatedDataWidthBits/8));
2371 if (InquiryUnitSerialNumber->PeripheralDeviceType != 0x1F)
2372 DAC960_Info(" Serial Number: %s\n", Controller, SerialNumber);
2373 if (PhysicalDeviceInfo->PhysicalDeviceState ==
2374 DAC960_V2_Device_Unconfigured)
2375 continue;
2376 DAC960_Info(" Disk Status: %s, %u blocks\n", Controller,
2377 (PhysicalDeviceInfo->PhysicalDeviceState
2378 == DAC960_V2_Device_Online
2379 ? "Online"
2380 : PhysicalDeviceInfo->PhysicalDeviceState
2381 == DAC960_V2_Device_Rebuild
2382 ? "Rebuild"
2383 : PhysicalDeviceInfo->PhysicalDeviceState
2384 == DAC960_V2_Device_Missing
2385 ? "Missing"
2386 : PhysicalDeviceInfo->PhysicalDeviceState
2387 == DAC960_V2_Device_Critical
2388 ? "Critical"
2389 : PhysicalDeviceInfo->PhysicalDeviceState
2390 == DAC960_V2_Device_Dead
2391 ? "Dead"
2392 : PhysicalDeviceInfo->PhysicalDeviceState
2393 == DAC960_V2_Device_SuspectedDead
2394 ? "Suspected-Dead"
2395 : PhysicalDeviceInfo->PhysicalDeviceState
2396 == DAC960_V2_Device_CommandedOffline
2397 ? "Commanded-Offline"
2398 : PhysicalDeviceInfo->PhysicalDeviceState
2399 == DAC960_V2_Device_Standby
2400 ? "Standby" : "Unknown"),
2401 PhysicalDeviceInfo->ConfigurableDeviceSize);
2402 if (PhysicalDeviceInfo->ParityErrors == 0 &&
2403 PhysicalDeviceInfo->SoftErrors == 0 &&
2404 PhysicalDeviceInfo->HardErrors == 0 &&
2405 PhysicalDeviceInfo->MiscellaneousErrors == 0 &&
2406 PhysicalDeviceInfo->CommandTimeouts == 0 &&
2407 PhysicalDeviceInfo->Retries == 0 &&
2408 PhysicalDeviceInfo->Aborts == 0 &&
2409 PhysicalDeviceInfo->PredictedFailuresDetected == 0)
2410 continue;
2411 DAC960_Info(" Errors - Parity: %d, Soft: %d, "
2412 "Hard: %d, Misc: %d\n", Controller,
2413 PhysicalDeviceInfo->ParityErrors,
2414 PhysicalDeviceInfo->SoftErrors,
2415 PhysicalDeviceInfo->HardErrors,
2416 PhysicalDeviceInfo->MiscellaneousErrors);
2417 DAC960_Info(" Timeouts: %d, Retries: %d, "
2418 "Aborts: %d, Predicted: %d\n", Controller,
2419 PhysicalDeviceInfo->CommandTimeouts,
2420 PhysicalDeviceInfo->Retries,
2421 PhysicalDeviceInfo->Aborts,
2422 PhysicalDeviceInfo->PredictedFailuresDetected);
2424 DAC960_Info(" Logical Drives:\n", Controller);
2425 for (LogicalDriveNumber = 0;
2426 LogicalDriveNumber < DAC960_MaxLogicalDrives;
2427 LogicalDriveNumber++)
2429 DAC960_V2_LogicalDeviceInfo_T *LogicalDeviceInfo =
2430 Controller->V2.LogicalDeviceInformation[LogicalDriveNumber];
2431 unsigned char *ReadCacheStatus[] = { "Read Cache Disabled",
2432 "Read Cache Enabled",
2433 "Read Ahead Enabled",
2434 "Intelligent Read Ahead Enabled",
2435 "-", "-", "-", "-" };
2436 unsigned char *WriteCacheStatus[] = { "Write Cache Disabled",
2437 "Logical Device Read Only",
2438 "Write Cache Enabled",
2439 "Intelligent Write Cache Enabled",
2440 "-", "-", "-", "-" };
2441 unsigned char *GeometryTranslation;
2442 if (LogicalDeviceInfo == NULL) continue;
2443 switch (LogicalDeviceInfo->DriveGeometry)
2445 case DAC960_V2_Geometry_128_32:
2446 GeometryTranslation = "128/32";
2447 break;
2448 case DAC960_V2_Geometry_255_63:
2449 GeometryTranslation = "255/63";
2450 break;
2451 default:
2452 GeometryTranslation = "Invalid";
2453 DAC960_Error("Illegal Logical Device Geometry %d\n",
2454 Controller, LogicalDeviceInfo->DriveGeometry);
2455 break;
2457 DAC960_Info(" /dev/rd/c%dd%d: RAID-%d, %s, %u blocks\n",
2458 Controller, Controller->ControllerNumber, LogicalDriveNumber,
2459 LogicalDeviceInfo->RAIDLevel,
2460 (LogicalDeviceInfo->LogicalDeviceState
2461 == DAC960_V2_LogicalDevice_Online
2462 ? "Online"
2463 : LogicalDeviceInfo->LogicalDeviceState
2464 == DAC960_V2_LogicalDevice_Critical
2465 ? "Critical" : "Offline"),
2466 LogicalDeviceInfo->ConfigurableDeviceSize);
2467 DAC960_Info(" Logical Device %s, BIOS Geometry: %s\n",
2468 Controller,
2469 (LogicalDeviceInfo->LogicalDeviceControl
2470 .LogicalDeviceInitialized
2471 ? "Initialized" : "Uninitialized"),
2472 GeometryTranslation);
2473 if (LogicalDeviceInfo->StripeSize == 0)
2475 if (LogicalDeviceInfo->CacheLineSize == 0)
2476 DAC960_Info(" Stripe Size: N/A, "
2477 "Segment Size: N/A\n", Controller);
2478 else
2479 DAC960_Info(" Stripe Size: N/A, "
2480 "Segment Size: %dKB\n", Controller,
2481 1 << (LogicalDeviceInfo->CacheLineSize - 2));
2483 else
2485 if (LogicalDeviceInfo->CacheLineSize == 0)
2486 DAC960_Info(" Stripe Size: %dKB, "
2487 "Segment Size: N/A\n", Controller,
2488 1 << (LogicalDeviceInfo->StripeSize - 2));
2489 else
2490 DAC960_Info(" Stripe Size: %dKB, "
2491 "Segment Size: %dKB\n", Controller,
2492 1 << (LogicalDeviceInfo->StripeSize - 2),
2493 1 << (LogicalDeviceInfo->CacheLineSize - 2));
2495 DAC960_Info(" %s, %s\n", Controller,
2496 ReadCacheStatus[
2497 LogicalDeviceInfo->LogicalDeviceControl.ReadCache],
2498 WriteCacheStatus[
2499 LogicalDeviceInfo->LogicalDeviceControl.WriteCache]);
2500 if (LogicalDeviceInfo->SoftErrors > 0 ||
2501 LogicalDeviceInfo->CommandsFailed > 0 ||
2502 LogicalDeviceInfo->DeferredWriteErrors)
2503 DAC960_Info(" Errors - Soft: %d, Failed: %d, "
2504 "Deferred Write: %d\n", Controller,
2505 LogicalDeviceInfo->SoftErrors,
2506 LogicalDeviceInfo->CommandsFailed,
2507 LogicalDeviceInfo->DeferredWriteErrors);
2510 return true;
2514 DAC960_RegisterBlockDevice registers the Block Device structures
2515 associated with Controller.
2518 static bool DAC960_RegisterBlockDevice(DAC960_Controller_T *Controller)
2520 int MajorNumber = DAC960_MAJOR + Controller->ControllerNumber;
2521 int n;
2524 Register the Block Device Major Number for this DAC960 Controller.
2526 if (register_blkdev(MajorNumber, "dac960") < 0)
2527 return false;
2529 for (n = 0; n < DAC960_MaxLogicalDrives; n++) {
2530 struct gendisk *disk = Controller->disks[n];
2531 struct request_queue *RequestQueue;
2533 /* for now, let all request queues share controller's lock */
2534 RequestQueue = blk_init_queue(DAC960_RequestFunction,&Controller->queue_lock);
2535 if (!RequestQueue) {
2536 printk("DAC960: failure to allocate request queue\n");
2537 continue;
2539 Controller->RequestQueue[n] = RequestQueue;
2540 blk_queue_bounce_limit(RequestQueue, Controller->BounceBufferLimit);
2541 RequestQueue->queuedata = Controller;
2542 blk_queue_max_segments(RequestQueue, Controller->DriverScatterGatherLimit);
2543 blk_queue_max_hw_sectors(RequestQueue, Controller->MaxBlocksPerCommand);
2544 disk->queue = RequestQueue;
2545 sprintf(disk->disk_name, "rd/c%dd%d", Controller->ControllerNumber, n);
2546 disk->major = MajorNumber;
2547 disk->first_minor = n << DAC960_MaxPartitionsBits;
2548 disk->fops = &DAC960_BlockDeviceOperations;
2551 Indicate the Block Device Registration completed successfully,
2553 return true;
2558 DAC960_UnregisterBlockDevice unregisters the Block Device structures
2559 associated with Controller.
2562 static void DAC960_UnregisterBlockDevice(DAC960_Controller_T *Controller)
2564 int MajorNumber = DAC960_MAJOR + Controller->ControllerNumber;
2565 int disk;
2567 /* does order matter when deleting gendisk and cleanup in request queue? */
2568 for (disk = 0; disk < DAC960_MaxLogicalDrives; disk++) {
2569 del_gendisk(Controller->disks[disk]);
2570 blk_cleanup_queue(Controller->RequestQueue[disk]);
2571 Controller->RequestQueue[disk] = NULL;
2575 Unregister the Block Device Major Number for this DAC960 Controller.
2577 unregister_blkdev(MajorNumber, "dac960");
2581 DAC960_ComputeGenericDiskInfo computes the values for the Generic Disk
2582 Information Partition Sector Counts and Block Sizes.
2585 static void DAC960_ComputeGenericDiskInfo(DAC960_Controller_T *Controller)
2587 int disk;
2588 for (disk = 0; disk < DAC960_MaxLogicalDrives; disk++)
2589 set_capacity(Controller->disks[disk], disk_size(Controller, disk));
2593 DAC960_ReportErrorStatus reports Controller BIOS Messages passed through
2594 the Error Status Register when the driver performs the BIOS handshaking.
2595 It returns true for fatal errors and false otherwise.
2598 static bool DAC960_ReportErrorStatus(DAC960_Controller_T *Controller,
2599 unsigned char ErrorStatus,
2600 unsigned char Parameter0,
2601 unsigned char Parameter1)
2603 switch (ErrorStatus)
2605 case 0x00:
2606 DAC960_Notice("Physical Device %d:%d Not Responding\n",
2607 Controller, Parameter1, Parameter0);
2608 break;
2609 case 0x08:
2610 if (Controller->DriveSpinUpMessageDisplayed) break;
2611 DAC960_Notice("Spinning Up Drives\n", Controller);
2612 Controller->DriveSpinUpMessageDisplayed = true;
2613 break;
2614 case 0x30:
2615 DAC960_Notice("Configuration Checksum Error\n", Controller);
2616 break;
2617 case 0x60:
2618 DAC960_Notice("Mirror Race Recovery Failed\n", Controller);
2619 break;
2620 case 0x70:
2621 DAC960_Notice("Mirror Race Recovery In Progress\n", Controller);
2622 break;
2623 case 0x90:
2624 DAC960_Notice("Physical Device %d:%d COD Mismatch\n",
2625 Controller, Parameter1, Parameter0);
2626 break;
2627 case 0xA0:
2628 DAC960_Notice("Logical Drive Installation Aborted\n", Controller);
2629 break;
2630 case 0xB0:
2631 DAC960_Notice("Mirror Race On A Critical Logical Drive\n", Controller);
2632 break;
2633 case 0xD0:
2634 DAC960_Notice("New Controller Configuration Found\n", Controller);
2635 break;
2636 case 0xF0:
2637 DAC960_Error("Fatal Memory Parity Error for Controller at\n", Controller);
2638 return true;
2639 default:
2640 DAC960_Error("Unknown Initialization Error %02X for Controller at\n",
2641 Controller, ErrorStatus);
2642 return true;
2644 return false;
2649 * DAC960_DetectCleanup releases the resources that were allocated
2650 * during DAC960_DetectController(). DAC960_DetectController can
2651 * has several internal failure points, so not ALL resources may
2652 * have been allocated. It's important to free only
2653 * resources that HAVE been allocated. The code below always
2654 * tests that the resource has been allocated before attempting to
2655 * free it.
2657 static void DAC960_DetectCleanup(DAC960_Controller_T *Controller)
2659 int i;
2661 /* Free the memory mailbox, status, and related structures */
2662 free_dma_loaf(Controller->PCIDevice, &Controller->DmaPages);
2663 if (Controller->MemoryMappedAddress) {
2664 switch(Controller->HardwareType)
2666 case DAC960_GEM_Controller:
2667 DAC960_GEM_DisableInterrupts(Controller->BaseAddress);
2668 break;
2669 case DAC960_BA_Controller:
2670 DAC960_BA_DisableInterrupts(Controller->BaseAddress);
2671 break;
2672 case DAC960_LP_Controller:
2673 DAC960_LP_DisableInterrupts(Controller->BaseAddress);
2674 break;
2675 case DAC960_LA_Controller:
2676 DAC960_LA_DisableInterrupts(Controller->BaseAddress);
2677 break;
2678 case DAC960_PG_Controller:
2679 DAC960_PG_DisableInterrupts(Controller->BaseAddress);
2680 break;
2681 case DAC960_PD_Controller:
2682 DAC960_PD_DisableInterrupts(Controller->BaseAddress);
2683 break;
2684 case DAC960_P_Controller:
2685 DAC960_PD_DisableInterrupts(Controller->BaseAddress);
2686 break;
2688 iounmap(Controller->MemoryMappedAddress);
2690 if (Controller->IRQ_Channel)
2691 free_irq(Controller->IRQ_Channel, Controller);
2692 if (Controller->IO_Address)
2693 release_region(Controller->IO_Address, 0x80);
2694 pci_disable_device(Controller->PCIDevice);
2695 for (i = 0; (i < DAC960_MaxLogicalDrives) && Controller->disks[i]; i++)
2696 put_disk(Controller->disks[i]);
2697 DAC960_Controllers[Controller->ControllerNumber] = NULL;
2698 kfree(Controller);
2703 DAC960_DetectController detects Mylex DAC960/AcceleRAID/eXtremeRAID
2704 PCI RAID Controllers by interrogating the PCI Configuration Space for
2705 Controller Type.
2708 static DAC960_Controller_T *
2709 DAC960_DetectController(struct pci_dev *PCI_Device,
2710 const struct pci_device_id *entry)
2712 struct DAC960_privdata *privdata =
2713 (struct DAC960_privdata *)entry->driver_data;
2714 irq_handler_t InterruptHandler = privdata->InterruptHandler;
2715 unsigned int MemoryWindowSize = privdata->MemoryWindowSize;
2716 DAC960_Controller_T *Controller = NULL;
2717 unsigned char DeviceFunction = PCI_Device->devfn;
2718 unsigned char ErrorStatus, Parameter0, Parameter1;
2719 unsigned int IRQ_Channel;
2720 void __iomem *BaseAddress;
2721 int i;
2723 Controller = kzalloc(sizeof(DAC960_Controller_T), GFP_ATOMIC);
2724 if (Controller == NULL) {
2725 DAC960_Error("Unable to allocate Controller structure for "
2726 "Controller at\n", NULL);
2727 return NULL;
2729 Controller->ControllerNumber = DAC960_ControllerCount;
2730 DAC960_Controllers[DAC960_ControllerCount++] = Controller;
2731 Controller->Bus = PCI_Device->bus->number;
2732 Controller->FirmwareType = privdata->FirmwareType;
2733 Controller->HardwareType = privdata->HardwareType;
2734 Controller->Device = DeviceFunction >> 3;
2735 Controller->Function = DeviceFunction & 0x7;
2736 Controller->PCIDevice = PCI_Device;
2737 strcpy(Controller->FullModelName, "DAC960");
2739 if (pci_enable_device(PCI_Device))
2740 goto Failure;
2742 switch (Controller->HardwareType)
2744 case DAC960_GEM_Controller:
2745 Controller->PCI_Address = pci_resource_start(PCI_Device, 0);
2746 break;
2747 case DAC960_BA_Controller:
2748 Controller->PCI_Address = pci_resource_start(PCI_Device, 0);
2749 break;
2750 case DAC960_LP_Controller:
2751 Controller->PCI_Address = pci_resource_start(PCI_Device, 0);
2752 break;
2753 case DAC960_LA_Controller:
2754 Controller->PCI_Address = pci_resource_start(PCI_Device, 0);
2755 break;
2756 case DAC960_PG_Controller:
2757 Controller->PCI_Address = pci_resource_start(PCI_Device, 0);
2758 break;
2759 case DAC960_PD_Controller:
2760 Controller->IO_Address = pci_resource_start(PCI_Device, 0);
2761 Controller->PCI_Address = pci_resource_start(PCI_Device, 1);
2762 break;
2763 case DAC960_P_Controller:
2764 Controller->IO_Address = pci_resource_start(PCI_Device, 0);
2765 Controller->PCI_Address = pci_resource_start(PCI_Device, 1);
2766 break;
2769 pci_set_drvdata(PCI_Device, (void *)((long)Controller->ControllerNumber));
2770 for (i = 0; i < DAC960_MaxLogicalDrives; i++) {
2771 Controller->disks[i] = alloc_disk(1<<DAC960_MaxPartitionsBits);
2772 if (!Controller->disks[i])
2773 goto Failure;
2774 Controller->disks[i]->private_data = (void *)((long)i);
2776 init_waitqueue_head(&Controller->CommandWaitQueue);
2777 init_waitqueue_head(&Controller->HealthStatusWaitQueue);
2778 spin_lock_init(&Controller->queue_lock);
2779 DAC960_AnnounceDriver(Controller);
2781 Map the Controller Register Window.
2783 if (MemoryWindowSize < PAGE_SIZE)
2784 MemoryWindowSize = PAGE_SIZE;
2785 Controller->MemoryMappedAddress =
2786 ioremap_nocache(Controller->PCI_Address & PAGE_MASK, MemoryWindowSize);
2787 Controller->BaseAddress =
2788 Controller->MemoryMappedAddress + (Controller->PCI_Address & ~PAGE_MASK);
2789 if (Controller->MemoryMappedAddress == NULL)
2791 DAC960_Error("Unable to map Controller Register Window for "
2792 "Controller at\n", Controller);
2793 goto Failure;
2795 BaseAddress = Controller->BaseAddress;
2796 switch (Controller->HardwareType)
2798 case DAC960_GEM_Controller:
2799 DAC960_GEM_DisableInterrupts(BaseAddress);
2800 DAC960_GEM_AcknowledgeHardwareMailboxStatus(BaseAddress);
2801 udelay(1000);
2802 while (DAC960_GEM_InitializationInProgressP(BaseAddress))
2804 if (DAC960_GEM_ReadErrorStatus(BaseAddress, &ErrorStatus,
2805 &Parameter0, &Parameter1) &&
2806 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2807 Parameter0, Parameter1))
2808 goto Failure;
2809 udelay(10);
2811 if (!DAC960_V2_EnableMemoryMailboxInterface(Controller))
2813 DAC960_Error("Unable to Enable Memory Mailbox Interface "
2814 "for Controller at\n", Controller);
2815 goto Failure;
2817 DAC960_GEM_EnableInterrupts(BaseAddress);
2818 Controller->QueueCommand = DAC960_GEM_QueueCommand;
2819 Controller->ReadControllerConfiguration =
2820 DAC960_V2_ReadControllerConfiguration;
2821 Controller->ReadDeviceConfiguration =
2822 DAC960_V2_ReadDeviceConfiguration;
2823 Controller->ReportDeviceConfiguration =
2824 DAC960_V2_ReportDeviceConfiguration;
2825 Controller->QueueReadWriteCommand =
2826 DAC960_V2_QueueReadWriteCommand;
2827 break;
2828 case DAC960_BA_Controller:
2829 DAC960_BA_DisableInterrupts(BaseAddress);
2830 DAC960_BA_AcknowledgeHardwareMailboxStatus(BaseAddress);
2831 udelay(1000);
2832 while (DAC960_BA_InitializationInProgressP(BaseAddress))
2834 if (DAC960_BA_ReadErrorStatus(BaseAddress, &ErrorStatus,
2835 &Parameter0, &Parameter1) &&
2836 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2837 Parameter0, Parameter1))
2838 goto Failure;
2839 udelay(10);
2841 if (!DAC960_V2_EnableMemoryMailboxInterface(Controller))
2843 DAC960_Error("Unable to Enable Memory Mailbox Interface "
2844 "for Controller at\n", Controller);
2845 goto Failure;
2847 DAC960_BA_EnableInterrupts(BaseAddress);
2848 Controller->QueueCommand = DAC960_BA_QueueCommand;
2849 Controller->ReadControllerConfiguration =
2850 DAC960_V2_ReadControllerConfiguration;
2851 Controller->ReadDeviceConfiguration =
2852 DAC960_V2_ReadDeviceConfiguration;
2853 Controller->ReportDeviceConfiguration =
2854 DAC960_V2_ReportDeviceConfiguration;
2855 Controller->QueueReadWriteCommand =
2856 DAC960_V2_QueueReadWriteCommand;
2857 break;
2858 case DAC960_LP_Controller:
2859 DAC960_LP_DisableInterrupts(BaseAddress);
2860 DAC960_LP_AcknowledgeHardwareMailboxStatus(BaseAddress);
2861 udelay(1000);
2862 while (DAC960_LP_InitializationInProgressP(BaseAddress))
2864 if (DAC960_LP_ReadErrorStatus(BaseAddress, &ErrorStatus,
2865 &Parameter0, &Parameter1) &&
2866 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2867 Parameter0, Parameter1))
2868 goto Failure;
2869 udelay(10);
2871 if (!DAC960_V2_EnableMemoryMailboxInterface(Controller))
2873 DAC960_Error("Unable to Enable Memory Mailbox Interface "
2874 "for Controller at\n", Controller);
2875 goto Failure;
2877 DAC960_LP_EnableInterrupts(BaseAddress);
2878 Controller->QueueCommand = DAC960_LP_QueueCommand;
2879 Controller->ReadControllerConfiguration =
2880 DAC960_V2_ReadControllerConfiguration;
2881 Controller->ReadDeviceConfiguration =
2882 DAC960_V2_ReadDeviceConfiguration;
2883 Controller->ReportDeviceConfiguration =
2884 DAC960_V2_ReportDeviceConfiguration;
2885 Controller->QueueReadWriteCommand =
2886 DAC960_V2_QueueReadWriteCommand;
2887 break;
2888 case DAC960_LA_Controller:
2889 DAC960_LA_DisableInterrupts(BaseAddress);
2890 DAC960_LA_AcknowledgeHardwareMailboxStatus(BaseAddress);
2891 udelay(1000);
2892 while (DAC960_LA_InitializationInProgressP(BaseAddress))
2894 if (DAC960_LA_ReadErrorStatus(BaseAddress, &ErrorStatus,
2895 &Parameter0, &Parameter1) &&
2896 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2897 Parameter0, Parameter1))
2898 goto Failure;
2899 udelay(10);
2901 if (!DAC960_V1_EnableMemoryMailboxInterface(Controller))
2903 DAC960_Error("Unable to Enable Memory Mailbox Interface "
2904 "for Controller at\n", Controller);
2905 goto Failure;
2907 DAC960_LA_EnableInterrupts(BaseAddress);
2908 if (Controller->V1.DualModeMemoryMailboxInterface)
2909 Controller->QueueCommand = DAC960_LA_QueueCommandDualMode;
2910 else Controller->QueueCommand = DAC960_LA_QueueCommandSingleMode;
2911 Controller->ReadControllerConfiguration =
2912 DAC960_V1_ReadControllerConfiguration;
2913 Controller->ReadDeviceConfiguration =
2914 DAC960_V1_ReadDeviceConfiguration;
2915 Controller->ReportDeviceConfiguration =
2916 DAC960_V1_ReportDeviceConfiguration;
2917 Controller->QueueReadWriteCommand =
2918 DAC960_V1_QueueReadWriteCommand;
2919 break;
2920 case DAC960_PG_Controller:
2921 DAC960_PG_DisableInterrupts(BaseAddress);
2922 DAC960_PG_AcknowledgeHardwareMailboxStatus(BaseAddress);
2923 udelay(1000);
2924 while (DAC960_PG_InitializationInProgressP(BaseAddress))
2926 if (DAC960_PG_ReadErrorStatus(BaseAddress, &ErrorStatus,
2927 &Parameter0, &Parameter1) &&
2928 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2929 Parameter0, Parameter1))
2930 goto Failure;
2931 udelay(10);
2933 if (!DAC960_V1_EnableMemoryMailboxInterface(Controller))
2935 DAC960_Error("Unable to Enable Memory Mailbox Interface "
2936 "for Controller at\n", Controller);
2937 goto Failure;
2939 DAC960_PG_EnableInterrupts(BaseAddress);
2940 if (Controller->V1.DualModeMemoryMailboxInterface)
2941 Controller->QueueCommand = DAC960_PG_QueueCommandDualMode;
2942 else Controller->QueueCommand = DAC960_PG_QueueCommandSingleMode;
2943 Controller->ReadControllerConfiguration =
2944 DAC960_V1_ReadControllerConfiguration;
2945 Controller->ReadDeviceConfiguration =
2946 DAC960_V1_ReadDeviceConfiguration;
2947 Controller->ReportDeviceConfiguration =
2948 DAC960_V1_ReportDeviceConfiguration;
2949 Controller->QueueReadWriteCommand =
2950 DAC960_V1_QueueReadWriteCommand;
2951 break;
2952 case DAC960_PD_Controller:
2953 if (!request_region(Controller->IO_Address, 0x80,
2954 Controller->FullModelName)) {
2955 DAC960_Error("IO port 0x%d busy for Controller at\n",
2956 Controller, Controller->IO_Address);
2957 goto Failure;
2959 DAC960_PD_DisableInterrupts(BaseAddress);
2960 DAC960_PD_AcknowledgeStatus(BaseAddress);
2961 udelay(1000);
2962 while (DAC960_PD_InitializationInProgressP(BaseAddress))
2964 if (DAC960_PD_ReadErrorStatus(BaseAddress, &ErrorStatus,
2965 &Parameter0, &Parameter1) &&
2966 DAC960_ReportErrorStatus(Controller, ErrorStatus,
2967 Parameter0, Parameter1))
2968 goto Failure;
2969 udelay(10);
2971 if (!DAC960_V1_EnableMemoryMailboxInterface(Controller))
2973 DAC960_Error("Unable to allocate DMA mapped memory "
2974 "for Controller at\n", Controller);
2975 goto Failure;
2977 DAC960_PD_EnableInterrupts(BaseAddress);
2978 Controller->QueueCommand = DAC960_PD_QueueCommand;
2979 Controller->ReadControllerConfiguration =
2980 DAC960_V1_ReadControllerConfiguration;
2981 Controller->ReadDeviceConfiguration =
2982 DAC960_V1_ReadDeviceConfiguration;
2983 Controller->ReportDeviceConfiguration =
2984 DAC960_V1_ReportDeviceConfiguration;
2985 Controller->QueueReadWriteCommand =
2986 DAC960_V1_QueueReadWriteCommand;
2987 break;
2988 case DAC960_P_Controller:
2989 if (!request_region(Controller->IO_Address, 0x80,
2990 Controller->FullModelName)){
2991 DAC960_Error("IO port 0x%d busy for Controller at\n",
2992 Controller, Controller->IO_Address);
2993 goto Failure;
2995 DAC960_PD_DisableInterrupts(BaseAddress);
2996 DAC960_PD_AcknowledgeStatus(BaseAddress);
2997 udelay(1000);
2998 while (DAC960_PD_InitializationInProgressP(BaseAddress))
3000 if (DAC960_PD_ReadErrorStatus(BaseAddress, &ErrorStatus,
3001 &Parameter0, &Parameter1) &&
3002 DAC960_ReportErrorStatus(Controller, ErrorStatus,
3003 Parameter0, Parameter1))
3004 goto Failure;
3005 udelay(10);
3007 if (!DAC960_V1_EnableMemoryMailboxInterface(Controller))
3009 DAC960_Error("Unable to allocate DMA mapped memory"
3010 "for Controller at\n", Controller);
3011 goto Failure;
3013 DAC960_PD_EnableInterrupts(BaseAddress);
3014 Controller->QueueCommand = DAC960_P_QueueCommand;
3015 Controller->ReadControllerConfiguration =
3016 DAC960_V1_ReadControllerConfiguration;
3017 Controller->ReadDeviceConfiguration =
3018 DAC960_V1_ReadDeviceConfiguration;
3019 Controller->ReportDeviceConfiguration =
3020 DAC960_V1_ReportDeviceConfiguration;
3021 Controller->QueueReadWriteCommand =
3022 DAC960_V1_QueueReadWriteCommand;
3023 break;
3026 Acquire shared access to the IRQ Channel.
3028 IRQ_Channel = PCI_Device->irq;
3029 if (request_irq(IRQ_Channel, InterruptHandler, IRQF_SHARED,
3030 Controller->FullModelName, Controller) < 0)
3032 DAC960_Error("Unable to acquire IRQ Channel %d for Controller at\n",
3033 Controller, Controller->IRQ_Channel);
3034 goto Failure;
3036 Controller->IRQ_Channel = IRQ_Channel;
3037 Controller->InitialCommand.CommandIdentifier = 1;
3038 Controller->InitialCommand.Controller = Controller;
3039 Controller->Commands[0] = &Controller->InitialCommand;
3040 Controller->FreeCommands = &Controller->InitialCommand;
3041 return Controller;
3043 Failure:
3044 if (Controller->IO_Address == 0)
3045 DAC960_Error("PCI Bus %d Device %d Function %d I/O Address N/A "
3046 "PCI Address 0x%X\n", Controller,
3047 Controller->Bus, Controller->Device,
3048 Controller->Function, Controller->PCI_Address);
3049 else
3050 DAC960_Error("PCI Bus %d Device %d Function %d I/O Address "
3051 "0x%X PCI Address 0x%X\n", Controller,
3052 Controller->Bus, Controller->Device,
3053 Controller->Function, Controller->IO_Address,
3054 Controller->PCI_Address);
3055 DAC960_DetectCleanup(Controller);
3056 DAC960_ControllerCount--;
3057 return NULL;
3061 DAC960_InitializeController initializes Controller.
3064 static bool
3065 DAC960_InitializeController(DAC960_Controller_T *Controller)
3067 if (DAC960_ReadControllerConfiguration(Controller) &&
3068 DAC960_ReportControllerConfiguration(Controller) &&
3069 DAC960_CreateAuxiliaryStructures(Controller) &&
3070 DAC960_ReadDeviceConfiguration(Controller) &&
3071 DAC960_ReportDeviceConfiguration(Controller) &&
3072 DAC960_RegisterBlockDevice(Controller))
3075 Initialize the Monitoring Timer.
3077 init_timer(&Controller->MonitoringTimer);
3078 Controller->MonitoringTimer.expires =
3079 jiffies + DAC960_MonitoringTimerInterval;
3080 Controller->MonitoringTimer.data = (unsigned long) Controller;
3081 Controller->MonitoringTimer.function = DAC960_MonitoringTimerFunction;
3082 add_timer(&Controller->MonitoringTimer);
3083 Controller->ControllerInitialized = true;
3084 return true;
3086 return false;
3091 DAC960_FinalizeController finalizes Controller.
3094 static void DAC960_FinalizeController(DAC960_Controller_T *Controller)
3096 if (Controller->ControllerInitialized)
3098 unsigned long flags;
3101 * Acquiring and releasing lock here eliminates
3102 * a very low probability race.
3104 * The code below allocates controller command structures
3105 * from the free list without holding the controller lock.
3106 * This is safe assuming there is no other activity on
3107 * the controller at the time.
3109 * But, there might be a monitoring command still
3110 * in progress. Setting the Shutdown flag while holding
3111 * the lock ensures that there is no monitoring command
3112 * in the interrupt handler currently, and any monitoring
3113 * commands that complete from this time on will NOT return
3114 * their command structure to the free list.
3117 spin_lock_irqsave(&Controller->queue_lock, flags);
3118 Controller->ShutdownMonitoringTimer = 1;
3119 spin_unlock_irqrestore(&Controller->queue_lock, flags);
3121 del_timer_sync(&Controller->MonitoringTimer);
3122 if (Controller->FirmwareType == DAC960_V1_Controller)
3124 DAC960_Notice("Flushing Cache...", Controller);
3125 DAC960_V1_ExecuteType3(Controller, DAC960_V1_Flush, 0);
3126 DAC960_Notice("done\n", Controller);
3128 if (Controller->HardwareType == DAC960_PD_Controller)
3129 release_region(Controller->IO_Address, 0x80);
3131 else
3133 DAC960_Notice("Flushing Cache...", Controller);
3134 DAC960_V2_DeviceOperation(Controller, DAC960_V2_PauseDevice,
3135 DAC960_V2_RAID_Controller);
3136 DAC960_Notice("done\n", Controller);
3139 DAC960_UnregisterBlockDevice(Controller);
3140 DAC960_DestroyAuxiliaryStructures(Controller);
3141 DAC960_DestroyProcEntries(Controller);
3142 DAC960_DetectCleanup(Controller);
3147 DAC960_Probe verifies controller's existence and
3148 initializes the DAC960 Driver for that controller.
3151 static int
3152 DAC960_Probe(struct pci_dev *dev, const struct pci_device_id *entry)
3154 int disk;
3155 DAC960_Controller_T *Controller;
3157 if (DAC960_ControllerCount == DAC960_MaxControllers)
3159 DAC960_Error("More than %d DAC960 Controllers detected - "
3160 "ignoring from Controller at\n",
3161 NULL, DAC960_MaxControllers);
3162 return -ENODEV;
3165 Controller = DAC960_DetectController(dev, entry);
3166 if (!Controller)
3167 return -ENODEV;
3169 if (!DAC960_InitializeController(Controller)) {
3170 DAC960_FinalizeController(Controller);
3171 return -ENODEV;
3174 for (disk = 0; disk < DAC960_MaxLogicalDrives; disk++) {
3175 set_capacity(Controller->disks[disk], disk_size(Controller, disk));
3176 add_disk(Controller->disks[disk]);
3178 DAC960_CreateProcEntries(Controller);
3179 return 0;
3184 DAC960_Finalize finalizes the DAC960 Driver.
3187 static void DAC960_Remove(struct pci_dev *PCI_Device)
3189 int Controller_Number = (long)pci_get_drvdata(PCI_Device);
3190 DAC960_Controller_T *Controller = DAC960_Controllers[Controller_Number];
3191 if (Controller != NULL)
3192 DAC960_FinalizeController(Controller);
3197 DAC960_V1_QueueReadWriteCommand prepares and queues a Read/Write Command for
3198 DAC960 V1 Firmware Controllers.
3201 static void DAC960_V1_QueueReadWriteCommand(DAC960_Command_T *Command)
3203 DAC960_Controller_T *Controller = Command->Controller;
3204 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
3205 DAC960_V1_ScatterGatherSegment_T *ScatterGatherList =
3206 Command->V1.ScatterGatherList;
3207 struct scatterlist *ScatterList = Command->V1.ScatterList;
3209 DAC960_V1_ClearCommand(Command);
3211 if (Command->SegmentCount == 1)
3213 if (Command->DmaDirection == PCI_DMA_FROMDEVICE)
3214 CommandMailbox->Type5.CommandOpcode = DAC960_V1_Read;
3215 else
3216 CommandMailbox->Type5.CommandOpcode = DAC960_V1_Write;
3218 CommandMailbox->Type5.LD.TransferLength = Command->BlockCount;
3219 CommandMailbox->Type5.LD.LogicalDriveNumber = Command->LogicalDriveNumber;
3220 CommandMailbox->Type5.LogicalBlockAddress = Command->BlockNumber;
3221 CommandMailbox->Type5.BusAddress =
3222 (DAC960_BusAddress32_T)sg_dma_address(ScatterList);
3224 else
3226 int i;
3228 if (Command->DmaDirection == PCI_DMA_FROMDEVICE)
3229 CommandMailbox->Type5.CommandOpcode = DAC960_V1_ReadWithScatterGather;
3230 else
3231 CommandMailbox->Type5.CommandOpcode = DAC960_V1_WriteWithScatterGather;
3233 CommandMailbox->Type5.LD.TransferLength = Command->BlockCount;
3234 CommandMailbox->Type5.LD.LogicalDriveNumber = Command->LogicalDriveNumber;
3235 CommandMailbox->Type5.LogicalBlockAddress = Command->BlockNumber;
3236 CommandMailbox->Type5.BusAddress = Command->V1.ScatterGatherListDMA;
3238 CommandMailbox->Type5.ScatterGatherCount = Command->SegmentCount;
3240 for (i = 0; i < Command->SegmentCount; i++, ScatterList++, ScatterGatherList++) {
3241 ScatterGatherList->SegmentDataPointer =
3242 (DAC960_BusAddress32_T)sg_dma_address(ScatterList);
3243 ScatterGatherList->SegmentByteCount =
3244 (DAC960_ByteCount32_T)sg_dma_len(ScatterList);
3247 DAC960_QueueCommand(Command);
3252 DAC960_V2_QueueReadWriteCommand prepares and queues a Read/Write Command for
3253 DAC960 V2 Firmware Controllers.
3256 static void DAC960_V2_QueueReadWriteCommand(DAC960_Command_T *Command)
3258 DAC960_Controller_T *Controller = Command->Controller;
3259 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
3260 struct scatterlist *ScatterList = Command->V2.ScatterList;
3262 DAC960_V2_ClearCommand(Command);
3264 CommandMailbox->SCSI_10.CommandOpcode = DAC960_V2_SCSI_10;
3265 CommandMailbox->SCSI_10.CommandControlBits.DataTransferControllerToHost =
3266 (Command->DmaDirection == PCI_DMA_FROMDEVICE);
3267 CommandMailbox->SCSI_10.DataTransferSize =
3268 Command->BlockCount << DAC960_BlockSizeBits;
3269 CommandMailbox->SCSI_10.RequestSenseBusAddress = Command->V2.RequestSenseDMA;
3270 CommandMailbox->SCSI_10.PhysicalDevice =
3271 Controller->V2.LogicalDriveToVirtualDevice[Command->LogicalDriveNumber];
3272 CommandMailbox->SCSI_10.RequestSenseSize = sizeof(DAC960_SCSI_RequestSense_T);
3273 CommandMailbox->SCSI_10.CDBLength = 10;
3274 CommandMailbox->SCSI_10.SCSI_CDB[0] =
3275 (Command->DmaDirection == PCI_DMA_FROMDEVICE ? 0x28 : 0x2A);
3276 CommandMailbox->SCSI_10.SCSI_CDB[2] = Command->BlockNumber >> 24;
3277 CommandMailbox->SCSI_10.SCSI_CDB[3] = Command->BlockNumber >> 16;
3278 CommandMailbox->SCSI_10.SCSI_CDB[4] = Command->BlockNumber >> 8;
3279 CommandMailbox->SCSI_10.SCSI_CDB[5] = Command->BlockNumber;
3280 CommandMailbox->SCSI_10.SCSI_CDB[7] = Command->BlockCount >> 8;
3281 CommandMailbox->SCSI_10.SCSI_CDB[8] = Command->BlockCount;
3283 if (Command->SegmentCount == 1)
3285 CommandMailbox->SCSI_10.DataTransferMemoryAddress
3286 .ScatterGatherSegments[0]
3287 .SegmentDataPointer =
3288 (DAC960_BusAddress64_T)sg_dma_address(ScatterList);
3289 CommandMailbox->SCSI_10.DataTransferMemoryAddress
3290 .ScatterGatherSegments[0]
3291 .SegmentByteCount =
3292 CommandMailbox->SCSI_10.DataTransferSize;
3294 else
3296 DAC960_V2_ScatterGatherSegment_T *ScatterGatherList;
3297 int i;
3299 if (Command->SegmentCount > 2)
3301 ScatterGatherList = Command->V2.ScatterGatherList;
3302 CommandMailbox->SCSI_10.CommandControlBits
3303 .AdditionalScatterGatherListMemory = true;
3304 CommandMailbox->SCSI_10.DataTransferMemoryAddress
3305 .ExtendedScatterGather.ScatterGatherList0Length = Command->SegmentCount;
3306 CommandMailbox->SCSI_10.DataTransferMemoryAddress
3307 .ExtendedScatterGather.ScatterGatherList0Address =
3308 Command->V2.ScatterGatherListDMA;
3310 else
3311 ScatterGatherList = CommandMailbox->SCSI_10.DataTransferMemoryAddress
3312 .ScatterGatherSegments;
3314 for (i = 0; i < Command->SegmentCount; i++, ScatterList++, ScatterGatherList++) {
3315 ScatterGatherList->SegmentDataPointer =
3316 (DAC960_BusAddress64_T)sg_dma_address(ScatterList);
3317 ScatterGatherList->SegmentByteCount =
3318 (DAC960_ByteCount64_T)sg_dma_len(ScatterList);
3321 DAC960_QueueCommand(Command);
3325 static int DAC960_process_queue(DAC960_Controller_T *Controller, struct request_queue *req_q)
3327 struct request *Request;
3328 DAC960_Command_T *Command;
3330 while(1) {
3331 Request = blk_peek_request(req_q);
3332 if (!Request)
3333 return 1;
3335 Command = DAC960_AllocateCommand(Controller);
3336 if (Command == NULL)
3337 return 0;
3339 if (rq_data_dir(Request) == READ) {
3340 Command->DmaDirection = PCI_DMA_FROMDEVICE;
3341 Command->CommandType = DAC960_ReadCommand;
3342 } else {
3343 Command->DmaDirection = PCI_DMA_TODEVICE;
3344 Command->CommandType = DAC960_WriteCommand;
3346 Command->Completion = Request->end_io_data;
3347 Command->LogicalDriveNumber = (long)Request->rq_disk->private_data;
3348 Command->BlockNumber = blk_rq_pos(Request);
3349 Command->BlockCount = blk_rq_sectors(Request);
3350 Command->Request = Request;
3351 blk_start_request(Request);
3352 Command->SegmentCount = blk_rq_map_sg(req_q,
3353 Command->Request, Command->cmd_sglist);
3354 /* pci_map_sg MAY change the value of SegCount */
3355 Command->SegmentCount = pci_map_sg(Controller->PCIDevice, Command->cmd_sglist,
3356 Command->SegmentCount, Command->DmaDirection);
3358 DAC960_QueueReadWriteCommand(Command);
3363 DAC960_ProcessRequest attempts to remove one I/O Request from Controller's
3364 I/O Request Queue and queues it to the Controller. WaitForCommand is true if
3365 this function should wait for a Command to become available if necessary.
3366 This function returns true if an I/O Request was queued and false otherwise.
3368 static void DAC960_ProcessRequest(DAC960_Controller_T *controller)
3370 int i;
3372 if (!controller->ControllerInitialized)
3373 return;
3375 /* Do this better later! */
3376 for (i = controller->req_q_index; i < DAC960_MaxLogicalDrives; i++) {
3377 struct request_queue *req_q = controller->RequestQueue[i];
3379 if (req_q == NULL)
3380 continue;
3382 if (!DAC960_process_queue(controller, req_q)) {
3383 controller->req_q_index = i;
3384 return;
3388 if (controller->req_q_index == 0)
3389 return;
3391 for (i = 0; i < controller->req_q_index; i++) {
3392 struct request_queue *req_q = controller->RequestQueue[i];
3394 if (req_q == NULL)
3395 continue;
3397 if (!DAC960_process_queue(controller, req_q)) {
3398 controller->req_q_index = i;
3399 return;
3406 DAC960_queue_partial_rw extracts one bio from the request already
3407 associated with argument command, and construct a new command block to retry I/O
3408 only on that bio. Queue that command to the controller.
3410 This function re-uses a previously-allocated Command,
3411 there is no failure mode from trying to allocate a command.
3414 static void DAC960_queue_partial_rw(DAC960_Command_T *Command)
3416 DAC960_Controller_T *Controller = Command->Controller;
3417 struct request *Request = Command->Request;
3418 struct request_queue *req_q = Controller->RequestQueue[Command->LogicalDriveNumber];
3420 if (Command->DmaDirection == PCI_DMA_FROMDEVICE)
3421 Command->CommandType = DAC960_ReadRetryCommand;
3422 else
3423 Command->CommandType = DAC960_WriteRetryCommand;
3426 * We could be more efficient with these mapping requests
3427 * and map only the portions that we need. But since this
3428 * code should almost never be called, just go with a
3429 * simple coding.
3431 (void)blk_rq_map_sg(req_q, Command->Request, Command->cmd_sglist);
3433 (void)pci_map_sg(Controller->PCIDevice, Command->cmd_sglist, 1, Command->DmaDirection);
3435 * Resubmitting the request sector at a time is really tedious.
3436 * But, this should almost never happen. So, we're willing to pay
3437 * this price so that in the end, as much of the transfer is completed
3438 * successfully as possible.
3440 Command->SegmentCount = 1;
3441 Command->BlockNumber = blk_rq_pos(Request);
3442 Command->BlockCount = 1;
3443 DAC960_QueueReadWriteCommand(Command);
3444 return;
3448 DAC960_RequestFunction is the I/O Request Function for DAC960 Controllers.
3451 static void DAC960_RequestFunction(struct request_queue *RequestQueue)
3453 DAC960_ProcessRequest(RequestQueue->queuedata);
3457 DAC960_ProcessCompletedBuffer performs completion processing for an
3458 individual Buffer.
3461 static inline bool DAC960_ProcessCompletedRequest(DAC960_Command_T *Command,
3462 bool SuccessfulIO)
3464 struct request *Request = Command->Request;
3465 int Error = SuccessfulIO ? 0 : -EIO;
3467 pci_unmap_sg(Command->Controller->PCIDevice, Command->cmd_sglist,
3468 Command->SegmentCount, Command->DmaDirection);
3470 if (!__blk_end_request(Request, Error, Command->BlockCount << 9)) {
3471 if (Command->Completion) {
3472 complete(Command->Completion);
3473 Command->Completion = NULL;
3475 return true;
3477 return false;
3481 DAC960_V1_ReadWriteError prints an appropriate error message for Command
3482 when an error occurs on a Read or Write operation.
3485 static void DAC960_V1_ReadWriteError(DAC960_Command_T *Command)
3487 DAC960_Controller_T *Controller = Command->Controller;
3488 unsigned char *CommandName = "UNKNOWN";
3489 switch (Command->CommandType)
3491 case DAC960_ReadCommand:
3492 case DAC960_ReadRetryCommand:
3493 CommandName = "READ";
3494 break;
3495 case DAC960_WriteCommand:
3496 case DAC960_WriteRetryCommand:
3497 CommandName = "WRITE";
3498 break;
3499 case DAC960_MonitoringCommand:
3500 case DAC960_ImmediateCommand:
3501 case DAC960_QueuedCommand:
3502 break;
3504 switch (Command->V1.CommandStatus)
3506 case DAC960_V1_IrrecoverableDataError:
3507 DAC960_Error("Irrecoverable Data Error on %s:\n",
3508 Controller, CommandName);
3509 break;
3510 case DAC960_V1_LogicalDriveNonexistentOrOffline:
3511 DAC960_Error("Logical Drive Nonexistent or Offline on %s:\n",
3512 Controller, CommandName);
3513 break;
3514 case DAC960_V1_AccessBeyondEndOfLogicalDrive:
3515 DAC960_Error("Attempt to Access Beyond End of Logical Drive "
3516 "on %s:\n", Controller, CommandName);
3517 break;
3518 case DAC960_V1_BadDataEncountered:
3519 DAC960_Error("Bad Data Encountered on %s:\n", Controller, CommandName);
3520 break;
3521 default:
3522 DAC960_Error("Unexpected Error Status %04X on %s:\n",
3523 Controller, Command->V1.CommandStatus, CommandName);
3524 break;
3526 DAC960_Error(" /dev/rd/c%dd%d: absolute blocks %u..%u\n",
3527 Controller, Controller->ControllerNumber,
3528 Command->LogicalDriveNumber, Command->BlockNumber,
3529 Command->BlockNumber + Command->BlockCount - 1);
3534 DAC960_V1_ProcessCompletedCommand performs completion processing for Command
3535 for DAC960 V1 Firmware Controllers.
3538 static void DAC960_V1_ProcessCompletedCommand(DAC960_Command_T *Command)
3540 DAC960_Controller_T *Controller = Command->Controller;
3541 DAC960_CommandType_T CommandType = Command->CommandType;
3542 DAC960_V1_CommandOpcode_T CommandOpcode =
3543 Command->V1.CommandMailbox.Common.CommandOpcode;
3544 DAC960_V1_CommandStatus_T CommandStatus = Command->V1.CommandStatus;
3546 if (CommandType == DAC960_ReadCommand ||
3547 CommandType == DAC960_WriteCommand)
3550 #ifdef FORCE_RETRY_DEBUG
3551 CommandStatus = DAC960_V1_IrrecoverableDataError;
3552 #endif
3554 if (CommandStatus == DAC960_V1_NormalCompletion) {
3556 if (!DAC960_ProcessCompletedRequest(Command, true))
3557 BUG();
3559 } else if (CommandStatus == DAC960_V1_IrrecoverableDataError ||
3560 CommandStatus == DAC960_V1_BadDataEncountered)
3563 * break the command down into pieces and resubmit each
3564 * piece, hoping that some of them will succeed.
3566 DAC960_queue_partial_rw(Command);
3567 return;
3569 else
3571 if (CommandStatus != DAC960_V1_LogicalDriveNonexistentOrOffline)
3572 DAC960_V1_ReadWriteError(Command);
3574 if (!DAC960_ProcessCompletedRequest(Command, false))
3575 BUG();
3578 else if (CommandType == DAC960_ReadRetryCommand ||
3579 CommandType == DAC960_WriteRetryCommand)
3581 bool normal_completion;
3582 #ifdef FORCE_RETRY_FAILURE_DEBUG
3583 static int retry_count = 1;
3584 #endif
3586 Perform completion processing for the portion that was
3587 retried, and submit the next portion, if any.
3589 normal_completion = true;
3590 if (CommandStatus != DAC960_V1_NormalCompletion) {
3591 normal_completion = false;
3592 if (CommandStatus != DAC960_V1_LogicalDriveNonexistentOrOffline)
3593 DAC960_V1_ReadWriteError(Command);
3596 #ifdef FORCE_RETRY_FAILURE_DEBUG
3597 if (!(++retry_count % 10000)) {
3598 printk("V1 error retry failure test\n");
3599 normal_completion = false;
3600 DAC960_V1_ReadWriteError(Command);
3602 #endif
3604 if (!DAC960_ProcessCompletedRequest(Command, normal_completion)) {
3605 DAC960_queue_partial_rw(Command);
3606 return;
3610 else if (CommandType == DAC960_MonitoringCommand)
3612 if (Controller->ShutdownMonitoringTimer)
3613 return;
3614 if (CommandOpcode == DAC960_V1_Enquiry)
3616 DAC960_V1_Enquiry_T *OldEnquiry = &Controller->V1.Enquiry;
3617 DAC960_V1_Enquiry_T *NewEnquiry = Controller->V1.NewEnquiry;
3618 unsigned int OldCriticalLogicalDriveCount =
3619 OldEnquiry->CriticalLogicalDriveCount;
3620 unsigned int NewCriticalLogicalDriveCount =
3621 NewEnquiry->CriticalLogicalDriveCount;
3622 if (NewEnquiry->NumberOfLogicalDrives > Controller->LogicalDriveCount)
3624 int LogicalDriveNumber = Controller->LogicalDriveCount - 1;
3625 while (++LogicalDriveNumber < NewEnquiry->NumberOfLogicalDrives)
3626 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
3627 "Now Exists\n", Controller,
3628 LogicalDriveNumber,
3629 Controller->ControllerNumber,
3630 LogicalDriveNumber);
3631 Controller->LogicalDriveCount = NewEnquiry->NumberOfLogicalDrives;
3632 DAC960_ComputeGenericDiskInfo(Controller);
3634 if (NewEnquiry->NumberOfLogicalDrives < Controller->LogicalDriveCount)
3636 int LogicalDriveNumber = NewEnquiry->NumberOfLogicalDrives - 1;
3637 while (++LogicalDriveNumber < Controller->LogicalDriveCount)
3638 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
3639 "No Longer Exists\n", Controller,
3640 LogicalDriveNumber,
3641 Controller->ControllerNumber,
3642 LogicalDriveNumber);
3643 Controller->LogicalDriveCount = NewEnquiry->NumberOfLogicalDrives;
3644 DAC960_ComputeGenericDiskInfo(Controller);
3646 if (NewEnquiry->StatusFlags.DeferredWriteError !=
3647 OldEnquiry->StatusFlags.DeferredWriteError)
3648 DAC960_Critical("Deferred Write Error Flag is now %s\n", Controller,
3649 (NewEnquiry->StatusFlags.DeferredWriteError
3650 ? "TRUE" : "FALSE"));
3651 if ((NewCriticalLogicalDriveCount > 0 ||
3652 NewCriticalLogicalDriveCount != OldCriticalLogicalDriveCount) ||
3653 (NewEnquiry->OfflineLogicalDriveCount > 0 ||
3654 NewEnquiry->OfflineLogicalDriveCount !=
3655 OldEnquiry->OfflineLogicalDriveCount) ||
3656 (NewEnquiry->DeadDriveCount > 0 ||
3657 NewEnquiry->DeadDriveCount !=
3658 OldEnquiry->DeadDriveCount) ||
3659 (NewEnquiry->EventLogSequenceNumber !=
3660 OldEnquiry->EventLogSequenceNumber) ||
3661 Controller->MonitoringTimerCount == 0 ||
3662 time_after_eq(jiffies, Controller->SecondaryMonitoringTime
3663 + DAC960_SecondaryMonitoringInterval))
3665 Controller->V1.NeedLogicalDriveInformation = true;
3666 Controller->V1.NewEventLogSequenceNumber =
3667 NewEnquiry->EventLogSequenceNumber;
3668 Controller->V1.NeedErrorTableInformation = true;
3669 Controller->V1.NeedDeviceStateInformation = true;
3670 Controller->V1.StartDeviceStateScan = true;
3671 Controller->V1.NeedBackgroundInitializationStatus =
3672 Controller->V1.BackgroundInitializationStatusSupported;
3673 Controller->SecondaryMonitoringTime = jiffies;
3675 if (NewEnquiry->RebuildFlag == DAC960_V1_StandbyRebuildInProgress ||
3676 NewEnquiry->RebuildFlag
3677 == DAC960_V1_BackgroundRebuildInProgress ||
3678 OldEnquiry->RebuildFlag == DAC960_V1_StandbyRebuildInProgress ||
3679 OldEnquiry->RebuildFlag == DAC960_V1_BackgroundRebuildInProgress)
3681 Controller->V1.NeedRebuildProgress = true;
3682 Controller->V1.RebuildProgressFirst =
3683 (NewEnquiry->CriticalLogicalDriveCount <
3684 OldEnquiry->CriticalLogicalDriveCount);
3686 if (OldEnquiry->RebuildFlag == DAC960_V1_BackgroundCheckInProgress)
3687 switch (NewEnquiry->RebuildFlag)
3689 case DAC960_V1_NoStandbyRebuildOrCheckInProgress:
3690 DAC960_Progress("Consistency Check Completed Successfully\n",
3691 Controller);
3692 break;
3693 case DAC960_V1_StandbyRebuildInProgress:
3694 case DAC960_V1_BackgroundRebuildInProgress:
3695 break;
3696 case DAC960_V1_BackgroundCheckInProgress:
3697 Controller->V1.NeedConsistencyCheckProgress = true;
3698 break;
3699 case DAC960_V1_StandbyRebuildCompletedWithError:
3700 DAC960_Progress("Consistency Check Completed with Error\n",
3701 Controller);
3702 break;
3703 case DAC960_V1_BackgroundRebuildOrCheckFailed_DriveFailed:
3704 DAC960_Progress("Consistency Check Failed - "
3705 "Physical Device Failed\n", Controller);
3706 break;
3707 case DAC960_V1_BackgroundRebuildOrCheckFailed_LogicalDriveFailed:
3708 DAC960_Progress("Consistency Check Failed - "
3709 "Logical Drive Failed\n", Controller);
3710 break;
3711 case DAC960_V1_BackgroundRebuildOrCheckFailed_OtherCauses:
3712 DAC960_Progress("Consistency Check Failed - Other Causes\n",
3713 Controller);
3714 break;
3715 case DAC960_V1_BackgroundRebuildOrCheckSuccessfullyTerminated:
3716 DAC960_Progress("Consistency Check Successfully Terminated\n",
3717 Controller);
3718 break;
3720 else if (NewEnquiry->RebuildFlag
3721 == DAC960_V1_BackgroundCheckInProgress)
3722 Controller->V1.NeedConsistencyCheckProgress = true;
3723 Controller->MonitoringAlertMode =
3724 (NewEnquiry->CriticalLogicalDriveCount > 0 ||
3725 NewEnquiry->OfflineLogicalDriveCount > 0 ||
3726 NewEnquiry->DeadDriveCount > 0);
3727 if (NewEnquiry->RebuildFlag > DAC960_V1_BackgroundCheckInProgress)
3729 Controller->V1.PendingRebuildFlag = NewEnquiry->RebuildFlag;
3730 Controller->V1.RebuildFlagPending = true;
3732 memcpy(&Controller->V1.Enquiry, &Controller->V1.NewEnquiry,
3733 sizeof(DAC960_V1_Enquiry_T));
3735 else if (CommandOpcode == DAC960_V1_PerformEventLogOperation)
3737 static char
3738 *DAC960_EventMessages[] =
3739 { "killed because write recovery failed",
3740 "killed because of SCSI bus reset failure",
3741 "killed because of double check condition",
3742 "killed because it was removed",
3743 "killed because of gross error on SCSI chip",
3744 "killed because of bad tag returned from drive",
3745 "killed because of timeout on SCSI command",
3746 "killed because of reset SCSI command issued from system",
3747 "killed because busy or parity error count exceeded limit",
3748 "killed because of 'kill drive' command from system",
3749 "killed because of selection timeout",
3750 "killed due to SCSI phase sequence error",
3751 "killed due to unknown status" };
3752 DAC960_V1_EventLogEntry_T *EventLogEntry =
3753 Controller->V1.EventLogEntry;
3754 if (EventLogEntry->SequenceNumber ==
3755 Controller->V1.OldEventLogSequenceNumber)
3757 unsigned char SenseKey = EventLogEntry->SenseKey;
3758 unsigned char AdditionalSenseCode =
3759 EventLogEntry->AdditionalSenseCode;
3760 unsigned char AdditionalSenseCodeQualifier =
3761 EventLogEntry->AdditionalSenseCodeQualifier;
3762 if (SenseKey == DAC960_SenseKey_VendorSpecific &&
3763 AdditionalSenseCode == 0x80 &&
3764 AdditionalSenseCodeQualifier <
3765 ARRAY_SIZE(DAC960_EventMessages))
3766 DAC960_Critical("Physical Device %d:%d %s\n", Controller,
3767 EventLogEntry->Channel,
3768 EventLogEntry->TargetID,
3769 DAC960_EventMessages[
3770 AdditionalSenseCodeQualifier]);
3771 else if (SenseKey == DAC960_SenseKey_UnitAttention &&
3772 AdditionalSenseCode == 0x29)
3774 if (Controller->MonitoringTimerCount > 0)
3775 Controller->V1.DeviceResetCount[EventLogEntry->Channel]
3776 [EventLogEntry->TargetID]++;
3778 else if (!(SenseKey == DAC960_SenseKey_NoSense ||
3779 (SenseKey == DAC960_SenseKey_NotReady &&
3780 AdditionalSenseCode == 0x04 &&
3781 (AdditionalSenseCodeQualifier == 0x01 ||
3782 AdditionalSenseCodeQualifier == 0x02))))
3784 DAC960_Critical("Physical Device %d:%d Error Log: "
3785 "Sense Key = %X, ASC = %02X, ASCQ = %02X\n",
3786 Controller,
3787 EventLogEntry->Channel,
3788 EventLogEntry->TargetID,
3789 SenseKey,
3790 AdditionalSenseCode,
3791 AdditionalSenseCodeQualifier);
3792 DAC960_Critical("Physical Device %d:%d Error Log: "
3793 "Information = %02X%02X%02X%02X "
3794 "%02X%02X%02X%02X\n",
3795 Controller,
3796 EventLogEntry->Channel,
3797 EventLogEntry->TargetID,
3798 EventLogEntry->Information[0],
3799 EventLogEntry->Information[1],
3800 EventLogEntry->Information[2],
3801 EventLogEntry->Information[3],
3802 EventLogEntry->CommandSpecificInformation[0],
3803 EventLogEntry->CommandSpecificInformation[1],
3804 EventLogEntry->CommandSpecificInformation[2],
3805 EventLogEntry->CommandSpecificInformation[3]);
3808 Controller->V1.OldEventLogSequenceNumber++;
3810 else if (CommandOpcode == DAC960_V1_GetErrorTable)
3812 DAC960_V1_ErrorTable_T *OldErrorTable = &Controller->V1.ErrorTable;
3813 DAC960_V1_ErrorTable_T *NewErrorTable = Controller->V1.NewErrorTable;
3814 int Channel, TargetID;
3815 for (Channel = 0; Channel < Controller->Channels; Channel++)
3816 for (TargetID = 0; TargetID < Controller->Targets; TargetID++)
3818 DAC960_V1_ErrorTableEntry_T *NewErrorEntry =
3819 &NewErrorTable->ErrorTableEntries[Channel][TargetID];
3820 DAC960_V1_ErrorTableEntry_T *OldErrorEntry =
3821 &OldErrorTable->ErrorTableEntries[Channel][TargetID];
3822 if ((NewErrorEntry->ParityErrorCount !=
3823 OldErrorEntry->ParityErrorCount) ||
3824 (NewErrorEntry->SoftErrorCount !=
3825 OldErrorEntry->SoftErrorCount) ||
3826 (NewErrorEntry->HardErrorCount !=
3827 OldErrorEntry->HardErrorCount) ||
3828 (NewErrorEntry->MiscErrorCount !=
3829 OldErrorEntry->MiscErrorCount))
3830 DAC960_Critical("Physical Device %d:%d Errors: "
3831 "Parity = %d, Soft = %d, "
3832 "Hard = %d, Misc = %d\n",
3833 Controller, Channel, TargetID,
3834 NewErrorEntry->ParityErrorCount,
3835 NewErrorEntry->SoftErrorCount,
3836 NewErrorEntry->HardErrorCount,
3837 NewErrorEntry->MiscErrorCount);
3839 memcpy(&Controller->V1.ErrorTable, Controller->V1.NewErrorTable,
3840 sizeof(DAC960_V1_ErrorTable_T));
3842 else if (CommandOpcode == DAC960_V1_GetDeviceState)
3844 DAC960_V1_DeviceState_T *OldDeviceState =
3845 &Controller->V1.DeviceState[Controller->V1.DeviceStateChannel]
3846 [Controller->V1.DeviceStateTargetID];
3847 DAC960_V1_DeviceState_T *NewDeviceState =
3848 Controller->V1.NewDeviceState;
3849 if (NewDeviceState->DeviceState != OldDeviceState->DeviceState)
3850 DAC960_Critical("Physical Device %d:%d is now %s\n", Controller,
3851 Controller->V1.DeviceStateChannel,
3852 Controller->V1.DeviceStateTargetID,
3853 (NewDeviceState->DeviceState
3854 == DAC960_V1_Device_Dead
3855 ? "DEAD"
3856 : NewDeviceState->DeviceState
3857 == DAC960_V1_Device_WriteOnly
3858 ? "WRITE-ONLY"
3859 : NewDeviceState->DeviceState
3860 == DAC960_V1_Device_Online
3861 ? "ONLINE" : "STANDBY"));
3862 if (OldDeviceState->DeviceState == DAC960_V1_Device_Dead &&
3863 NewDeviceState->DeviceState != DAC960_V1_Device_Dead)
3865 Controller->V1.NeedDeviceInquiryInformation = true;
3866 Controller->V1.NeedDeviceSerialNumberInformation = true;
3867 Controller->V1.DeviceResetCount
3868 [Controller->V1.DeviceStateChannel]
3869 [Controller->V1.DeviceStateTargetID] = 0;
3871 memcpy(OldDeviceState, NewDeviceState,
3872 sizeof(DAC960_V1_DeviceState_T));
3874 else if (CommandOpcode == DAC960_V1_GetLogicalDriveInformation)
3876 int LogicalDriveNumber;
3877 for (LogicalDriveNumber = 0;
3878 LogicalDriveNumber < Controller->LogicalDriveCount;
3879 LogicalDriveNumber++)
3881 DAC960_V1_LogicalDriveInformation_T *OldLogicalDriveInformation =
3882 &Controller->V1.LogicalDriveInformation[LogicalDriveNumber];
3883 DAC960_V1_LogicalDriveInformation_T *NewLogicalDriveInformation =
3884 &(*Controller->V1.NewLogicalDriveInformation)[LogicalDriveNumber];
3885 if (NewLogicalDriveInformation->LogicalDriveState !=
3886 OldLogicalDriveInformation->LogicalDriveState)
3887 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
3888 "is now %s\n", Controller,
3889 LogicalDriveNumber,
3890 Controller->ControllerNumber,
3891 LogicalDriveNumber,
3892 (NewLogicalDriveInformation->LogicalDriveState
3893 == DAC960_V1_LogicalDrive_Online
3894 ? "ONLINE"
3895 : NewLogicalDriveInformation->LogicalDriveState
3896 == DAC960_V1_LogicalDrive_Critical
3897 ? "CRITICAL" : "OFFLINE"));
3898 if (NewLogicalDriveInformation->WriteBack !=
3899 OldLogicalDriveInformation->WriteBack)
3900 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
3901 "is now %s\n", Controller,
3902 LogicalDriveNumber,
3903 Controller->ControllerNumber,
3904 LogicalDriveNumber,
3905 (NewLogicalDriveInformation->WriteBack
3906 ? "WRITE BACK" : "WRITE THRU"));
3908 memcpy(&Controller->V1.LogicalDriveInformation,
3909 Controller->V1.NewLogicalDriveInformation,
3910 sizeof(DAC960_V1_LogicalDriveInformationArray_T));
3912 else if (CommandOpcode == DAC960_V1_GetRebuildProgress)
3914 unsigned int LogicalDriveNumber =
3915 Controller->V1.RebuildProgress->LogicalDriveNumber;
3916 unsigned int LogicalDriveSize =
3917 Controller->V1.RebuildProgress->LogicalDriveSize;
3918 unsigned int BlocksCompleted =
3919 LogicalDriveSize - Controller->V1.RebuildProgress->RemainingBlocks;
3920 if (CommandStatus == DAC960_V1_NoRebuildOrCheckInProgress &&
3921 Controller->V1.LastRebuildStatus == DAC960_V1_NormalCompletion)
3922 CommandStatus = DAC960_V1_RebuildSuccessful;
3923 switch (CommandStatus)
3925 case DAC960_V1_NormalCompletion:
3926 Controller->EphemeralProgressMessage = true;
3927 DAC960_Progress("Rebuild in Progress: "
3928 "Logical Drive %d (/dev/rd/c%dd%d) "
3929 "%d%% completed\n",
3930 Controller, LogicalDriveNumber,
3931 Controller->ControllerNumber,
3932 LogicalDriveNumber,
3933 (100 * (BlocksCompleted >> 7))
3934 / (LogicalDriveSize >> 7));
3935 Controller->EphemeralProgressMessage = false;
3936 break;
3937 case DAC960_V1_RebuildFailed_LogicalDriveFailure:
3938 DAC960_Progress("Rebuild Failed due to "
3939 "Logical Drive Failure\n", Controller);
3940 break;
3941 case DAC960_V1_RebuildFailed_BadBlocksOnOther:
3942 DAC960_Progress("Rebuild Failed due to "
3943 "Bad Blocks on Other Drives\n", Controller);
3944 break;
3945 case DAC960_V1_RebuildFailed_NewDriveFailed:
3946 DAC960_Progress("Rebuild Failed due to "
3947 "Failure of Drive Being Rebuilt\n", Controller);
3948 break;
3949 case DAC960_V1_NoRebuildOrCheckInProgress:
3950 break;
3951 case DAC960_V1_RebuildSuccessful:
3952 DAC960_Progress("Rebuild Completed Successfully\n", Controller);
3953 break;
3954 case DAC960_V1_RebuildSuccessfullyTerminated:
3955 DAC960_Progress("Rebuild Successfully Terminated\n", Controller);
3956 break;
3958 Controller->V1.LastRebuildStatus = CommandStatus;
3959 if (CommandType != DAC960_MonitoringCommand &&
3960 Controller->V1.RebuildStatusPending)
3962 Command->V1.CommandStatus = Controller->V1.PendingRebuildStatus;
3963 Controller->V1.RebuildStatusPending = false;
3965 else if (CommandType == DAC960_MonitoringCommand &&
3966 CommandStatus != DAC960_V1_NormalCompletion &&
3967 CommandStatus != DAC960_V1_NoRebuildOrCheckInProgress)
3969 Controller->V1.PendingRebuildStatus = CommandStatus;
3970 Controller->V1.RebuildStatusPending = true;
3973 else if (CommandOpcode == DAC960_V1_RebuildStat)
3975 unsigned int LogicalDriveNumber =
3976 Controller->V1.RebuildProgress->LogicalDriveNumber;
3977 unsigned int LogicalDriveSize =
3978 Controller->V1.RebuildProgress->LogicalDriveSize;
3979 unsigned int BlocksCompleted =
3980 LogicalDriveSize - Controller->V1.RebuildProgress->RemainingBlocks;
3981 if (CommandStatus == DAC960_V1_NormalCompletion)
3983 Controller->EphemeralProgressMessage = true;
3984 DAC960_Progress("Consistency Check in Progress: "
3985 "Logical Drive %d (/dev/rd/c%dd%d) "
3986 "%d%% completed\n",
3987 Controller, LogicalDriveNumber,
3988 Controller->ControllerNumber,
3989 LogicalDriveNumber,
3990 (100 * (BlocksCompleted >> 7))
3991 / (LogicalDriveSize >> 7));
3992 Controller->EphemeralProgressMessage = false;
3995 else if (CommandOpcode == DAC960_V1_BackgroundInitializationControl)
3997 unsigned int LogicalDriveNumber =
3998 Controller->V1.BackgroundInitializationStatus->LogicalDriveNumber;
3999 unsigned int LogicalDriveSize =
4000 Controller->V1.BackgroundInitializationStatus->LogicalDriveSize;
4001 unsigned int BlocksCompleted =
4002 Controller->V1.BackgroundInitializationStatus->BlocksCompleted;
4003 switch (CommandStatus)
4005 case DAC960_V1_NormalCompletion:
4006 switch (Controller->V1.BackgroundInitializationStatus->Status)
4008 case DAC960_V1_BackgroundInitializationInvalid:
4009 break;
4010 case DAC960_V1_BackgroundInitializationStarted:
4011 DAC960_Progress("Background Initialization Started\n",
4012 Controller);
4013 break;
4014 case DAC960_V1_BackgroundInitializationInProgress:
4015 if (BlocksCompleted ==
4016 Controller->V1.LastBackgroundInitializationStatus.
4017 BlocksCompleted &&
4018 LogicalDriveNumber ==
4019 Controller->V1.LastBackgroundInitializationStatus.
4020 LogicalDriveNumber)
4021 break;
4022 Controller->EphemeralProgressMessage = true;
4023 DAC960_Progress("Background Initialization in Progress: "
4024 "Logical Drive %d (/dev/rd/c%dd%d) "
4025 "%d%% completed\n",
4026 Controller, LogicalDriveNumber,
4027 Controller->ControllerNumber,
4028 LogicalDriveNumber,
4029 (100 * (BlocksCompleted >> 7))
4030 / (LogicalDriveSize >> 7));
4031 Controller->EphemeralProgressMessage = false;
4032 break;
4033 case DAC960_V1_BackgroundInitializationSuspended:
4034 DAC960_Progress("Background Initialization Suspended\n",
4035 Controller);
4036 break;
4037 case DAC960_V1_BackgroundInitializationCancelled:
4038 DAC960_Progress("Background Initialization Cancelled\n",
4039 Controller);
4040 break;
4042 memcpy(&Controller->V1.LastBackgroundInitializationStatus,
4043 Controller->V1.BackgroundInitializationStatus,
4044 sizeof(DAC960_V1_BackgroundInitializationStatus_T));
4045 break;
4046 case DAC960_V1_BackgroundInitSuccessful:
4047 if (Controller->V1.BackgroundInitializationStatus->Status ==
4048 DAC960_V1_BackgroundInitializationInProgress)
4049 DAC960_Progress("Background Initialization "
4050 "Completed Successfully\n", Controller);
4051 Controller->V1.BackgroundInitializationStatus->Status =
4052 DAC960_V1_BackgroundInitializationInvalid;
4053 break;
4054 case DAC960_V1_BackgroundInitAborted:
4055 if (Controller->V1.BackgroundInitializationStatus->Status ==
4056 DAC960_V1_BackgroundInitializationInProgress)
4057 DAC960_Progress("Background Initialization Aborted\n",
4058 Controller);
4059 Controller->V1.BackgroundInitializationStatus->Status =
4060 DAC960_V1_BackgroundInitializationInvalid;
4061 break;
4062 case DAC960_V1_NoBackgroundInitInProgress:
4063 break;
4066 else if (CommandOpcode == DAC960_V1_DCDB)
4069 This is a bit ugly.
4071 The InquiryStandardData and
4072 the InquiryUntitSerialNumber information
4073 retrieval operations BOTH use the DAC960_V1_DCDB
4074 commands. the test above can't distinguish between
4075 these two cases.
4077 Instead, we rely on the order of code later in this
4078 function to ensure that DeviceInquiryInformation commands
4079 are submitted before DeviceSerialNumber commands.
4081 if (Controller->V1.NeedDeviceInquiryInformation)
4083 DAC960_SCSI_Inquiry_T *InquiryStandardData =
4084 &Controller->V1.InquiryStandardData
4085 [Controller->V1.DeviceStateChannel]
4086 [Controller->V1.DeviceStateTargetID];
4087 if (CommandStatus != DAC960_V1_NormalCompletion)
4089 memset(InquiryStandardData, 0,
4090 sizeof(DAC960_SCSI_Inquiry_T));
4091 InquiryStandardData->PeripheralDeviceType = 0x1F;
4093 else
4094 memcpy(InquiryStandardData,
4095 Controller->V1.NewInquiryStandardData,
4096 sizeof(DAC960_SCSI_Inquiry_T));
4097 Controller->V1.NeedDeviceInquiryInformation = false;
4099 else if (Controller->V1.NeedDeviceSerialNumberInformation)
4101 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
4102 &Controller->V1.InquiryUnitSerialNumber
4103 [Controller->V1.DeviceStateChannel]
4104 [Controller->V1.DeviceStateTargetID];
4105 if (CommandStatus != DAC960_V1_NormalCompletion)
4107 memset(InquiryUnitSerialNumber, 0,
4108 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
4109 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
4111 else
4112 memcpy(InquiryUnitSerialNumber,
4113 Controller->V1.NewInquiryUnitSerialNumber,
4114 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
4115 Controller->V1.NeedDeviceSerialNumberInformation = false;
4119 Begin submitting new monitoring commands.
4121 if (Controller->V1.NewEventLogSequenceNumber
4122 - Controller->V1.OldEventLogSequenceNumber > 0)
4124 Command->V1.CommandMailbox.Type3E.CommandOpcode =
4125 DAC960_V1_PerformEventLogOperation;
4126 Command->V1.CommandMailbox.Type3E.OperationType =
4127 DAC960_V1_GetEventLogEntry;
4128 Command->V1.CommandMailbox.Type3E.OperationQualifier = 1;
4129 Command->V1.CommandMailbox.Type3E.SequenceNumber =
4130 Controller->V1.OldEventLogSequenceNumber;
4131 Command->V1.CommandMailbox.Type3E.BusAddress =
4132 Controller->V1.EventLogEntryDMA;
4133 DAC960_QueueCommand(Command);
4134 return;
4136 if (Controller->V1.NeedErrorTableInformation)
4138 Controller->V1.NeedErrorTableInformation = false;
4139 Command->V1.CommandMailbox.Type3.CommandOpcode =
4140 DAC960_V1_GetErrorTable;
4141 Command->V1.CommandMailbox.Type3.BusAddress =
4142 Controller->V1.NewErrorTableDMA;
4143 DAC960_QueueCommand(Command);
4144 return;
4146 if (Controller->V1.NeedRebuildProgress &&
4147 Controller->V1.RebuildProgressFirst)
4149 Controller->V1.NeedRebuildProgress = false;
4150 Command->V1.CommandMailbox.Type3.CommandOpcode =
4151 DAC960_V1_GetRebuildProgress;
4152 Command->V1.CommandMailbox.Type3.BusAddress =
4153 Controller->V1.RebuildProgressDMA;
4154 DAC960_QueueCommand(Command);
4155 return;
4157 if (Controller->V1.NeedDeviceStateInformation)
4159 if (Controller->V1.NeedDeviceInquiryInformation)
4161 DAC960_V1_DCDB_T *DCDB = Controller->V1.MonitoringDCDB;
4162 dma_addr_t DCDB_DMA = Controller->V1.MonitoringDCDB_DMA;
4164 dma_addr_t NewInquiryStandardDataDMA =
4165 Controller->V1.NewInquiryStandardDataDMA;
4167 Command->V1.CommandMailbox.Type3.CommandOpcode = DAC960_V1_DCDB;
4168 Command->V1.CommandMailbox.Type3.BusAddress = DCDB_DMA;
4169 DCDB->Channel = Controller->V1.DeviceStateChannel;
4170 DCDB->TargetID = Controller->V1.DeviceStateTargetID;
4171 DCDB->Direction = DAC960_V1_DCDB_DataTransferDeviceToSystem;
4172 DCDB->EarlyStatus = false;
4173 DCDB->Timeout = DAC960_V1_DCDB_Timeout_10_seconds;
4174 DCDB->NoAutomaticRequestSense = false;
4175 DCDB->DisconnectPermitted = true;
4176 DCDB->TransferLength = sizeof(DAC960_SCSI_Inquiry_T);
4177 DCDB->BusAddress = NewInquiryStandardDataDMA;
4178 DCDB->CDBLength = 6;
4179 DCDB->TransferLengthHigh4 = 0;
4180 DCDB->SenseLength = sizeof(DCDB->SenseData);
4181 DCDB->CDB[0] = 0x12; /* INQUIRY */
4182 DCDB->CDB[1] = 0; /* EVPD = 0 */
4183 DCDB->CDB[2] = 0; /* Page Code */
4184 DCDB->CDB[3] = 0; /* Reserved */
4185 DCDB->CDB[4] = sizeof(DAC960_SCSI_Inquiry_T);
4186 DCDB->CDB[5] = 0; /* Control */
4187 DAC960_QueueCommand(Command);
4188 return;
4190 if (Controller->V1.NeedDeviceSerialNumberInformation)
4192 DAC960_V1_DCDB_T *DCDB = Controller->V1.MonitoringDCDB;
4193 dma_addr_t DCDB_DMA = Controller->V1.MonitoringDCDB_DMA;
4194 dma_addr_t NewInquiryUnitSerialNumberDMA =
4195 Controller->V1.NewInquiryUnitSerialNumberDMA;
4197 Command->V1.CommandMailbox.Type3.CommandOpcode = DAC960_V1_DCDB;
4198 Command->V1.CommandMailbox.Type3.BusAddress = DCDB_DMA;
4199 DCDB->Channel = Controller->V1.DeviceStateChannel;
4200 DCDB->TargetID = Controller->V1.DeviceStateTargetID;
4201 DCDB->Direction = DAC960_V1_DCDB_DataTransferDeviceToSystem;
4202 DCDB->EarlyStatus = false;
4203 DCDB->Timeout = DAC960_V1_DCDB_Timeout_10_seconds;
4204 DCDB->NoAutomaticRequestSense = false;
4205 DCDB->DisconnectPermitted = true;
4206 DCDB->TransferLength =
4207 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
4208 DCDB->BusAddress = NewInquiryUnitSerialNumberDMA;
4209 DCDB->CDBLength = 6;
4210 DCDB->TransferLengthHigh4 = 0;
4211 DCDB->SenseLength = sizeof(DCDB->SenseData);
4212 DCDB->CDB[0] = 0x12; /* INQUIRY */
4213 DCDB->CDB[1] = 1; /* EVPD = 1 */
4214 DCDB->CDB[2] = 0x80; /* Page Code */
4215 DCDB->CDB[3] = 0; /* Reserved */
4216 DCDB->CDB[4] = sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T);
4217 DCDB->CDB[5] = 0; /* Control */
4218 DAC960_QueueCommand(Command);
4219 return;
4221 if (Controller->V1.StartDeviceStateScan)
4223 Controller->V1.DeviceStateChannel = 0;
4224 Controller->V1.DeviceStateTargetID = 0;
4225 Controller->V1.StartDeviceStateScan = false;
4227 else if (++Controller->V1.DeviceStateTargetID == Controller->Targets)
4229 Controller->V1.DeviceStateChannel++;
4230 Controller->V1.DeviceStateTargetID = 0;
4232 if (Controller->V1.DeviceStateChannel < Controller->Channels)
4234 Controller->V1.NewDeviceState->DeviceState =
4235 DAC960_V1_Device_Dead;
4236 Command->V1.CommandMailbox.Type3D.CommandOpcode =
4237 DAC960_V1_GetDeviceState;
4238 Command->V1.CommandMailbox.Type3D.Channel =
4239 Controller->V1.DeviceStateChannel;
4240 Command->V1.CommandMailbox.Type3D.TargetID =
4241 Controller->V1.DeviceStateTargetID;
4242 Command->V1.CommandMailbox.Type3D.BusAddress =
4243 Controller->V1.NewDeviceStateDMA;
4244 DAC960_QueueCommand(Command);
4245 return;
4247 Controller->V1.NeedDeviceStateInformation = false;
4249 if (Controller->V1.NeedLogicalDriveInformation)
4251 Controller->V1.NeedLogicalDriveInformation = false;
4252 Command->V1.CommandMailbox.Type3.CommandOpcode =
4253 DAC960_V1_GetLogicalDriveInformation;
4254 Command->V1.CommandMailbox.Type3.BusAddress =
4255 Controller->V1.NewLogicalDriveInformationDMA;
4256 DAC960_QueueCommand(Command);
4257 return;
4259 if (Controller->V1.NeedRebuildProgress)
4261 Controller->V1.NeedRebuildProgress = false;
4262 Command->V1.CommandMailbox.Type3.CommandOpcode =
4263 DAC960_V1_GetRebuildProgress;
4264 Command->V1.CommandMailbox.Type3.BusAddress =
4265 Controller->V1.RebuildProgressDMA;
4266 DAC960_QueueCommand(Command);
4267 return;
4269 if (Controller->V1.NeedConsistencyCheckProgress)
4271 Controller->V1.NeedConsistencyCheckProgress = false;
4272 Command->V1.CommandMailbox.Type3.CommandOpcode =
4273 DAC960_V1_RebuildStat;
4274 Command->V1.CommandMailbox.Type3.BusAddress =
4275 Controller->V1.RebuildProgressDMA;
4276 DAC960_QueueCommand(Command);
4277 return;
4279 if (Controller->V1.NeedBackgroundInitializationStatus)
4281 Controller->V1.NeedBackgroundInitializationStatus = false;
4282 Command->V1.CommandMailbox.Type3B.CommandOpcode =
4283 DAC960_V1_BackgroundInitializationControl;
4284 Command->V1.CommandMailbox.Type3B.CommandOpcode2 = 0x20;
4285 Command->V1.CommandMailbox.Type3B.BusAddress =
4286 Controller->V1.BackgroundInitializationStatusDMA;
4287 DAC960_QueueCommand(Command);
4288 return;
4290 Controller->MonitoringTimerCount++;
4291 Controller->MonitoringTimer.expires =
4292 jiffies + DAC960_MonitoringTimerInterval;
4293 add_timer(&Controller->MonitoringTimer);
4295 if (CommandType == DAC960_ImmediateCommand)
4297 complete(Command->Completion);
4298 Command->Completion = NULL;
4299 return;
4301 if (CommandType == DAC960_QueuedCommand)
4303 DAC960_V1_KernelCommand_T *KernelCommand = Command->V1.KernelCommand;
4304 KernelCommand->CommandStatus = Command->V1.CommandStatus;
4305 Command->V1.KernelCommand = NULL;
4306 if (CommandOpcode == DAC960_V1_DCDB)
4307 Controller->V1.DirectCommandActive[KernelCommand->DCDB->Channel]
4308 [KernelCommand->DCDB->TargetID] =
4309 false;
4310 DAC960_DeallocateCommand(Command);
4311 KernelCommand->CompletionFunction(KernelCommand);
4312 return;
4315 Queue a Status Monitoring Command to the Controller using the just
4316 completed Command if one was deferred previously due to lack of a
4317 free Command when the Monitoring Timer Function was called.
4319 if (Controller->MonitoringCommandDeferred)
4321 Controller->MonitoringCommandDeferred = false;
4322 DAC960_V1_QueueMonitoringCommand(Command);
4323 return;
4326 Deallocate the Command.
4328 DAC960_DeallocateCommand(Command);
4330 Wake up any processes waiting on a free Command.
4332 wake_up(&Controller->CommandWaitQueue);
4337 DAC960_V2_ReadWriteError prints an appropriate error message for Command
4338 when an error occurs on a Read or Write operation.
4341 static void DAC960_V2_ReadWriteError(DAC960_Command_T *Command)
4343 DAC960_Controller_T *Controller = Command->Controller;
4344 unsigned char *SenseErrors[] = { "NO SENSE", "RECOVERED ERROR",
4345 "NOT READY", "MEDIUM ERROR",
4346 "HARDWARE ERROR", "ILLEGAL REQUEST",
4347 "UNIT ATTENTION", "DATA PROTECT",
4348 "BLANK CHECK", "VENDOR-SPECIFIC",
4349 "COPY ABORTED", "ABORTED COMMAND",
4350 "EQUAL", "VOLUME OVERFLOW",
4351 "MISCOMPARE", "RESERVED" };
4352 unsigned char *CommandName = "UNKNOWN";
4353 switch (Command->CommandType)
4355 case DAC960_ReadCommand:
4356 case DAC960_ReadRetryCommand:
4357 CommandName = "READ";
4358 break;
4359 case DAC960_WriteCommand:
4360 case DAC960_WriteRetryCommand:
4361 CommandName = "WRITE";
4362 break;
4363 case DAC960_MonitoringCommand:
4364 case DAC960_ImmediateCommand:
4365 case DAC960_QueuedCommand:
4366 break;
4368 DAC960_Error("Error Condition %s on %s:\n", Controller,
4369 SenseErrors[Command->V2.RequestSense->SenseKey], CommandName);
4370 DAC960_Error(" /dev/rd/c%dd%d: absolute blocks %u..%u\n",
4371 Controller, Controller->ControllerNumber,
4372 Command->LogicalDriveNumber, Command->BlockNumber,
4373 Command->BlockNumber + Command->BlockCount - 1);
4378 DAC960_V2_ReportEvent prints an appropriate message when a Controller Event
4379 occurs.
4382 static void DAC960_V2_ReportEvent(DAC960_Controller_T *Controller,
4383 DAC960_V2_Event_T *Event)
4385 DAC960_SCSI_RequestSense_T *RequestSense =
4386 (DAC960_SCSI_RequestSense_T *) &Event->RequestSenseData;
4387 unsigned char MessageBuffer[DAC960_LineBufferSize];
4388 static struct { int EventCode; unsigned char *EventMessage; } EventList[] =
4389 { /* Physical Device Events (0x0000 - 0x007F) */
4390 { 0x0001, "P Online" },
4391 { 0x0002, "P Standby" },
4392 { 0x0005, "P Automatic Rebuild Started" },
4393 { 0x0006, "P Manual Rebuild Started" },
4394 { 0x0007, "P Rebuild Completed" },
4395 { 0x0008, "P Rebuild Cancelled" },
4396 { 0x0009, "P Rebuild Failed for Unknown Reasons" },
4397 { 0x000A, "P Rebuild Failed due to New Physical Device" },
4398 { 0x000B, "P Rebuild Failed due to Logical Drive Failure" },
4399 { 0x000C, "S Offline" },
4400 { 0x000D, "P Found" },
4401 { 0x000E, "P Removed" },
4402 { 0x000F, "P Unconfigured" },
4403 { 0x0010, "P Expand Capacity Started" },
4404 { 0x0011, "P Expand Capacity Completed" },
4405 { 0x0012, "P Expand Capacity Failed" },
4406 { 0x0013, "P Command Timed Out" },
4407 { 0x0014, "P Command Aborted" },
4408 { 0x0015, "P Command Retried" },
4409 { 0x0016, "P Parity Error" },
4410 { 0x0017, "P Soft Error" },
4411 { 0x0018, "P Miscellaneous Error" },
4412 { 0x0019, "P Reset" },
4413 { 0x001A, "P Active Spare Found" },
4414 { 0x001B, "P Warm Spare Found" },
4415 { 0x001C, "S Sense Data Received" },
4416 { 0x001D, "P Initialization Started" },
4417 { 0x001E, "P Initialization Completed" },
4418 { 0x001F, "P Initialization Failed" },
4419 { 0x0020, "P Initialization Cancelled" },
4420 { 0x0021, "P Failed because Write Recovery Failed" },
4421 { 0x0022, "P Failed because SCSI Bus Reset Failed" },
4422 { 0x0023, "P Failed because of Double Check Condition" },
4423 { 0x0024, "P Failed because Device Cannot Be Accessed" },
4424 { 0x0025, "P Failed because of Gross Error on SCSI Processor" },
4425 { 0x0026, "P Failed because of Bad Tag from Device" },
4426 { 0x0027, "P Failed because of Command Timeout" },
4427 { 0x0028, "P Failed because of System Reset" },
4428 { 0x0029, "P Failed because of Busy Status or Parity Error" },
4429 { 0x002A, "P Failed because Host Set Device to Failed State" },
4430 { 0x002B, "P Failed because of Selection Timeout" },
4431 { 0x002C, "P Failed because of SCSI Bus Phase Error" },
4432 { 0x002D, "P Failed because Device Returned Unknown Status" },
4433 { 0x002E, "P Failed because Device Not Ready" },
4434 { 0x002F, "P Failed because Device Not Found at Startup" },
4435 { 0x0030, "P Failed because COD Write Operation Failed" },
4436 { 0x0031, "P Failed because BDT Write Operation Failed" },
4437 { 0x0039, "P Missing at Startup" },
4438 { 0x003A, "P Start Rebuild Failed due to Physical Drive Too Small" },
4439 { 0x003C, "P Temporarily Offline Device Automatically Made Online" },
4440 { 0x003D, "P Standby Rebuild Started" },
4441 /* Logical Device Events (0x0080 - 0x00FF) */
4442 { 0x0080, "M Consistency Check Started" },
4443 { 0x0081, "M Consistency Check Completed" },
4444 { 0x0082, "M Consistency Check Cancelled" },
4445 { 0x0083, "M Consistency Check Completed With Errors" },
4446 { 0x0084, "M Consistency Check Failed due to Logical Drive Failure" },
4447 { 0x0085, "M Consistency Check Failed due to Physical Device Failure" },
4448 { 0x0086, "L Offline" },
4449 { 0x0087, "L Critical" },
4450 { 0x0088, "L Online" },
4451 { 0x0089, "M Automatic Rebuild Started" },
4452 { 0x008A, "M Manual Rebuild Started" },
4453 { 0x008B, "M Rebuild Completed" },
4454 { 0x008C, "M Rebuild Cancelled" },
4455 { 0x008D, "M Rebuild Failed for Unknown Reasons" },
4456 { 0x008E, "M Rebuild Failed due to New Physical Device" },
4457 { 0x008F, "M Rebuild Failed due to Logical Drive Failure" },
4458 { 0x0090, "M Initialization Started" },
4459 { 0x0091, "M Initialization Completed" },
4460 { 0x0092, "M Initialization Cancelled" },
4461 { 0x0093, "M Initialization Failed" },
4462 { 0x0094, "L Found" },
4463 { 0x0095, "L Deleted" },
4464 { 0x0096, "M Expand Capacity Started" },
4465 { 0x0097, "M Expand Capacity Completed" },
4466 { 0x0098, "M Expand Capacity Failed" },
4467 { 0x0099, "L Bad Block Found" },
4468 { 0x009A, "L Size Changed" },
4469 { 0x009B, "L Type Changed" },
4470 { 0x009C, "L Bad Data Block Found" },
4471 { 0x009E, "L Read of Data Block in BDT" },
4472 { 0x009F, "L Write Back Data for Disk Block Lost" },
4473 { 0x00A0, "L Temporarily Offline RAID-5/3 Drive Made Online" },
4474 { 0x00A1, "L Temporarily Offline RAID-6/1/0/7 Drive Made Online" },
4475 { 0x00A2, "L Standby Rebuild Started" },
4476 /* Fault Management Events (0x0100 - 0x017F) */
4477 { 0x0140, "E Fan %d Failed" },
4478 { 0x0141, "E Fan %d OK" },
4479 { 0x0142, "E Fan %d Not Present" },
4480 { 0x0143, "E Power Supply %d Failed" },
4481 { 0x0144, "E Power Supply %d OK" },
4482 { 0x0145, "E Power Supply %d Not Present" },
4483 { 0x0146, "E Temperature Sensor %d Temperature Exceeds Safe Limit" },
4484 { 0x0147, "E Temperature Sensor %d Temperature Exceeds Working Limit" },
4485 { 0x0148, "E Temperature Sensor %d Temperature Normal" },
4486 { 0x0149, "E Temperature Sensor %d Not Present" },
4487 { 0x014A, "E Enclosure Management Unit %d Access Critical" },
4488 { 0x014B, "E Enclosure Management Unit %d Access OK" },
4489 { 0x014C, "E Enclosure Management Unit %d Access Offline" },
4490 /* Controller Events (0x0180 - 0x01FF) */
4491 { 0x0181, "C Cache Write Back Error" },
4492 { 0x0188, "C Battery Backup Unit Found" },
4493 { 0x0189, "C Battery Backup Unit Charge Level Low" },
4494 { 0x018A, "C Battery Backup Unit Charge Level OK" },
4495 { 0x0193, "C Installation Aborted" },
4496 { 0x0195, "C Battery Backup Unit Physically Removed" },
4497 { 0x0196, "C Memory Error During Warm Boot" },
4498 { 0x019E, "C Memory Soft ECC Error Corrected" },
4499 { 0x019F, "C Memory Hard ECC Error Corrected" },
4500 { 0x01A2, "C Battery Backup Unit Failed" },
4501 { 0x01AB, "C Mirror Race Recovery Failed" },
4502 { 0x01AC, "C Mirror Race on Critical Drive" },
4503 /* Controller Internal Processor Events */
4504 { 0x0380, "C Internal Controller Hung" },
4505 { 0x0381, "C Internal Controller Firmware Breakpoint" },
4506 { 0x0390, "C Internal Controller i960 Processor Specific Error" },
4507 { 0x03A0, "C Internal Controller StrongARM Processor Specific Error" },
4508 { 0, "" } };
4509 int EventListIndex = 0, EventCode;
4510 unsigned char EventType, *EventMessage;
4511 if (Event->EventCode == 0x1C &&
4512 RequestSense->SenseKey == DAC960_SenseKey_VendorSpecific &&
4513 (RequestSense->AdditionalSenseCode == 0x80 ||
4514 RequestSense->AdditionalSenseCode == 0x81))
4515 Event->EventCode = ((RequestSense->AdditionalSenseCode - 0x80) << 8) |
4516 RequestSense->AdditionalSenseCodeQualifier;
4517 while (true)
4519 EventCode = EventList[EventListIndex].EventCode;
4520 if (EventCode == Event->EventCode || EventCode == 0) break;
4521 EventListIndex++;
4523 EventType = EventList[EventListIndex].EventMessage[0];
4524 EventMessage = &EventList[EventListIndex].EventMessage[2];
4525 if (EventCode == 0)
4527 DAC960_Critical("Unknown Controller Event Code %04X\n",
4528 Controller, Event->EventCode);
4529 return;
4531 switch (EventType)
4533 case 'P':
4534 DAC960_Critical("Physical Device %d:%d %s\n", Controller,
4535 Event->Channel, Event->TargetID, EventMessage);
4536 break;
4537 case 'L':
4538 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) %s\n", Controller,
4539 Event->LogicalUnit, Controller->ControllerNumber,
4540 Event->LogicalUnit, EventMessage);
4541 break;
4542 case 'M':
4543 DAC960_Progress("Logical Drive %d (/dev/rd/c%dd%d) %s\n", Controller,
4544 Event->LogicalUnit, Controller->ControllerNumber,
4545 Event->LogicalUnit, EventMessage);
4546 break;
4547 case 'S':
4548 if (RequestSense->SenseKey == DAC960_SenseKey_NoSense ||
4549 (RequestSense->SenseKey == DAC960_SenseKey_NotReady &&
4550 RequestSense->AdditionalSenseCode == 0x04 &&
4551 (RequestSense->AdditionalSenseCodeQualifier == 0x01 ||
4552 RequestSense->AdditionalSenseCodeQualifier == 0x02)))
4553 break;
4554 DAC960_Critical("Physical Device %d:%d %s\n", Controller,
4555 Event->Channel, Event->TargetID, EventMessage);
4556 DAC960_Critical("Physical Device %d:%d Request Sense: "
4557 "Sense Key = %X, ASC = %02X, ASCQ = %02X\n",
4558 Controller,
4559 Event->Channel,
4560 Event->TargetID,
4561 RequestSense->SenseKey,
4562 RequestSense->AdditionalSenseCode,
4563 RequestSense->AdditionalSenseCodeQualifier);
4564 DAC960_Critical("Physical Device %d:%d Request Sense: "
4565 "Information = %02X%02X%02X%02X "
4566 "%02X%02X%02X%02X\n",
4567 Controller,
4568 Event->Channel,
4569 Event->TargetID,
4570 RequestSense->Information[0],
4571 RequestSense->Information[1],
4572 RequestSense->Information[2],
4573 RequestSense->Information[3],
4574 RequestSense->CommandSpecificInformation[0],
4575 RequestSense->CommandSpecificInformation[1],
4576 RequestSense->CommandSpecificInformation[2],
4577 RequestSense->CommandSpecificInformation[3]);
4578 break;
4579 case 'E':
4580 if (Controller->SuppressEnclosureMessages) break;
4581 sprintf(MessageBuffer, EventMessage, Event->LogicalUnit);
4582 DAC960_Critical("Enclosure %d %s\n", Controller,
4583 Event->TargetID, MessageBuffer);
4584 break;
4585 case 'C':
4586 DAC960_Critical("Controller %s\n", Controller, EventMessage);
4587 break;
4588 default:
4589 DAC960_Critical("Unknown Controller Event Code %04X\n",
4590 Controller, Event->EventCode);
4591 break;
4597 DAC960_V2_ReportProgress prints an appropriate progress message for
4598 Logical Device Long Operations.
4601 static void DAC960_V2_ReportProgress(DAC960_Controller_T *Controller,
4602 unsigned char *MessageString,
4603 unsigned int LogicalDeviceNumber,
4604 unsigned long BlocksCompleted,
4605 unsigned long LogicalDeviceSize)
4607 Controller->EphemeralProgressMessage = true;
4608 DAC960_Progress("%s in Progress: Logical Drive %d (/dev/rd/c%dd%d) "
4609 "%d%% completed\n", Controller,
4610 MessageString,
4611 LogicalDeviceNumber,
4612 Controller->ControllerNumber,
4613 LogicalDeviceNumber,
4614 (100 * (BlocksCompleted >> 7)) / (LogicalDeviceSize >> 7));
4615 Controller->EphemeralProgressMessage = false;
4620 DAC960_V2_ProcessCompletedCommand performs completion processing for Command
4621 for DAC960 V2 Firmware Controllers.
4624 static void DAC960_V2_ProcessCompletedCommand(DAC960_Command_T *Command)
4626 DAC960_Controller_T *Controller = Command->Controller;
4627 DAC960_CommandType_T CommandType = Command->CommandType;
4628 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
4629 DAC960_V2_IOCTL_Opcode_T CommandOpcode = CommandMailbox->Common.IOCTL_Opcode;
4630 DAC960_V2_CommandStatus_T CommandStatus = Command->V2.CommandStatus;
4632 if (CommandType == DAC960_ReadCommand ||
4633 CommandType == DAC960_WriteCommand)
4636 #ifdef FORCE_RETRY_DEBUG
4637 CommandStatus = DAC960_V2_AbormalCompletion;
4638 #endif
4639 Command->V2.RequestSense->SenseKey = DAC960_SenseKey_MediumError;
4641 if (CommandStatus == DAC960_V2_NormalCompletion) {
4643 if (!DAC960_ProcessCompletedRequest(Command, true))
4644 BUG();
4646 } else if (Command->V2.RequestSense->SenseKey == DAC960_SenseKey_MediumError)
4649 * break the command down into pieces and resubmit each
4650 * piece, hoping that some of them will succeed.
4652 DAC960_queue_partial_rw(Command);
4653 return;
4655 else
4657 if (Command->V2.RequestSense->SenseKey != DAC960_SenseKey_NotReady)
4658 DAC960_V2_ReadWriteError(Command);
4660 Perform completion processing for all buffers in this I/O Request.
4662 (void)DAC960_ProcessCompletedRequest(Command, false);
4665 else if (CommandType == DAC960_ReadRetryCommand ||
4666 CommandType == DAC960_WriteRetryCommand)
4668 bool normal_completion;
4670 #ifdef FORCE_RETRY_FAILURE_DEBUG
4671 static int retry_count = 1;
4672 #endif
4674 Perform completion processing for the portion that was
4675 retried, and submit the next portion, if any.
4677 normal_completion = true;
4678 if (CommandStatus != DAC960_V2_NormalCompletion) {
4679 normal_completion = false;
4680 if (Command->V2.RequestSense->SenseKey != DAC960_SenseKey_NotReady)
4681 DAC960_V2_ReadWriteError(Command);
4684 #ifdef FORCE_RETRY_FAILURE_DEBUG
4685 if (!(++retry_count % 10000)) {
4686 printk("V2 error retry failure test\n");
4687 normal_completion = false;
4688 DAC960_V2_ReadWriteError(Command);
4690 #endif
4692 if (!DAC960_ProcessCompletedRequest(Command, normal_completion)) {
4693 DAC960_queue_partial_rw(Command);
4694 return;
4697 else if (CommandType == DAC960_MonitoringCommand)
4699 if (Controller->ShutdownMonitoringTimer)
4700 return;
4701 if (CommandOpcode == DAC960_V2_GetControllerInfo)
4703 DAC960_V2_ControllerInfo_T *NewControllerInfo =
4704 Controller->V2.NewControllerInformation;
4705 DAC960_V2_ControllerInfo_T *ControllerInfo =
4706 &Controller->V2.ControllerInformation;
4707 Controller->LogicalDriveCount =
4708 NewControllerInfo->LogicalDevicesPresent;
4709 Controller->V2.NeedLogicalDeviceInformation = true;
4710 Controller->V2.NeedPhysicalDeviceInformation = true;
4711 Controller->V2.StartLogicalDeviceInformationScan = true;
4712 Controller->V2.StartPhysicalDeviceInformationScan = true;
4713 Controller->MonitoringAlertMode =
4714 (NewControllerInfo->LogicalDevicesCritical > 0 ||
4715 NewControllerInfo->LogicalDevicesOffline > 0 ||
4716 NewControllerInfo->PhysicalDisksCritical > 0 ||
4717 NewControllerInfo->PhysicalDisksOffline > 0);
4718 memcpy(ControllerInfo, NewControllerInfo,
4719 sizeof(DAC960_V2_ControllerInfo_T));
4721 else if (CommandOpcode == DAC960_V2_GetEvent)
4723 if (CommandStatus == DAC960_V2_NormalCompletion) {
4724 DAC960_V2_ReportEvent(Controller, Controller->V2.Event);
4726 Controller->V2.NextEventSequenceNumber++;
4728 else if (CommandOpcode == DAC960_V2_GetPhysicalDeviceInfoValid &&
4729 CommandStatus == DAC960_V2_NormalCompletion)
4731 DAC960_V2_PhysicalDeviceInfo_T *NewPhysicalDeviceInfo =
4732 Controller->V2.NewPhysicalDeviceInformation;
4733 unsigned int PhysicalDeviceIndex = Controller->V2.PhysicalDeviceIndex;
4734 DAC960_V2_PhysicalDeviceInfo_T *PhysicalDeviceInfo =
4735 Controller->V2.PhysicalDeviceInformation[PhysicalDeviceIndex];
4736 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
4737 Controller->V2.InquiryUnitSerialNumber[PhysicalDeviceIndex];
4738 unsigned int DeviceIndex;
4739 while (PhysicalDeviceInfo != NULL &&
4740 (NewPhysicalDeviceInfo->Channel >
4741 PhysicalDeviceInfo->Channel ||
4742 (NewPhysicalDeviceInfo->Channel ==
4743 PhysicalDeviceInfo->Channel &&
4744 (NewPhysicalDeviceInfo->TargetID >
4745 PhysicalDeviceInfo->TargetID ||
4746 (NewPhysicalDeviceInfo->TargetID ==
4747 PhysicalDeviceInfo->TargetID &&
4748 NewPhysicalDeviceInfo->LogicalUnit >
4749 PhysicalDeviceInfo->LogicalUnit)))))
4751 DAC960_Critical("Physical Device %d:%d No Longer Exists\n",
4752 Controller,
4753 PhysicalDeviceInfo->Channel,
4754 PhysicalDeviceInfo->TargetID);
4755 Controller->V2.PhysicalDeviceInformation
4756 [PhysicalDeviceIndex] = NULL;
4757 Controller->V2.InquiryUnitSerialNumber
4758 [PhysicalDeviceIndex] = NULL;
4759 kfree(PhysicalDeviceInfo);
4760 kfree(InquiryUnitSerialNumber);
4761 for (DeviceIndex = PhysicalDeviceIndex;
4762 DeviceIndex < DAC960_V2_MaxPhysicalDevices - 1;
4763 DeviceIndex++)
4765 Controller->V2.PhysicalDeviceInformation[DeviceIndex] =
4766 Controller->V2.PhysicalDeviceInformation[DeviceIndex+1];
4767 Controller->V2.InquiryUnitSerialNumber[DeviceIndex] =
4768 Controller->V2.InquiryUnitSerialNumber[DeviceIndex+1];
4770 Controller->V2.PhysicalDeviceInformation
4771 [DAC960_V2_MaxPhysicalDevices-1] = NULL;
4772 Controller->V2.InquiryUnitSerialNumber
4773 [DAC960_V2_MaxPhysicalDevices-1] = NULL;
4774 PhysicalDeviceInfo =
4775 Controller->V2.PhysicalDeviceInformation[PhysicalDeviceIndex];
4776 InquiryUnitSerialNumber =
4777 Controller->V2.InquiryUnitSerialNumber[PhysicalDeviceIndex];
4779 if (PhysicalDeviceInfo == NULL ||
4780 (NewPhysicalDeviceInfo->Channel !=
4781 PhysicalDeviceInfo->Channel) ||
4782 (NewPhysicalDeviceInfo->TargetID !=
4783 PhysicalDeviceInfo->TargetID) ||
4784 (NewPhysicalDeviceInfo->LogicalUnit !=
4785 PhysicalDeviceInfo->LogicalUnit))
4787 PhysicalDeviceInfo =
4788 kmalloc(sizeof(DAC960_V2_PhysicalDeviceInfo_T), GFP_ATOMIC);
4789 InquiryUnitSerialNumber =
4790 kmalloc(sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T),
4791 GFP_ATOMIC);
4792 if (InquiryUnitSerialNumber == NULL ||
4793 PhysicalDeviceInfo == NULL)
4795 kfree(InquiryUnitSerialNumber);
4796 InquiryUnitSerialNumber = NULL;
4797 kfree(PhysicalDeviceInfo);
4798 PhysicalDeviceInfo = NULL;
4800 DAC960_Critical("Physical Device %d:%d Now Exists%s\n",
4801 Controller,
4802 NewPhysicalDeviceInfo->Channel,
4803 NewPhysicalDeviceInfo->TargetID,
4804 (PhysicalDeviceInfo != NULL
4805 ? "" : " - Allocation Failed"));
4806 if (PhysicalDeviceInfo != NULL)
4808 memset(PhysicalDeviceInfo, 0,
4809 sizeof(DAC960_V2_PhysicalDeviceInfo_T));
4810 PhysicalDeviceInfo->PhysicalDeviceState =
4811 DAC960_V2_Device_InvalidState;
4812 memset(InquiryUnitSerialNumber, 0,
4813 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
4814 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
4815 for (DeviceIndex = DAC960_V2_MaxPhysicalDevices - 1;
4816 DeviceIndex > PhysicalDeviceIndex;
4817 DeviceIndex--)
4819 Controller->V2.PhysicalDeviceInformation[DeviceIndex] =
4820 Controller->V2.PhysicalDeviceInformation[DeviceIndex-1];
4821 Controller->V2.InquiryUnitSerialNumber[DeviceIndex] =
4822 Controller->V2.InquiryUnitSerialNumber[DeviceIndex-1];
4824 Controller->V2.PhysicalDeviceInformation
4825 [PhysicalDeviceIndex] =
4826 PhysicalDeviceInfo;
4827 Controller->V2.InquiryUnitSerialNumber
4828 [PhysicalDeviceIndex] =
4829 InquiryUnitSerialNumber;
4830 Controller->V2.NeedDeviceSerialNumberInformation = true;
4833 if (PhysicalDeviceInfo != NULL)
4835 if (NewPhysicalDeviceInfo->PhysicalDeviceState !=
4836 PhysicalDeviceInfo->PhysicalDeviceState)
4837 DAC960_Critical(
4838 "Physical Device %d:%d is now %s\n", Controller,
4839 NewPhysicalDeviceInfo->Channel,
4840 NewPhysicalDeviceInfo->TargetID,
4841 (NewPhysicalDeviceInfo->PhysicalDeviceState
4842 == DAC960_V2_Device_Online
4843 ? "ONLINE"
4844 : NewPhysicalDeviceInfo->PhysicalDeviceState
4845 == DAC960_V2_Device_Rebuild
4846 ? "REBUILD"
4847 : NewPhysicalDeviceInfo->PhysicalDeviceState
4848 == DAC960_V2_Device_Missing
4849 ? "MISSING"
4850 : NewPhysicalDeviceInfo->PhysicalDeviceState
4851 == DAC960_V2_Device_Critical
4852 ? "CRITICAL"
4853 : NewPhysicalDeviceInfo->PhysicalDeviceState
4854 == DAC960_V2_Device_Dead
4855 ? "DEAD"
4856 : NewPhysicalDeviceInfo->PhysicalDeviceState
4857 == DAC960_V2_Device_SuspectedDead
4858 ? "SUSPECTED-DEAD"
4859 : NewPhysicalDeviceInfo->PhysicalDeviceState
4860 == DAC960_V2_Device_CommandedOffline
4861 ? "COMMANDED-OFFLINE"
4862 : NewPhysicalDeviceInfo->PhysicalDeviceState
4863 == DAC960_V2_Device_Standby
4864 ? "STANDBY" : "UNKNOWN"));
4865 if ((NewPhysicalDeviceInfo->ParityErrors !=
4866 PhysicalDeviceInfo->ParityErrors) ||
4867 (NewPhysicalDeviceInfo->SoftErrors !=
4868 PhysicalDeviceInfo->SoftErrors) ||
4869 (NewPhysicalDeviceInfo->HardErrors !=
4870 PhysicalDeviceInfo->HardErrors) ||
4871 (NewPhysicalDeviceInfo->MiscellaneousErrors !=
4872 PhysicalDeviceInfo->MiscellaneousErrors) ||
4873 (NewPhysicalDeviceInfo->CommandTimeouts !=
4874 PhysicalDeviceInfo->CommandTimeouts) ||
4875 (NewPhysicalDeviceInfo->Retries !=
4876 PhysicalDeviceInfo->Retries) ||
4877 (NewPhysicalDeviceInfo->Aborts !=
4878 PhysicalDeviceInfo->Aborts) ||
4879 (NewPhysicalDeviceInfo->PredictedFailuresDetected !=
4880 PhysicalDeviceInfo->PredictedFailuresDetected))
4882 DAC960_Critical("Physical Device %d:%d Errors: "
4883 "Parity = %d, Soft = %d, "
4884 "Hard = %d, Misc = %d\n",
4885 Controller,
4886 NewPhysicalDeviceInfo->Channel,
4887 NewPhysicalDeviceInfo->TargetID,
4888 NewPhysicalDeviceInfo->ParityErrors,
4889 NewPhysicalDeviceInfo->SoftErrors,
4890 NewPhysicalDeviceInfo->HardErrors,
4891 NewPhysicalDeviceInfo->MiscellaneousErrors);
4892 DAC960_Critical("Physical Device %d:%d Errors: "
4893 "Timeouts = %d, Retries = %d, "
4894 "Aborts = %d, Predicted = %d\n",
4895 Controller,
4896 NewPhysicalDeviceInfo->Channel,
4897 NewPhysicalDeviceInfo->TargetID,
4898 NewPhysicalDeviceInfo->CommandTimeouts,
4899 NewPhysicalDeviceInfo->Retries,
4900 NewPhysicalDeviceInfo->Aborts,
4901 NewPhysicalDeviceInfo
4902 ->PredictedFailuresDetected);
4904 if ((PhysicalDeviceInfo->PhysicalDeviceState
4905 == DAC960_V2_Device_Dead ||
4906 PhysicalDeviceInfo->PhysicalDeviceState
4907 == DAC960_V2_Device_InvalidState) &&
4908 NewPhysicalDeviceInfo->PhysicalDeviceState
4909 != DAC960_V2_Device_Dead)
4910 Controller->V2.NeedDeviceSerialNumberInformation = true;
4911 memcpy(PhysicalDeviceInfo, NewPhysicalDeviceInfo,
4912 sizeof(DAC960_V2_PhysicalDeviceInfo_T));
4914 NewPhysicalDeviceInfo->LogicalUnit++;
4915 Controller->V2.PhysicalDeviceIndex++;
4917 else if (CommandOpcode == DAC960_V2_GetPhysicalDeviceInfoValid)
4919 unsigned int DeviceIndex;
4920 for (DeviceIndex = Controller->V2.PhysicalDeviceIndex;
4921 DeviceIndex < DAC960_V2_MaxPhysicalDevices;
4922 DeviceIndex++)
4924 DAC960_V2_PhysicalDeviceInfo_T *PhysicalDeviceInfo =
4925 Controller->V2.PhysicalDeviceInformation[DeviceIndex];
4926 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
4927 Controller->V2.InquiryUnitSerialNumber[DeviceIndex];
4928 if (PhysicalDeviceInfo == NULL) break;
4929 DAC960_Critical("Physical Device %d:%d No Longer Exists\n",
4930 Controller,
4931 PhysicalDeviceInfo->Channel,
4932 PhysicalDeviceInfo->TargetID);
4933 Controller->V2.PhysicalDeviceInformation[DeviceIndex] = NULL;
4934 Controller->V2.InquiryUnitSerialNumber[DeviceIndex] = NULL;
4935 kfree(PhysicalDeviceInfo);
4936 kfree(InquiryUnitSerialNumber);
4938 Controller->V2.NeedPhysicalDeviceInformation = false;
4940 else if (CommandOpcode == DAC960_V2_GetLogicalDeviceInfoValid &&
4941 CommandStatus == DAC960_V2_NormalCompletion)
4943 DAC960_V2_LogicalDeviceInfo_T *NewLogicalDeviceInfo =
4944 Controller->V2.NewLogicalDeviceInformation;
4945 unsigned short LogicalDeviceNumber =
4946 NewLogicalDeviceInfo->LogicalDeviceNumber;
4947 DAC960_V2_LogicalDeviceInfo_T *LogicalDeviceInfo =
4948 Controller->V2.LogicalDeviceInformation[LogicalDeviceNumber];
4949 if (LogicalDeviceInfo == NULL)
4951 DAC960_V2_PhysicalDevice_T PhysicalDevice;
4952 PhysicalDevice.Controller = 0;
4953 PhysicalDevice.Channel = NewLogicalDeviceInfo->Channel;
4954 PhysicalDevice.TargetID = NewLogicalDeviceInfo->TargetID;
4955 PhysicalDevice.LogicalUnit = NewLogicalDeviceInfo->LogicalUnit;
4956 Controller->V2.LogicalDriveToVirtualDevice[LogicalDeviceNumber] =
4957 PhysicalDevice;
4958 LogicalDeviceInfo = kmalloc(sizeof(DAC960_V2_LogicalDeviceInfo_T),
4959 GFP_ATOMIC);
4960 Controller->V2.LogicalDeviceInformation[LogicalDeviceNumber] =
4961 LogicalDeviceInfo;
4962 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
4963 "Now Exists%s\n", Controller,
4964 LogicalDeviceNumber,
4965 Controller->ControllerNumber,
4966 LogicalDeviceNumber,
4967 (LogicalDeviceInfo != NULL
4968 ? "" : " - Allocation Failed"));
4969 if (LogicalDeviceInfo != NULL)
4971 memset(LogicalDeviceInfo, 0,
4972 sizeof(DAC960_V2_LogicalDeviceInfo_T));
4973 DAC960_ComputeGenericDiskInfo(Controller);
4976 if (LogicalDeviceInfo != NULL)
4978 unsigned long LogicalDeviceSize =
4979 NewLogicalDeviceInfo->ConfigurableDeviceSize;
4980 if (NewLogicalDeviceInfo->LogicalDeviceState !=
4981 LogicalDeviceInfo->LogicalDeviceState)
4982 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
4983 "is now %s\n", Controller,
4984 LogicalDeviceNumber,
4985 Controller->ControllerNumber,
4986 LogicalDeviceNumber,
4987 (NewLogicalDeviceInfo->LogicalDeviceState
4988 == DAC960_V2_LogicalDevice_Online
4989 ? "ONLINE"
4990 : NewLogicalDeviceInfo->LogicalDeviceState
4991 == DAC960_V2_LogicalDevice_Critical
4992 ? "CRITICAL" : "OFFLINE"));
4993 if ((NewLogicalDeviceInfo->SoftErrors !=
4994 LogicalDeviceInfo->SoftErrors) ||
4995 (NewLogicalDeviceInfo->CommandsFailed !=
4996 LogicalDeviceInfo->CommandsFailed) ||
4997 (NewLogicalDeviceInfo->DeferredWriteErrors !=
4998 LogicalDeviceInfo->DeferredWriteErrors))
4999 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) Errors: "
5000 "Soft = %d, Failed = %d, Deferred Write = %d\n",
5001 Controller, LogicalDeviceNumber,
5002 Controller->ControllerNumber,
5003 LogicalDeviceNumber,
5004 NewLogicalDeviceInfo->SoftErrors,
5005 NewLogicalDeviceInfo->CommandsFailed,
5006 NewLogicalDeviceInfo->DeferredWriteErrors);
5007 if (NewLogicalDeviceInfo->ConsistencyCheckInProgress)
5008 DAC960_V2_ReportProgress(Controller,
5009 "Consistency Check",
5010 LogicalDeviceNumber,
5011 NewLogicalDeviceInfo
5012 ->ConsistencyCheckBlockNumber,
5013 LogicalDeviceSize);
5014 else if (NewLogicalDeviceInfo->RebuildInProgress)
5015 DAC960_V2_ReportProgress(Controller,
5016 "Rebuild",
5017 LogicalDeviceNumber,
5018 NewLogicalDeviceInfo
5019 ->RebuildBlockNumber,
5020 LogicalDeviceSize);
5021 else if (NewLogicalDeviceInfo->BackgroundInitializationInProgress)
5022 DAC960_V2_ReportProgress(Controller,
5023 "Background Initialization",
5024 LogicalDeviceNumber,
5025 NewLogicalDeviceInfo
5026 ->BackgroundInitializationBlockNumber,
5027 LogicalDeviceSize);
5028 else if (NewLogicalDeviceInfo->ForegroundInitializationInProgress)
5029 DAC960_V2_ReportProgress(Controller,
5030 "Foreground Initialization",
5031 LogicalDeviceNumber,
5032 NewLogicalDeviceInfo
5033 ->ForegroundInitializationBlockNumber,
5034 LogicalDeviceSize);
5035 else if (NewLogicalDeviceInfo->DataMigrationInProgress)
5036 DAC960_V2_ReportProgress(Controller,
5037 "Data Migration",
5038 LogicalDeviceNumber,
5039 NewLogicalDeviceInfo
5040 ->DataMigrationBlockNumber,
5041 LogicalDeviceSize);
5042 else if (NewLogicalDeviceInfo->PatrolOperationInProgress)
5043 DAC960_V2_ReportProgress(Controller,
5044 "Patrol Operation",
5045 LogicalDeviceNumber,
5046 NewLogicalDeviceInfo
5047 ->PatrolOperationBlockNumber,
5048 LogicalDeviceSize);
5049 if (LogicalDeviceInfo->BackgroundInitializationInProgress &&
5050 !NewLogicalDeviceInfo->BackgroundInitializationInProgress)
5051 DAC960_Progress("Logical Drive %d (/dev/rd/c%dd%d) "
5052 "Background Initialization %s\n",
5053 Controller,
5054 LogicalDeviceNumber,
5055 Controller->ControllerNumber,
5056 LogicalDeviceNumber,
5057 (NewLogicalDeviceInfo->LogicalDeviceControl
5058 .LogicalDeviceInitialized
5059 ? "Completed" : "Failed"));
5060 memcpy(LogicalDeviceInfo, NewLogicalDeviceInfo,
5061 sizeof(DAC960_V2_LogicalDeviceInfo_T));
5063 Controller->V2.LogicalDriveFoundDuringScan
5064 [LogicalDeviceNumber] = true;
5065 NewLogicalDeviceInfo->LogicalDeviceNumber++;
5067 else if (CommandOpcode == DAC960_V2_GetLogicalDeviceInfoValid)
5069 int LogicalDriveNumber;
5070 for (LogicalDriveNumber = 0;
5071 LogicalDriveNumber < DAC960_MaxLogicalDrives;
5072 LogicalDriveNumber++)
5074 DAC960_V2_LogicalDeviceInfo_T *LogicalDeviceInfo =
5075 Controller->V2.LogicalDeviceInformation[LogicalDriveNumber];
5076 if (LogicalDeviceInfo == NULL ||
5077 Controller->V2.LogicalDriveFoundDuringScan
5078 [LogicalDriveNumber])
5079 continue;
5080 DAC960_Critical("Logical Drive %d (/dev/rd/c%dd%d) "
5081 "No Longer Exists\n", Controller,
5082 LogicalDriveNumber,
5083 Controller->ControllerNumber,
5084 LogicalDriveNumber);
5085 Controller->V2.LogicalDeviceInformation
5086 [LogicalDriveNumber] = NULL;
5087 kfree(LogicalDeviceInfo);
5088 Controller->LogicalDriveInitiallyAccessible
5089 [LogicalDriveNumber] = false;
5090 DAC960_ComputeGenericDiskInfo(Controller);
5092 Controller->V2.NeedLogicalDeviceInformation = false;
5094 else if (CommandOpcode == DAC960_V2_SCSI_10_Passthru)
5096 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
5097 Controller->V2.InquiryUnitSerialNumber[Controller->V2.PhysicalDeviceIndex - 1];
5099 if (CommandStatus != DAC960_V2_NormalCompletion) {
5100 memset(InquiryUnitSerialNumber,
5101 0, sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
5102 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
5103 } else
5104 memcpy(InquiryUnitSerialNumber,
5105 Controller->V2.NewInquiryUnitSerialNumber,
5106 sizeof(DAC960_SCSI_Inquiry_UnitSerialNumber_T));
5108 Controller->V2.NeedDeviceSerialNumberInformation = false;
5111 if (Controller->V2.HealthStatusBuffer->NextEventSequenceNumber
5112 - Controller->V2.NextEventSequenceNumber > 0)
5114 CommandMailbox->GetEvent.CommandOpcode = DAC960_V2_IOCTL;
5115 CommandMailbox->GetEvent.DataTransferSize = sizeof(DAC960_V2_Event_T);
5116 CommandMailbox->GetEvent.EventSequenceNumberHigh16 =
5117 Controller->V2.NextEventSequenceNumber >> 16;
5118 CommandMailbox->GetEvent.ControllerNumber = 0;
5119 CommandMailbox->GetEvent.IOCTL_Opcode =
5120 DAC960_V2_GetEvent;
5121 CommandMailbox->GetEvent.EventSequenceNumberLow16 =
5122 Controller->V2.NextEventSequenceNumber & 0xFFFF;
5123 CommandMailbox->GetEvent.DataTransferMemoryAddress
5124 .ScatterGatherSegments[0]
5125 .SegmentDataPointer =
5126 Controller->V2.EventDMA;
5127 CommandMailbox->GetEvent.DataTransferMemoryAddress
5128 .ScatterGatherSegments[0]
5129 .SegmentByteCount =
5130 CommandMailbox->GetEvent.DataTransferSize;
5131 DAC960_QueueCommand(Command);
5132 return;
5134 if (Controller->V2.NeedPhysicalDeviceInformation)
5136 if (Controller->V2.NeedDeviceSerialNumberInformation)
5138 DAC960_SCSI_Inquiry_UnitSerialNumber_T *InquiryUnitSerialNumber =
5139 Controller->V2.NewInquiryUnitSerialNumber;
5140 InquiryUnitSerialNumber->PeripheralDeviceType = 0x1F;
5142 DAC960_V2_ConstructNewUnitSerialNumber(Controller, CommandMailbox,
5143 Controller->V2.NewPhysicalDeviceInformation->Channel,
5144 Controller->V2.NewPhysicalDeviceInformation->TargetID,
5145 Controller->V2.NewPhysicalDeviceInformation->LogicalUnit - 1);
5148 DAC960_QueueCommand(Command);
5149 return;
5151 if (Controller->V2.StartPhysicalDeviceInformationScan)
5153 Controller->V2.PhysicalDeviceIndex = 0;
5154 Controller->V2.NewPhysicalDeviceInformation->Channel = 0;
5155 Controller->V2.NewPhysicalDeviceInformation->TargetID = 0;
5156 Controller->V2.NewPhysicalDeviceInformation->LogicalUnit = 0;
5157 Controller->V2.StartPhysicalDeviceInformationScan = false;
5159 CommandMailbox->PhysicalDeviceInfo.CommandOpcode = DAC960_V2_IOCTL;
5160 CommandMailbox->PhysicalDeviceInfo.DataTransferSize =
5161 sizeof(DAC960_V2_PhysicalDeviceInfo_T);
5162 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.LogicalUnit =
5163 Controller->V2.NewPhysicalDeviceInformation->LogicalUnit;
5164 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.TargetID =
5165 Controller->V2.NewPhysicalDeviceInformation->TargetID;
5166 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.Channel =
5167 Controller->V2.NewPhysicalDeviceInformation->Channel;
5168 CommandMailbox->PhysicalDeviceInfo.IOCTL_Opcode =
5169 DAC960_V2_GetPhysicalDeviceInfoValid;
5170 CommandMailbox->PhysicalDeviceInfo.DataTransferMemoryAddress
5171 .ScatterGatherSegments[0]
5172 .SegmentDataPointer =
5173 Controller->V2.NewPhysicalDeviceInformationDMA;
5174 CommandMailbox->PhysicalDeviceInfo.DataTransferMemoryAddress
5175 .ScatterGatherSegments[0]
5176 .SegmentByteCount =
5177 CommandMailbox->PhysicalDeviceInfo.DataTransferSize;
5178 DAC960_QueueCommand(Command);
5179 return;
5181 if (Controller->V2.NeedLogicalDeviceInformation)
5183 if (Controller->V2.StartLogicalDeviceInformationScan)
5185 int LogicalDriveNumber;
5186 for (LogicalDriveNumber = 0;
5187 LogicalDriveNumber < DAC960_MaxLogicalDrives;
5188 LogicalDriveNumber++)
5189 Controller->V2.LogicalDriveFoundDuringScan
5190 [LogicalDriveNumber] = false;
5191 Controller->V2.NewLogicalDeviceInformation->LogicalDeviceNumber = 0;
5192 Controller->V2.StartLogicalDeviceInformationScan = false;
5194 CommandMailbox->LogicalDeviceInfo.CommandOpcode = DAC960_V2_IOCTL;
5195 CommandMailbox->LogicalDeviceInfo.DataTransferSize =
5196 sizeof(DAC960_V2_LogicalDeviceInfo_T);
5197 CommandMailbox->LogicalDeviceInfo.LogicalDevice.LogicalDeviceNumber =
5198 Controller->V2.NewLogicalDeviceInformation->LogicalDeviceNumber;
5199 CommandMailbox->LogicalDeviceInfo.IOCTL_Opcode =
5200 DAC960_V2_GetLogicalDeviceInfoValid;
5201 CommandMailbox->LogicalDeviceInfo.DataTransferMemoryAddress
5202 .ScatterGatherSegments[0]
5203 .SegmentDataPointer =
5204 Controller->V2.NewLogicalDeviceInformationDMA;
5205 CommandMailbox->LogicalDeviceInfo.DataTransferMemoryAddress
5206 .ScatterGatherSegments[0]
5207 .SegmentByteCount =
5208 CommandMailbox->LogicalDeviceInfo.DataTransferSize;
5209 DAC960_QueueCommand(Command);
5210 return;
5212 Controller->MonitoringTimerCount++;
5213 Controller->MonitoringTimer.expires =
5214 jiffies + DAC960_HealthStatusMonitoringInterval;
5215 add_timer(&Controller->MonitoringTimer);
5217 if (CommandType == DAC960_ImmediateCommand)
5219 complete(Command->Completion);
5220 Command->Completion = NULL;
5221 return;
5223 if (CommandType == DAC960_QueuedCommand)
5225 DAC960_V2_KernelCommand_T *KernelCommand = Command->V2.KernelCommand;
5226 KernelCommand->CommandStatus = CommandStatus;
5227 KernelCommand->RequestSenseLength = Command->V2.RequestSenseLength;
5228 KernelCommand->DataTransferLength = Command->V2.DataTransferResidue;
5229 Command->V2.KernelCommand = NULL;
5230 DAC960_DeallocateCommand(Command);
5231 KernelCommand->CompletionFunction(KernelCommand);
5232 return;
5235 Queue a Status Monitoring Command to the Controller using the just
5236 completed Command if one was deferred previously due to lack of a
5237 free Command when the Monitoring Timer Function was called.
5239 if (Controller->MonitoringCommandDeferred)
5241 Controller->MonitoringCommandDeferred = false;
5242 DAC960_V2_QueueMonitoringCommand(Command);
5243 return;
5246 Deallocate the Command.
5248 DAC960_DeallocateCommand(Command);
5250 Wake up any processes waiting on a free Command.
5252 wake_up(&Controller->CommandWaitQueue);
5256 DAC960_GEM_InterruptHandler handles hardware interrupts from DAC960 GEM Series
5257 Controllers.
5260 static irqreturn_t DAC960_GEM_InterruptHandler(int IRQ_Channel,
5261 void *DeviceIdentifier)
5263 DAC960_Controller_T *Controller = DeviceIdentifier;
5264 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5265 DAC960_V2_StatusMailbox_T *NextStatusMailbox;
5266 unsigned long flags;
5268 spin_lock_irqsave(&Controller->queue_lock, flags);
5269 DAC960_GEM_AcknowledgeInterrupt(ControllerBaseAddress);
5270 NextStatusMailbox = Controller->V2.NextStatusMailbox;
5271 while (NextStatusMailbox->Fields.CommandIdentifier > 0)
5273 DAC960_V2_CommandIdentifier_T CommandIdentifier =
5274 NextStatusMailbox->Fields.CommandIdentifier;
5275 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5276 Command->V2.CommandStatus = NextStatusMailbox->Fields.CommandStatus;
5277 Command->V2.RequestSenseLength =
5278 NextStatusMailbox->Fields.RequestSenseLength;
5279 Command->V2.DataTransferResidue =
5280 NextStatusMailbox->Fields.DataTransferResidue;
5281 NextStatusMailbox->Words[0] = 0;
5282 if (++NextStatusMailbox > Controller->V2.LastStatusMailbox)
5283 NextStatusMailbox = Controller->V2.FirstStatusMailbox;
5284 DAC960_V2_ProcessCompletedCommand(Command);
5286 Controller->V2.NextStatusMailbox = NextStatusMailbox;
5288 Attempt to remove additional I/O Requests from the Controller's
5289 I/O Request Queue and queue them to the Controller.
5291 DAC960_ProcessRequest(Controller);
5292 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5293 return IRQ_HANDLED;
5297 DAC960_BA_InterruptHandler handles hardware interrupts from DAC960 BA Series
5298 Controllers.
5301 static irqreturn_t DAC960_BA_InterruptHandler(int IRQ_Channel,
5302 void *DeviceIdentifier)
5304 DAC960_Controller_T *Controller = DeviceIdentifier;
5305 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5306 DAC960_V2_StatusMailbox_T *NextStatusMailbox;
5307 unsigned long flags;
5309 spin_lock_irqsave(&Controller->queue_lock, flags);
5310 DAC960_BA_AcknowledgeInterrupt(ControllerBaseAddress);
5311 NextStatusMailbox = Controller->V2.NextStatusMailbox;
5312 while (NextStatusMailbox->Fields.CommandIdentifier > 0)
5314 DAC960_V2_CommandIdentifier_T CommandIdentifier =
5315 NextStatusMailbox->Fields.CommandIdentifier;
5316 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5317 Command->V2.CommandStatus = NextStatusMailbox->Fields.CommandStatus;
5318 Command->V2.RequestSenseLength =
5319 NextStatusMailbox->Fields.RequestSenseLength;
5320 Command->V2.DataTransferResidue =
5321 NextStatusMailbox->Fields.DataTransferResidue;
5322 NextStatusMailbox->Words[0] = 0;
5323 if (++NextStatusMailbox > Controller->V2.LastStatusMailbox)
5324 NextStatusMailbox = Controller->V2.FirstStatusMailbox;
5325 DAC960_V2_ProcessCompletedCommand(Command);
5327 Controller->V2.NextStatusMailbox = NextStatusMailbox;
5329 Attempt to remove additional I/O Requests from the Controller's
5330 I/O Request Queue and queue them to the Controller.
5332 DAC960_ProcessRequest(Controller);
5333 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5334 return IRQ_HANDLED;
5339 DAC960_LP_InterruptHandler handles hardware interrupts from DAC960 LP Series
5340 Controllers.
5343 static irqreturn_t DAC960_LP_InterruptHandler(int IRQ_Channel,
5344 void *DeviceIdentifier)
5346 DAC960_Controller_T *Controller = DeviceIdentifier;
5347 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5348 DAC960_V2_StatusMailbox_T *NextStatusMailbox;
5349 unsigned long flags;
5351 spin_lock_irqsave(&Controller->queue_lock, flags);
5352 DAC960_LP_AcknowledgeInterrupt(ControllerBaseAddress);
5353 NextStatusMailbox = Controller->V2.NextStatusMailbox;
5354 while (NextStatusMailbox->Fields.CommandIdentifier > 0)
5356 DAC960_V2_CommandIdentifier_T CommandIdentifier =
5357 NextStatusMailbox->Fields.CommandIdentifier;
5358 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5359 Command->V2.CommandStatus = NextStatusMailbox->Fields.CommandStatus;
5360 Command->V2.RequestSenseLength =
5361 NextStatusMailbox->Fields.RequestSenseLength;
5362 Command->V2.DataTransferResidue =
5363 NextStatusMailbox->Fields.DataTransferResidue;
5364 NextStatusMailbox->Words[0] = 0;
5365 if (++NextStatusMailbox > Controller->V2.LastStatusMailbox)
5366 NextStatusMailbox = Controller->V2.FirstStatusMailbox;
5367 DAC960_V2_ProcessCompletedCommand(Command);
5369 Controller->V2.NextStatusMailbox = NextStatusMailbox;
5371 Attempt to remove additional I/O Requests from the Controller's
5372 I/O Request Queue and queue them to the Controller.
5374 DAC960_ProcessRequest(Controller);
5375 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5376 return IRQ_HANDLED;
5381 DAC960_LA_InterruptHandler handles hardware interrupts from DAC960 LA Series
5382 Controllers.
5385 static irqreturn_t DAC960_LA_InterruptHandler(int IRQ_Channel,
5386 void *DeviceIdentifier)
5388 DAC960_Controller_T *Controller = DeviceIdentifier;
5389 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5390 DAC960_V1_StatusMailbox_T *NextStatusMailbox;
5391 unsigned long flags;
5393 spin_lock_irqsave(&Controller->queue_lock, flags);
5394 DAC960_LA_AcknowledgeInterrupt(ControllerBaseAddress);
5395 NextStatusMailbox = Controller->V1.NextStatusMailbox;
5396 while (NextStatusMailbox->Fields.Valid)
5398 DAC960_V1_CommandIdentifier_T CommandIdentifier =
5399 NextStatusMailbox->Fields.CommandIdentifier;
5400 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5401 Command->V1.CommandStatus = NextStatusMailbox->Fields.CommandStatus;
5402 NextStatusMailbox->Word = 0;
5403 if (++NextStatusMailbox > Controller->V1.LastStatusMailbox)
5404 NextStatusMailbox = Controller->V1.FirstStatusMailbox;
5405 DAC960_V1_ProcessCompletedCommand(Command);
5407 Controller->V1.NextStatusMailbox = NextStatusMailbox;
5409 Attempt to remove additional I/O Requests from the Controller's
5410 I/O Request Queue and queue them to the Controller.
5412 DAC960_ProcessRequest(Controller);
5413 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5414 return IRQ_HANDLED;
5419 DAC960_PG_InterruptHandler handles hardware interrupts from DAC960 PG Series
5420 Controllers.
5423 static irqreturn_t DAC960_PG_InterruptHandler(int IRQ_Channel,
5424 void *DeviceIdentifier)
5426 DAC960_Controller_T *Controller = DeviceIdentifier;
5427 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5428 DAC960_V1_StatusMailbox_T *NextStatusMailbox;
5429 unsigned long flags;
5431 spin_lock_irqsave(&Controller->queue_lock, flags);
5432 DAC960_PG_AcknowledgeInterrupt(ControllerBaseAddress);
5433 NextStatusMailbox = Controller->V1.NextStatusMailbox;
5434 while (NextStatusMailbox->Fields.Valid)
5436 DAC960_V1_CommandIdentifier_T CommandIdentifier =
5437 NextStatusMailbox->Fields.CommandIdentifier;
5438 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5439 Command->V1.CommandStatus = NextStatusMailbox->Fields.CommandStatus;
5440 NextStatusMailbox->Word = 0;
5441 if (++NextStatusMailbox > Controller->V1.LastStatusMailbox)
5442 NextStatusMailbox = Controller->V1.FirstStatusMailbox;
5443 DAC960_V1_ProcessCompletedCommand(Command);
5445 Controller->V1.NextStatusMailbox = NextStatusMailbox;
5447 Attempt to remove additional I/O Requests from the Controller's
5448 I/O Request Queue and queue them to the Controller.
5450 DAC960_ProcessRequest(Controller);
5451 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5452 return IRQ_HANDLED;
5457 DAC960_PD_InterruptHandler handles hardware interrupts from DAC960 PD Series
5458 Controllers.
5461 static irqreturn_t DAC960_PD_InterruptHandler(int IRQ_Channel,
5462 void *DeviceIdentifier)
5464 DAC960_Controller_T *Controller = DeviceIdentifier;
5465 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5466 unsigned long flags;
5468 spin_lock_irqsave(&Controller->queue_lock, flags);
5469 while (DAC960_PD_StatusAvailableP(ControllerBaseAddress))
5471 DAC960_V1_CommandIdentifier_T CommandIdentifier =
5472 DAC960_PD_ReadStatusCommandIdentifier(ControllerBaseAddress);
5473 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5474 Command->V1.CommandStatus =
5475 DAC960_PD_ReadStatusRegister(ControllerBaseAddress);
5476 DAC960_PD_AcknowledgeInterrupt(ControllerBaseAddress);
5477 DAC960_PD_AcknowledgeStatus(ControllerBaseAddress);
5478 DAC960_V1_ProcessCompletedCommand(Command);
5481 Attempt to remove additional I/O Requests from the Controller's
5482 I/O Request Queue and queue them to the Controller.
5484 DAC960_ProcessRequest(Controller);
5485 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5486 return IRQ_HANDLED;
5491 DAC960_P_InterruptHandler handles hardware interrupts from DAC960 P Series
5492 Controllers.
5494 Translations of DAC960_V1_Enquiry and DAC960_V1_GetDeviceState rely
5495 on the data having been placed into DAC960_Controller_T, rather than
5496 an arbitrary buffer.
5499 static irqreturn_t DAC960_P_InterruptHandler(int IRQ_Channel,
5500 void *DeviceIdentifier)
5502 DAC960_Controller_T *Controller = DeviceIdentifier;
5503 void __iomem *ControllerBaseAddress = Controller->BaseAddress;
5504 unsigned long flags;
5506 spin_lock_irqsave(&Controller->queue_lock, flags);
5507 while (DAC960_PD_StatusAvailableP(ControllerBaseAddress))
5509 DAC960_V1_CommandIdentifier_T CommandIdentifier =
5510 DAC960_PD_ReadStatusCommandIdentifier(ControllerBaseAddress);
5511 DAC960_Command_T *Command = Controller->Commands[CommandIdentifier-1];
5512 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
5513 DAC960_V1_CommandOpcode_T CommandOpcode =
5514 CommandMailbox->Common.CommandOpcode;
5515 Command->V1.CommandStatus =
5516 DAC960_PD_ReadStatusRegister(ControllerBaseAddress);
5517 DAC960_PD_AcknowledgeInterrupt(ControllerBaseAddress);
5518 DAC960_PD_AcknowledgeStatus(ControllerBaseAddress);
5519 switch (CommandOpcode)
5521 case DAC960_V1_Enquiry_Old:
5522 Command->V1.CommandMailbox.Common.CommandOpcode = DAC960_V1_Enquiry;
5523 DAC960_P_To_PD_TranslateEnquiry(Controller->V1.NewEnquiry);
5524 break;
5525 case DAC960_V1_GetDeviceState_Old:
5526 Command->V1.CommandMailbox.Common.CommandOpcode =
5527 DAC960_V1_GetDeviceState;
5528 DAC960_P_To_PD_TranslateDeviceState(Controller->V1.NewDeviceState);
5529 break;
5530 case DAC960_V1_Read_Old:
5531 Command->V1.CommandMailbox.Common.CommandOpcode = DAC960_V1_Read;
5532 DAC960_P_To_PD_TranslateReadWriteCommand(CommandMailbox);
5533 break;
5534 case DAC960_V1_Write_Old:
5535 Command->V1.CommandMailbox.Common.CommandOpcode = DAC960_V1_Write;
5536 DAC960_P_To_PD_TranslateReadWriteCommand(CommandMailbox);
5537 break;
5538 case DAC960_V1_ReadWithScatterGather_Old:
5539 Command->V1.CommandMailbox.Common.CommandOpcode =
5540 DAC960_V1_ReadWithScatterGather;
5541 DAC960_P_To_PD_TranslateReadWriteCommand(CommandMailbox);
5542 break;
5543 case DAC960_V1_WriteWithScatterGather_Old:
5544 Command->V1.CommandMailbox.Common.CommandOpcode =
5545 DAC960_V1_WriteWithScatterGather;
5546 DAC960_P_To_PD_TranslateReadWriteCommand(CommandMailbox);
5547 break;
5548 default:
5549 break;
5551 DAC960_V1_ProcessCompletedCommand(Command);
5554 Attempt to remove additional I/O Requests from the Controller's
5555 I/O Request Queue and queue them to the Controller.
5557 DAC960_ProcessRequest(Controller);
5558 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5559 return IRQ_HANDLED;
5564 DAC960_V1_QueueMonitoringCommand queues a Monitoring Command to DAC960 V1
5565 Firmware Controllers.
5568 static void DAC960_V1_QueueMonitoringCommand(DAC960_Command_T *Command)
5570 DAC960_Controller_T *Controller = Command->Controller;
5571 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
5572 DAC960_V1_ClearCommand(Command);
5573 Command->CommandType = DAC960_MonitoringCommand;
5574 CommandMailbox->Type3.CommandOpcode = DAC960_V1_Enquiry;
5575 CommandMailbox->Type3.BusAddress = Controller->V1.NewEnquiryDMA;
5576 DAC960_QueueCommand(Command);
5581 DAC960_V2_QueueMonitoringCommand queues a Monitoring Command to DAC960 V2
5582 Firmware Controllers.
5585 static void DAC960_V2_QueueMonitoringCommand(DAC960_Command_T *Command)
5587 DAC960_Controller_T *Controller = Command->Controller;
5588 DAC960_V2_CommandMailbox_T *CommandMailbox = &Command->V2.CommandMailbox;
5589 DAC960_V2_ClearCommand(Command);
5590 Command->CommandType = DAC960_MonitoringCommand;
5591 CommandMailbox->ControllerInfo.CommandOpcode = DAC960_V2_IOCTL;
5592 CommandMailbox->ControllerInfo.CommandControlBits
5593 .DataTransferControllerToHost = true;
5594 CommandMailbox->ControllerInfo.CommandControlBits
5595 .NoAutoRequestSense = true;
5596 CommandMailbox->ControllerInfo.DataTransferSize =
5597 sizeof(DAC960_V2_ControllerInfo_T);
5598 CommandMailbox->ControllerInfo.ControllerNumber = 0;
5599 CommandMailbox->ControllerInfo.IOCTL_Opcode = DAC960_V2_GetControllerInfo;
5600 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
5601 .ScatterGatherSegments[0]
5602 .SegmentDataPointer =
5603 Controller->V2.NewControllerInformationDMA;
5604 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
5605 .ScatterGatherSegments[0]
5606 .SegmentByteCount =
5607 CommandMailbox->ControllerInfo.DataTransferSize;
5608 DAC960_QueueCommand(Command);
5613 DAC960_MonitoringTimerFunction is the timer function for monitoring
5614 the status of DAC960 Controllers.
5617 static void DAC960_MonitoringTimerFunction(unsigned long TimerData)
5619 DAC960_Controller_T *Controller = (DAC960_Controller_T *) TimerData;
5620 DAC960_Command_T *Command;
5621 unsigned long flags;
5623 if (Controller->FirmwareType == DAC960_V1_Controller)
5625 spin_lock_irqsave(&Controller->queue_lock, flags);
5627 Queue a Status Monitoring Command to Controller.
5629 Command = DAC960_AllocateCommand(Controller);
5630 if (Command != NULL)
5631 DAC960_V1_QueueMonitoringCommand(Command);
5632 else Controller->MonitoringCommandDeferred = true;
5633 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5635 else
5637 DAC960_V2_ControllerInfo_T *ControllerInfo =
5638 &Controller->V2.ControllerInformation;
5639 unsigned int StatusChangeCounter =
5640 Controller->V2.HealthStatusBuffer->StatusChangeCounter;
5641 bool ForceMonitoringCommand = false;
5642 if (time_after(jiffies, Controller->SecondaryMonitoringTime
5643 + DAC960_SecondaryMonitoringInterval))
5645 int LogicalDriveNumber;
5646 for (LogicalDriveNumber = 0;
5647 LogicalDriveNumber < DAC960_MaxLogicalDrives;
5648 LogicalDriveNumber++)
5650 DAC960_V2_LogicalDeviceInfo_T *LogicalDeviceInfo =
5651 Controller->V2.LogicalDeviceInformation[LogicalDriveNumber];
5652 if (LogicalDeviceInfo == NULL) continue;
5653 if (!LogicalDeviceInfo->LogicalDeviceControl
5654 .LogicalDeviceInitialized)
5656 ForceMonitoringCommand = true;
5657 break;
5660 Controller->SecondaryMonitoringTime = jiffies;
5662 if (StatusChangeCounter == Controller->V2.StatusChangeCounter &&
5663 Controller->V2.HealthStatusBuffer->NextEventSequenceNumber
5664 == Controller->V2.NextEventSequenceNumber &&
5665 (ControllerInfo->BackgroundInitializationsActive +
5666 ControllerInfo->LogicalDeviceInitializationsActive +
5667 ControllerInfo->PhysicalDeviceInitializationsActive +
5668 ControllerInfo->ConsistencyChecksActive +
5669 ControllerInfo->RebuildsActive +
5670 ControllerInfo->OnlineExpansionsActive == 0 ||
5671 time_before(jiffies, Controller->PrimaryMonitoringTime
5672 + DAC960_MonitoringTimerInterval)) &&
5673 !ForceMonitoringCommand)
5675 Controller->MonitoringTimer.expires =
5676 jiffies + DAC960_HealthStatusMonitoringInterval;
5677 add_timer(&Controller->MonitoringTimer);
5678 return;
5680 Controller->V2.StatusChangeCounter = StatusChangeCounter;
5681 Controller->PrimaryMonitoringTime = jiffies;
5683 spin_lock_irqsave(&Controller->queue_lock, flags);
5685 Queue a Status Monitoring Command to Controller.
5687 Command = DAC960_AllocateCommand(Controller);
5688 if (Command != NULL)
5689 DAC960_V2_QueueMonitoringCommand(Command);
5690 else Controller->MonitoringCommandDeferred = true;
5691 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5693 Wake up any processes waiting on a Health Status Buffer change.
5695 wake_up(&Controller->HealthStatusWaitQueue);
5700 DAC960_CheckStatusBuffer verifies that there is room to hold ByteCount
5701 additional bytes in the Combined Status Buffer and grows the buffer if
5702 necessary. It returns true if there is enough room and false otherwise.
5705 static bool DAC960_CheckStatusBuffer(DAC960_Controller_T *Controller,
5706 unsigned int ByteCount)
5708 unsigned char *NewStatusBuffer;
5709 if (Controller->InitialStatusLength + 1 +
5710 Controller->CurrentStatusLength + ByteCount + 1 <=
5711 Controller->CombinedStatusBufferLength)
5712 return true;
5713 if (Controller->CombinedStatusBufferLength == 0)
5715 unsigned int NewStatusBufferLength = DAC960_InitialStatusBufferSize;
5716 while (NewStatusBufferLength < ByteCount)
5717 NewStatusBufferLength *= 2;
5718 Controller->CombinedStatusBuffer = kmalloc(NewStatusBufferLength,
5719 GFP_ATOMIC);
5720 if (Controller->CombinedStatusBuffer == NULL) return false;
5721 Controller->CombinedStatusBufferLength = NewStatusBufferLength;
5722 return true;
5724 NewStatusBuffer = kmalloc(2 * Controller->CombinedStatusBufferLength,
5725 GFP_ATOMIC);
5726 if (NewStatusBuffer == NULL)
5728 DAC960_Warning("Unable to expand Combined Status Buffer - Truncating\n",
5729 Controller);
5730 return false;
5732 memcpy(NewStatusBuffer, Controller->CombinedStatusBuffer,
5733 Controller->CombinedStatusBufferLength);
5734 kfree(Controller->CombinedStatusBuffer);
5735 Controller->CombinedStatusBuffer = NewStatusBuffer;
5736 Controller->CombinedStatusBufferLength *= 2;
5737 Controller->CurrentStatusBuffer =
5738 &NewStatusBuffer[Controller->InitialStatusLength + 1];
5739 return true;
5744 DAC960_Message prints Driver Messages.
5747 static void DAC960_Message(DAC960_MessageLevel_T MessageLevel,
5748 unsigned char *Format,
5749 DAC960_Controller_T *Controller,
5750 ...)
5752 static unsigned char Buffer[DAC960_LineBufferSize];
5753 static bool BeginningOfLine = true;
5754 va_list Arguments;
5755 int Length = 0;
5756 va_start(Arguments, Controller);
5757 Length = vsprintf(Buffer, Format, Arguments);
5758 va_end(Arguments);
5759 if (Controller == NULL)
5760 printk("%sDAC960#%d: %s", DAC960_MessageLevelMap[MessageLevel],
5761 DAC960_ControllerCount, Buffer);
5762 else if (MessageLevel == DAC960_AnnounceLevel ||
5763 MessageLevel == DAC960_InfoLevel)
5765 if (!Controller->ControllerInitialized)
5767 if (DAC960_CheckStatusBuffer(Controller, Length))
5769 strcpy(&Controller->CombinedStatusBuffer
5770 [Controller->InitialStatusLength],
5771 Buffer);
5772 Controller->InitialStatusLength += Length;
5773 Controller->CurrentStatusBuffer =
5774 &Controller->CombinedStatusBuffer
5775 [Controller->InitialStatusLength + 1];
5777 if (MessageLevel == DAC960_AnnounceLevel)
5779 static int AnnouncementLines = 0;
5780 if (++AnnouncementLines <= 2)
5781 printk("%sDAC960: %s", DAC960_MessageLevelMap[MessageLevel],
5782 Buffer);
5784 else
5786 if (BeginningOfLine)
5788 if (Buffer[0] != '\n' || Length > 1)
5789 printk("%sDAC960#%d: %s",
5790 DAC960_MessageLevelMap[MessageLevel],
5791 Controller->ControllerNumber, Buffer);
5793 else printk("%s", Buffer);
5796 else if (DAC960_CheckStatusBuffer(Controller, Length))
5798 strcpy(&Controller->CurrentStatusBuffer[
5799 Controller->CurrentStatusLength], Buffer);
5800 Controller->CurrentStatusLength += Length;
5803 else if (MessageLevel == DAC960_ProgressLevel)
5805 strcpy(Controller->ProgressBuffer, Buffer);
5806 Controller->ProgressBufferLength = Length;
5807 if (Controller->EphemeralProgressMessage)
5809 if (time_after_eq(jiffies, Controller->LastProgressReportTime
5810 + DAC960_ProgressReportingInterval))
5812 printk("%sDAC960#%d: %s", DAC960_MessageLevelMap[MessageLevel],
5813 Controller->ControllerNumber, Buffer);
5814 Controller->LastProgressReportTime = jiffies;
5817 else printk("%sDAC960#%d: %s", DAC960_MessageLevelMap[MessageLevel],
5818 Controller->ControllerNumber, Buffer);
5820 else if (MessageLevel == DAC960_UserCriticalLevel)
5822 strcpy(&Controller->UserStatusBuffer[Controller->UserStatusLength],
5823 Buffer);
5824 Controller->UserStatusLength += Length;
5825 if (Buffer[0] != '\n' || Length > 1)
5826 printk("%sDAC960#%d: %s", DAC960_MessageLevelMap[MessageLevel],
5827 Controller->ControllerNumber, Buffer);
5829 else
5831 if (BeginningOfLine)
5832 printk("%sDAC960#%d: %s", DAC960_MessageLevelMap[MessageLevel],
5833 Controller->ControllerNumber, Buffer);
5834 else printk("%s", Buffer);
5836 BeginningOfLine = (Buffer[Length-1] == '\n');
5841 DAC960_ParsePhysicalDevice parses spaces followed by a Physical Device
5842 Channel:TargetID specification from a User Command string. It updates
5843 Channel and TargetID and returns true on success and false on failure.
5846 static bool DAC960_ParsePhysicalDevice(DAC960_Controller_T *Controller,
5847 char *UserCommandString,
5848 unsigned char *Channel,
5849 unsigned char *TargetID)
5851 char *NewUserCommandString = UserCommandString;
5852 unsigned long XChannel, XTargetID;
5853 while (*UserCommandString == ' ') UserCommandString++;
5854 if (UserCommandString == NewUserCommandString)
5855 return false;
5856 XChannel = simple_strtoul(UserCommandString, &NewUserCommandString, 10);
5857 if (NewUserCommandString == UserCommandString ||
5858 *NewUserCommandString != ':' ||
5859 XChannel >= Controller->Channels)
5860 return false;
5861 UserCommandString = ++NewUserCommandString;
5862 XTargetID = simple_strtoul(UserCommandString, &NewUserCommandString, 10);
5863 if (NewUserCommandString == UserCommandString ||
5864 *NewUserCommandString != '\0' ||
5865 XTargetID >= Controller->Targets)
5866 return false;
5867 *Channel = XChannel;
5868 *TargetID = XTargetID;
5869 return true;
5874 DAC960_ParseLogicalDrive parses spaces followed by a Logical Drive Number
5875 specification from a User Command string. It updates LogicalDriveNumber and
5876 returns true on success and false on failure.
5879 static bool DAC960_ParseLogicalDrive(DAC960_Controller_T *Controller,
5880 char *UserCommandString,
5881 unsigned char *LogicalDriveNumber)
5883 char *NewUserCommandString = UserCommandString;
5884 unsigned long XLogicalDriveNumber;
5885 while (*UserCommandString == ' ') UserCommandString++;
5886 if (UserCommandString == NewUserCommandString)
5887 return false;
5888 XLogicalDriveNumber =
5889 simple_strtoul(UserCommandString, &NewUserCommandString, 10);
5890 if (NewUserCommandString == UserCommandString ||
5891 *NewUserCommandString != '\0' ||
5892 XLogicalDriveNumber > DAC960_MaxLogicalDrives - 1)
5893 return false;
5894 *LogicalDriveNumber = XLogicalDriveNumber;
5895 return true;
5900 DAC960_V1_SetDeviceState sets the Device State for a Physical Device for
5901 DAC960 V1 Firmware Controllers.
5904 static void DAC960_V1_SetDeviceState(DAC960_Controller_T *Controller,
5905 DAC960_Command_T *Command,
5906 unsigned char Channel,
5907 unsigned char TargetID,
5908 DAC960_V1_PhysicalDeviceState_T
5909 DeviceState,
5910 const unsigned char *DeviceStateString)
5912 DAC960_V1_CommandMailbox_T *CommandMailbox = &Command->V1.CommandMailbox;
5913 CommandMailbox->Type3D.CommandOpcode = DAC960_V1_StartDevice;
5914 CommandMailbox->Type3D.Channel = Channel;
5915 CommandMailbox->Type3D.TargetID = TargetID;
5916 CommandMailbox->Type3D.DeviceState = DeviceState;
5917 CommandMailbox->Type3D.Modifier = 0;
5918 DAC960_ExecuteCommand(Command);
5919 switch (Command->V1.CommandStatus)
5921 case DAC960_V1_NormalCompletion:
5922 DAC960_UserCritical("%s of Physical Device %d:%d Succeeded\n", Controller,
5923 DeviceStateString, Channel, TargetID);
5924 break;
5925 case DAC960_V1_UnableToStartDevice:
5926 DAC960_UserCritical("%s of Physical Device %d:%d Failed - "
5927 "Unable to Start Device\n", Controller,
5928 DeviceStateString, Channel, TargetID);
5929 break;
5930 case DAC960_V1_NoDeviceAtAddress:
5931 DAC960_UserCritical("%s of Physical Device %d:%d Failed - "
5932 "No Device at Address\n", Controller,
5933 DeviceStateString, Channel, TargetID);
5934 break;
5935 case DAC960_V1_InvalidChannelOrTargetOrModifier:
5936 DAC960_UserCritical("%s of Physical Device %d:%d Failed - "
5937 "Invalid Channel or Target or Modifier\n",
5938 Controller, DeviceStateString, Channel, TargetID);
5939 break;
5940 case DAC960_V1_ChannelBusy:
5941 DAC960_UserCritical("%s of Physical Device %d:%d Failed - "
5942 "Channel Busy\n", Controller,
5943 DeviceStateString, Channel, TargetID);
5944 break;
5945 default:
5946 DAC960_UserCritical("%s of Physical Device %d:%d Failed - "
5947 "Unexpected Status %04X\n", Controller,
5948 DeviceStateString, Channel, TargetID,
5949 Command->V1.CommandStatus);
5950 break;
5956 DAC960_V1_ExecuteUserCommand executes a User Command for DAC960 V1 Firmware
5957 Controllers.
5960 static bool DAC960_V1_ExecuteUserCommand(DAC960_Controller_T *Controller,
5961 unsigned char *UserCommand)
5963 DAC960_Command_T *Command;
5964 DAC960_V1_CommandMailbox_T *CommandMailbox;
5965 unsigned long flags;
5966 unsigned char Channel, TargetID, LogicalDriveNumber;
5968 spin_lock_irqsave(&Controller->queue_lock, flags);
5969 while ((Command = DAC960_AllocateCommand(Controller)) == NULL)
5970 DAC960_WaitForCommand(Controller);
5971 spin_unlock_irqrestore(&Controller->queue_lock, flags);
5972 Controller->UserStatusLength = 0;
5973 DAC960_V1_ClearCommand(Command);
5974 Command->CommandType = DAC960_ImmediateCommand;
5975 CommandMailbox = &Command->V1.CommandMailbox;
5976 if (strcmp(UserCommand, "flush-cache") == 0)
5978 CommandMailbox->Type3.CommandOpcode = DAC960_V1_Flush;
5979 DAC960_ExecuteCommand(Command);
5980 DAC960_UserCritical("Cache Flush Completed\n", Controller);
5982 else if (strncmp(UserCommand, "kill", 4) == 0 &&
5983 DAC960_ParsePhysicalDevice(Controller, &UserCommand[4],
5984 &Channel, &TargetID))
5986 DAC960_V1_DeviceState_T *DeviceState =
5987 &Controller->V1.DeviceState[Channel][TargetID];
5988 if (DeviceState->Present &&
5989 DeviceState->DeviceType == DAC960_V1_DiskType &&
5990 DeviceState->DeviceState != DAC960_V1_Device_Dead)
5991 DAC960_V1_SetDeviceState(Controller, Command, Channel, TargetID,
5992 DAC960_V1_Device_Dead, "Kill");
5993 else DAC960_UserCritical("Kill of Physical Device %d:%d Illegal\n",
5994 Controller, Channel, TargetID);
5996 else if (strncmp(UserCommand, "make-online", 11) == 0 &&
5997 DAC960_ParsePhysicalDevice(Controller, &UserCommand[11],
5998 &Channel, &TargetID))
6000 DAC960_V1_DeviceState_T *DeviceState =
6001 &Controller->V1.DeviceState[Channel][TargetID];
6002 if (DeviceState->Present &&
6003 DeviceState->DeviceType == DAC960_V1_DiskType &&
6004 DeviceState->DeviceState == DAC960_V1_Device_Dead)
6005 DAC960_V1_SetDeviceState(Controller, Command, Channel, TargetID,
6006 DAC960_V1_Device_Online, "Make Online");
6007 else DAC960_UserCritical("Make Online of Physical Device %d:%d Illegal\n",
6008 Controller, Channel, TargetID);
6011 else if (strncmp(UserCommand, "make-standby", 12) == 0 &&
6012 DAC960_ParsePhysicalDevice(Controller, &UserCommand[12],
6013 &Channel, &TargetID))
6015 DAC960_V1_DeviceState_T *DeviceState =
6016 &Controller->V1.DeviceState[Channel][TargetID];
6017 if (DeviceState->Present &&
6018 DeviceState->DeviceType == DAC960_V1_DiskType &&
6019 DeviceState->DeviceState == DAC960_V1_Device_Dead)
6020 DAC960_V1_SetDeviceState(Controller, Command, Channel, TargetID,
6021 DAC960_V1_Device_Standby, "Make Standby");
6022 else DAC960_UserCritical("Make Standby of Physical "
6023 "Device %d:%d Illegal\n",
6024 Controller, Channel, TargetID);
6026 else if (strncmp(UserCommand, "rebuild", 7) == 0 &&
6027 DAC960_ParsePhysicalDevice(Controller, &UserCommand[7],
6028 &Channel, &TargetID))
6030 CommandMailbox->Type3D.CommandOpcode = DAC960_V1_RebuildAsync;
6031 CommandMailbox->Type3D.Channel = Channel;
6032 CommandMailbox->Type3D.TargetID = TargetID;
6033 DAC960_ExecuteCommand(Command);
6034 switch (Command->V1.CommandStatus)
6036 case DAC960_V1_NormalCompletion:
6037 DAC960_UserCritical("Rebuild of Physical Device %d:%d Initiated\n",
6038 Controller, Channel, TargetID);
6039 break;
6040 case DAC960_V1_AttemptToRebuildOnlineDrive:
6041 DAC960_UserCritical("Rebuild of Physical Device %d:%d Failed - "
6042 "Attempt to Rebuild Online or "
6043 "Unresponsive Drive\n",
6044 Controller, Channel, TargetID);
6045 break;
6046 case DAC960_V1_NewDiskFailedDuringRebuild:
6047 DAC960_UserCritical("Rebuild of Physical Device %d:%d Failed - "
6048 "New Disk Failed During Rebuild\n",
6049 Controller, Channel, TargetID);
6050 break;
6051 case DAC960_V1_InvalidDeviceAddress:
6052 DAC960_UserCritical("Rebuild of Physical Device %d:%d Failed - "
6053 "Invalid Device Address\n",
6054 Controller, Channel, TargetID);
6055 break;
6056 case DAC960_V1_RebuildOrCheckAlreadyInProgress:
6057 DAC960_UserCritical("Rebuild of Physical Device %d:%d Failed - "
6058 "Rebuild or Consistency Check Already "
6059 "in Progress\n", Controller, Channel, TargetID);
6060 break;
6061 default:
6062 DAC960_UserCritical("Rebuild of Physical Device %d:%d Failed - "
6063 "Unexpected Status %04X\n", Controller,
6064 Channel, TargetID, Command->V1.CommandStatus);
6065 break;
6068 else if (strncmp(UserCommand, "check-consistency", 17) == 0 &&
6069 DAC960_ParseLogicalDrive(Controller, &UserCommand[17],
6070 &LogicalDriveNumber))
6072 CommandMailbox->Type3C.CommandOpcode = DAC960_V1_CheckConsistencyAsync;
6073 CommandMailbox->Type3C.LogicalDriveNumber = LogicalDriveNumber;
6074 CommandMailbox->Type3C.AutoRestore = true;
6075 DAC960_ExecuteCommand(Command);
6076 switch (Command->V1.CommandStatus)
6078 case DAC960_V1_NormalCompletion:
6079 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6080 "(/dev/rd/c%dd%d) Initiated\n",
6081 Controller, LogicalDriveNumber,
6082 Controller->ControllerNumber,
6083 LogicalDriveNumber);
6084 break;
6085 case DAC960_V1_DependentDiskIsDead:
6086 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6087 "(/dev/rd/c%dd%d) Failed - "
6088 "Dependent Physical Device is DEAD\n",
6089 Controller, LogicalDriveNumber,
6090 Controller->ControllerNumber,
6091 LogicalDriveNumber);
6092 break;
6093 case DAC960_V1_InvalidOrNonredundantLogicalDrive:
6094 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6095 "(/dev/rd/c%dd%d) Failed - "
6096 "Invalid or Nonredundant Logical Drive\n",
6097 Controller, LogicalDriveNumber,
6098 Controller->ControllerNumber,
6099 LogicalDriveNumber);
6100 break;
6101 case DAC960_V1_RebuildOrCheckAlreadyInProgress:
6102 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6103 "(/dev/rd/c%dd%d) Failed - Rebuild or "
6104 "Consistency Check Already in Progress\n",
6105 Controller, LogicalDriveNumber,
6106 Controller->ControllerNumber,
6107 LogicalDriveNumber);
6108 break;
6109 default:
6110 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6111 "(/dev/rd/c%dd%d) Failed - "
6112 "Unexpected Status %04X\n",
6113 Controller, LogicalDriveNumber,
6114 Controller->ControllerNumber,
6115 LogicalDriveNumber, Command->V1.CommandStatus);
6116 break;
6119 else if (strcmp(UserCommand, "cancel-rebuild") == 0 ||
6120 strcmp(UserCommand, "cancel-consistency-check") == 0)
6123 the OldRebuildRateConstant is never actually used
6124 once its value is retrieved from the controller.
6126 unsigned char *OldRebuildRateConstant;
6127 dma_addr_t OldRebuildRateConstantDMA;
6129 OldRebuildRateConstant = pci_alloc_consistent( Controller->PCIDevice,
6130 sizeof(char), &OldRebuildRateConstantDMA);
6131 if (OldRebuildRateConstant == NULL) {
6132 DAC960_UserCritical("Cancellation of Rebuild or "
6133 "Consistency Check Failed - "
6134 "Out of Memory",
6135 Controller);
6136 goto failure;
6138 CommandMailbox->Type3R.CommandOpcode = DAC960_V1_RebuildControl;
6139 CommandMailbox->Type3R.RebuildRateConstant = 0xFF;
6140 CommandMailbox->Type3R.BusAddress = OldRebuildRateConstantDMA;
6141 DAC960_ExecuteCommand(Command);
6142 switch (Command->V1.CommandStatus)
6144 case DAC960_V1_NormalCompletion:
6145 DAC960_UserCritical("Rebuild or Consistency Check Cancelled\n",
6146 Controller);
6147 break;
6148 default:
6149 DAC960_UserCritical("Cancellation of Rebuild or "
6150 "Consistency Check Failed - "
6151 "Unexpected Status %04X\n",
6152 Controller, Command->V1.CommandStatus);
6153 break;
6155 failure:
6156 pci_free_consistent(Controller->PCIDevice, sizeof(char),
6157 OldRebuildRateConstant, OldRebuildRateConstantDMA);
6159 else DAC960_UserCritical("Illegal User Command: '%s'\n",
6160 Controller, UserCommand);
6162 spin_lock_irqsave(&Controller->queue_lock, flags);
6163 DAC960_DeallocateCommand(Command);
6164 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6165 return true;
6170 DAC960_V2_TranslatePhysicalDevice translates a Physical Device Channel and
6171 TargetID into a Logical Device. It returns true on success and false
6172 on failure.
6175 static bool DAC960_V2_TranslatePhysicalDevice(DAC960_Command_T *Command,
6176 unsigned char Channel,
6177 unsigned char TargetID,
6178 unsigned short
6179 *LogicalDeviceNumber)
6181 DAC960_V2_CommandMailbox_T SavedCommandMailbox, *CommandMailbox;
6182 DAC960_Controller_T *Controller = Command->Controller;
6184 CommandMailbox = &Command->V2.CommandMailbox;
6185 memcpy(&SavedCommandMailbox, CommandMailbox,
6186 sizeof(DAC960_V2_CommandMailbox_T));
6188 CommandMailbox->PhysicalDeviceInfo.CommandOpcode = DAC960_V2_IOCTL;
6189 CommandMailbox->PhysicalDeviceInfo.CommandControlBits
6190 .DataTransferControllerToHost = true;
6191 CommandMailbox->PhysicalDeviceInfo.CommandControlBits
6192 .NoAutoRequestSense = true;
6193 CommandMailbox->PhysicalDeviceInfo.DataTransferSize =
6194 sizeof(DAC960_V2_PhysicalToLogicalDevice_T);
6195 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.TargetID = TargetID;
6196 CommandMailbox->PhysicalDeviceInfo.PhysicalDevice.Channel = Channel;
6197 CommandMailbox->PhysicalDeviceInfo.IOCTL_Opcode =
6198 DAC960_V2_TranslatePhysicalToLogicalDevice;
6199 CommandMailbox->Common.DataTransferMemoryAddress
6200 .ScatterGatherSegments[0]
6201 .SegmentDataPointer =
6202 Controller->V2.PhysicalToLogicalDeviceDMA;
6203 CommandMailbox->Common.DataTransferMemoryAddress
6204 .ScatterGatherSegments[0]
6205 .SegmentByteCount =
6206 CommandMailbox->Common.DataTransferSize;
6208 DAC960_ExecuteCommand(Command);
6209 *LogicalDeviceNumber = Controller->V2.PhysicalToLogicalDevice->LogicalDeviceNumber;
6211 memcpy(CommandMailbox, &SavedCommandMailbox,
6212 sizeof(DAC960_V2_CommandMailbox_T));
6213 return (Command->V2.CommandStatus == DAC960_V2_NormalCompletion);
6218 DAC960_V2_ExecuteUserCommand executes a User Command for DAC960 V2 Firmware
6219 Controllers.
6222 static bool DAC960_V2_ExecuteUserCommand(DAC960_Controller_T *Controller,
6223 unsigned char *UserCommand)
6225 DAC960_Command_T *Command;
6226 DAC960_V2_CommandMailbox_T *CommandMailbox;
6227 unsigned long flags;
6228 unsigned char Channel, TargetID, LogicalDriveNumber;
6229 unsigned short LogicalDeviceNumber;
6231 spin_lock_irqsave(&Controller->queue_lock, flags);
6232 while ((Command = DAC960_AllocateCommand(Controller)) == NULL)
6233 DAC960_WaitForCommand(Controller);
6234 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6235 Controller->UserStatusLength = 0;
6236 DAC960_V2_ClearCommand(Command);
6237 Command->CommandType = DAC960_ImmediateCommand;
6238 CommandMailbox = &Command->V2.CommandMailbox;
6239 CommandMailbox->Common.CommandOpcode = DAC960_V2_IOCTL;
6240 CommandMailbox->Common.CommandControlBits.DataTransferControllerToHost = true;
6241 CommandMailbox->Common.CommandControlBits.NoAutoRequestSense = true;
6242 if (strcmp(UserCommand, "flush-cache") == 0)
6244 CommandMailbox->DeviceOperation.IOCTL_Opcode = DAC960_V2_PauseDevice;
6245 CommandMailbox->DeviceOperation.OperationDevice =
6246 DAC960_V2_RAID_Controller;
6247 DAC960_ExecuteCommand(Command);
6248 DAC960_UserCritical("Cache Flush Completed\n", Controller);
6250 else if (strncmp(UserCommand, "kill", 4) == 0 &&
6251 DAC960_ParsePhysicalDevice(Controller, &UserCommand[4],
6252 &Channel, &TargetID) &&
6253 DAC960_V2_TranslatePhysicalDevice(Command, Channel, TargetID,
6254 &LogicalDeviceNumber))
6256 CommandMailbox->SetDeviceState.LogicalDevice.LogicalDeviceNumber =
6257 LogicalDeviceNumber;
6258 CommandMailbox->SetDeviceState.IOCTL_Opcode =
6259 DAC960_V2_SetDeviceState;
6260 CommandMailbox->SetDeviceState.DeviceState.PhysicalDeviceState =
6261 DAC960_V2_Device_Dead;
6262 DAC960_ExecuteCommand(Command);
6263 DAC960_UserCritical("Kill of Physical Device %d:%d %s\n",
6264 Controller, Channel, TargetID,
6265 (Command->V2.CommandStatus
6266 == DAC960_V2_NormalCompletion
6267 ? "Succeeded" : "Failed"));
6269 else if (strncmp(UserCommand, "make-online", 11) == 0 &&
6270 DAC960_ParsePhysicalDevice(Controller, &UserCommand[11],
6271 &Channel, &TargetID) &&
6272 DAC960_V2_TranslatePhysicalDevice(Command, Channel, TargetID,
6273 &LogicalDeviceNumber))
6275 CommandMailbox->SetDeviceState.LogicalDevice.LogicalDeviceNumber =
6276 LogicalDeviceNumber;
6277 CommandMailbox->SetDeviceState.IOCTL_Opcode =
6278 DAC960_V2_SetDeviceState;
6279 CommandMailbox->SetDeviceState.DeviceState.PhysicalDeviceState =
6280 DAC960_V2_Device_Online;
6281 DAC960_ExecuteCommand(Command);
6282 DAC960_UserCritical("Make Online of Physical Device %d:%d %s\n",
6283 Controller, Channel, TargetID,
6284 (Command->V2.CommandStatus
6285 == DAC960_V2_NormalCompletion
6286 ? "Succeeded" : "Failed"));
6288 else if (strncmp(UserCommand, "make-standby", 12) == 0 &&
6289 DAC960_ParsePhysicalDevice(Controller, &UserCommand[12],
6290 &Channel, &TargetID) &&
6291 DAC960_V2_TranslatePhysicalDevice(Command, Channel, TargetID,
6292 &LogicalDeviceNumber))
6294 CommandMailbox->SetDeviceState.LogicalDevice.LogicalDeviceNumber =
6295 LogicalDeviceNumber;
6296 CommandMailbox->SetDeviceState.IOCTL_Opcode =
6297 DAC960_V2_SetDeviceState;
6298 CommandMailbox->SetDeviceState.DeviceState.PhysicalDeviceState =
6299 DAC960_V2_Device_Standby;
6300 DAC960_ExecuteCommand(Command);
6301 DAC960_UserCritical("Make Standby of Physical Device %d:%d %s\n",
6302 Controller, Channel, TargetID,
6303 (Command->V2.CommandStatus
6304 == DAC960_V2_NormalCompletion
6305 ? "Succeeded" : "Failed"));
6307 else if (strncmp(UserCommand, "rebuild", 7) == 0 &&
6308 DAC960_ParsePhysicalDevice(Controller, &UserCommand[7],
6309 &Channel, &TargetID) &&
6310 DAC960_V2_TranslatePhysicalDevice(Command, Channel, TargetID,
6311 &LogicalDeviceNumber))
6313 CommandMailbox->LogicalDeviceInfo.LogicalDevice.LogicalDeviceNumber =
6314 LogicalDeviceNumber;
6315 CommandMailbox->LogicalDeviceInfo.IOCTL_Opcode =
6316 DAC960_V2_RebuildDeviceStart;
6317 DAC960_ExecuteCommand(Command);
6318 DAC960_UserCritical("Rebuild of Physical Device %d:%d %s\n",
6319 Controller, Channel, TargetID,
6320 (Command->V2.CommandStatus
6321 == DAC960_V2_NormalCompletion
6322 ? "Initiated" : "Not Initiated"));
6324 else if (strncmp(UserCommand, "cancel-rebuild", 14) == 0 &&
6325 DAC960_ParsePhysicalDevice(Controller, &UserCommand[14],
6326 &Channel, &TargetID) &&
6327 DAC960_V2_TranslatePhysicalDevice(Command, Channel, TargetID,
6328 &LogicalDeviceNumber))
6330 CommandMailbox->LogicalDeviceInfo.LogicalDevice.LogicalDeviceNumber =
6331 LogicalDeviceNumber;
6332 CommandMailbox->LogicalDeviceInfo.IOCTL_Opcode =
6333 DAC960_V2_RebuildDeviceStop;
6334 DAC960_ExecuteCommand(Command);
6335 DAC960_UserCritical("Rebuild of Physical Device %d:%d %s\n",
6336 Controller, Channel, TargetID,
6337 (Command->V2.CommandStatus
6338 == DAC960_V2_NormalCompletion
6339 ? "Cancelled" : "Not Cancelled"));
6341 else if (strncmp(UserCommand, "check-consistency", 17) == 0 &&
6342 DAC960_ParseLogicalDrive(Controller, &UserCommand[17],
6343 &LogicalDriveNumber))
6345 CommandMailbox->ConsistencyCheck.LogicalDevice.LogicalDeviceNumber =
6346 LogicalDriveNumber;
6347 CommandMailbox->ConsistencyCheck.IOCTL_Opcode =
6348 DAC960_V2_ConsistencyCheckStart;
6349 CommandMailbox->ConsistencyCheck.RestoreConsistency = true;
6350 CommandMailbox->ConsistencyCheck.InitializedAreaOnly = false;
6351 DAC960_ExecuteCommand(Command);
6352 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6353 "(/dev/rd/c%dd%d) %s\n",
6354 Controller, LogicalDriveNumber,
6355 Controller->ControllerNumber,
6356 LogicalDriveNumber,
6357 (Command->V2.CommandStatus
6358 == DAC960_V2_NormalCompletion
6359 ? "Initiated" : "Not Initiated"));
6361 else if (strncmp(UserCommand, "cancel-consistency-check", 24) == 0 &&
6362 DAC960_ParseLogicalDrive(Controller, &UserCommand[24],
6363 &LogicalDriveNumber))
6365 CommandMailbox->ConsistencyCheck.LogicalDevice.LogicalDeviceNumber =
6366 LogicalDriveNumber;
6367 CommandMailbox->ConsistencyCheck.IOCTL_Opcode =
6368 DAC960_V2_ConsistencyCheckStop;
6369 DAC960_ExecuteCommand(Command);
6370 DAC960_UserCritical("Consistency Check of Logical Drive %d "
6371 "(/dev/rd/c%dd%d) %s\n",
6372 Controller, LogicalDriveNumber,
6373 Controller->ControllerNumber,
6374 LogicalDriveNumber,
6375 (Command->V2.CommandStatus
6376 == DAC960_V2_NormalCompletion
6377 ? "Cancelled" : "Not Cancelled"));
6379 else if (strcmp(UserCommand, "perform-discovery") == 0)
6381 CommandMailbox->Common.IOCTL_Opcode = DAC960_V2_StartDiscovery;
6382 DAC960_ExecuteCommand(Command);
6383 DAC960_UserCritical("Discovery %s\n", Controller,
6384 (Command->V2.CommandStatus
6385 == DAC960_V2_NormalCompletion
6386 ? "Initiated" : "Not Initiated"));
6387 if (Command->V2.CommandStatus == DAC960_V2_NormalCompletion)
6389 CommandMailbox->ControllerInfo.CommandOpcode = DAC960_V2_IOCTL;
6390 CommandMailbox->ControllerInfo.CommandControlBits
6391 .DataTransferControllerToHost = true;
6392 CommandMailbox->ControllerInfo.CommandControlBits
6393 .NoAutoRequestSense = true;
6394 CommandMailbox->ControllerInfo.DataTransferSize =
6395 sizeof(DAC960_V2_ControllerInfo_T);
6396 CommandMailbox->ControllerInfo.ControllerNumber = 0;
6397 CommandMailbox->ControllerInfo.IOCTL_Opcode =
6398 DAC960_V2_GetControllerInfo;
6400 * How does this NOT race with the queued Monitoring
6401 * usage of this structure?
6403 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
6404 .ScatterGatherSegments[0]
6405 .SegmentDataPointer =
6406 Controller->V2.NewControllerInformationDMA;
6407 CommandMailbox->ControllerInfo.DataTransferMemoryAddress
6408 .ScatterGatherSegments[0]
6409 .SegmentByteCount =
6410 CommandMailbox->ControllerInfo.DataTransferSize;
6411 DAC960_ExecuteCommand(Command);
6412 while (Controller->V2.NewControllerInformation->PhysicalScanActive)
6414 DAC960_ExecuteCommand(Command);
6415 sleep_on_timeout(&Controller->CommandWaitQueue, HZ);
6417 DAC960_UserCritical("Discovery Completed\n", Controller);
6420 else if (strcmp(UserCommand, "suppress-enclosure-messages") == 0)
6421 Controller->SuppressEnclosureMessages = true;
6422 else DAC960_UserCritical("Illegal User Command: '%s'\n",
6423 Controller, UserCommand);
6425 spin_lock_irqsave(&Controller->queue_lock, flags);
6426 DAC960_DeallocateCommand(Command);
6427 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6428 return true;
6431 static int dac960_proc_show(struct seq_file *m, void *v)
6433 unsigned char *StatusMessage = "OK\n";
6434 int ControllerNumber;
6435 for (ControllerNumber = 0;
6436 ControllerNumber < DAC960_ControllerCount;
6437 ControllerNumber++)
6439 DAC960_Controller_T *Controller = DAC960_Controllers[ControllerNumber];
6440 if (Controller == NULL) continue;
6441 if (Controller->MonitoringAlertMode)
6443 StatusMessage = "ALERT\n";
6444 break;
6447 seq_puts(m, StatusMessage);
6448 return 0;
6451 static int dac960_proc_open(struct inode *inode, struct file *file)
6453 return single_open(file, dac960_proc_show, NULL);
6456 static const struct file_operations dac960_proc_fops = {
6457 .owner = THIS_MODULE,
6458 .open = dac960_proc_open,
6459 .read = seq_read,
6460 .llseek = seq_lseek,
6461 .release = single_release,
6464 static int dac960_initial_status_proc_show(struct seq_file *m, void *v)
6466 DAC960_Controller_T *Controller = (DAC960_Controller_T *)m->private;
6467 seq_printf(m, "%.*s", Controller->InitialStatusLength, Controller->CombinedStatusBuffer);
6468 return 0;
6471 static int dac960_initial_status_proc_open(struct inode *inode, struct file *file)
6473 return single_open(file, dac960_initial_status_proc_show, PDE(inode)->data);
6476 static const struct file_operations dac960_initial_status_proc_fops = {
6477 .owner = THIS_MODULE,
6478 .open = dac960_initial_status_proc_open,
6479 .read = seq_read,
6480 .llseek = seq_lseek,
6481 .release = single_release,
6484 static int dac960_current_status_proc_show(struct seq_file *m, void *v)
6486 DAC960_Controller_T *Controller = (DAC960_Controller_T *) m->private;
6487 unsigned char *StatusMessage =
6488 "No Rebuild or Consistency Check in Progress\n";
6489 int ProgressMessageLength = strlen(StatusMessage);
6490 if (jiffies != Controller->LastCurrentStatusTime)
6492 Controller->CurrentStatusLength = 0;
6493 DAC960_AnnounceDriver(Controller);
6494 DAC960_ReportControllerConfiguration(Controller);
6495 DAC960_ReportDeviceConfiguration(Controller);
6496 if (Controller->ProgressBufferLength > 0)
6497 ProgressMessageLength = Controller->ProgressBufferLength;
6498 if (DAC960_CheckStatusBuffer(Controller, 2 + ProgressMessageLength))
6500 unsigned char *CurrentStatusBuffer = Controller->CurrentStatusBuffer;
6501 CurrentStatusBuffer[Controller->CurrentStatusLength++] = ' ';
6502 CurrentStatusBuffer[Controller->CurrentStatusLength++] = ' ';
6503 if (Controller->ProgressBufferLength > 0)
6504 strcpy(&CurrentStatusBuffer[Controller->CurrentStatusLength],
6505 Controller->ProgressBuffer);
6506 else
6507 strcpy(&CurrentStatusBuffer[Controller->CurrentStatusLength],
6508 StatusMessage);
6509 Controller->CurrentStatusLength += ProgressMessageLength;
6511 Controller->LastCurrentStatusTime = jiffies;
6513 seq_printf(m, "%.*s", Controller->CurrentStatusLength, Controller->CurrentStatusBuffer);
6514 return 0;
6517 static int dac960_current_status_proc_open(struct inode *inode, struct file *file)
6519 return single_open(file, dac960_current_status_proc_show, PDE(inode)->data);
6522 static const struct file_operations dac960_current_status_proc_fops = {
6523 .owner = THIS_MODULE,
6524 .open = dac960_current_status_proc_open,
6525 .read = seq_read,
6526 .llseek = seq_lseek,
6527 .release = single_release,
6530 static int dac960_user_command_proc_show(struct seq_file *m, void *v)
6532 DAC960_Controller_T *Controller = (DAC960_Controller_T *)m->private;
6534 seq_printf(m, "%.*s", Controller->UserStatusLength, Controller->UserStatusBuffer);
6535 return 0;
6538 static int dac960_user_command_proc_open(struct inode *inode, struct file *file)
6540 return single_open(file, dac960_user_command_proc_show, PDE(inode)->data);
6543 static ssize_t dac960_user_command_proc_write(struct file *file,
6544 const char __user *Buffer,
6545 size_t Count, loff_t *pos)
6547 DAC960_Controller_T *Controller = (DAC960_Controller_T *) PDE(file->f_path.dentry->d_inode)->data;
6548 unsigned char CommandBuffer[80];
6549 int Length;
6550 if (Count > sizeof(CommandBuffer)-1) return -EINVAL;
6551 if (copy_from_user(CommandBuffer, Buffer, Count)) return -EFAULT;
6552 CommandBuffer[Count] = '\0';
6553 Length = strlen(CommandBuffer);
6554 if (Length > 0 && CommandBuffer[Length-1] == '\n')
6555 CommandBuffer[--Length] = '\0';
6556 if (Controller->FirmwareType == DAC960_V1_Controller)
6557 return (DAC960_V1_ExecuteUserCommand(Controller, CommandBuffer)
6558 ? Count : -EBUSY);
6559 else
6560 return (DAC960_V2_ExecuteUserCommand(Controller, CommandBuffer)
6561 ? Count : -EBUSY);
6564 static const struct file_operations dac960_user_command_proc_fops = {
6565 .owner = THIS_MODULE,
6566 .open = dac960_user_command_proc_open,
6567 .read = seq_read,
6568 .llseek = seq_lseek,
6569 .release = single_release,
6570 .write = dac960_user_command_proc_write,
6574 DAC960_CreateProcEntries creates the /proc/rd/... entries for the
6575 DAC960 Driver.
6578 static void DAC960_CreateProcEntries(DAC960_Controller_T *Controller)
6580 struct proc_dir_entry *StatusProcEntry;
6581 struct proc_dir_entry *ControllerProcEntry;
6582 struct proc_dir_entry *UserCommandProcEntry;
6584 if (DAC960_ProcDirectoryEntry == NULL) {
6585 DAC960_ProcDirectoryEntry = proc_mkdir("rd", NULL);
6586 StatusProcEntry = proc_create("status", 0,
6587 DAC960_ProcDirectoryEntry,
6588 &dac960_proc_fops);
6591 sprintf(Controller->ControllerName, "c%d", Controller->ControllerNumber);
6592 ControllerProcEntry = proc_mkdir(Controller->ControllerName,
6593 DAC960_ProcDirectoryEntry);
6594 proc_create_data("initial_status", 0, ControllerProcEntry, &dac960_initial_status_proc_fops, Controller);
6595 proc_create_data("current_status", 0, ControllerProcEntry, &dac960_current_status_proc_fops, Controller);
6596 UserCommandProcEntry = proc_create_data("user_command", S_IWUSR | S_IRUSR, ControllerProcEntry, &dac960_user_command_proc_fops, Controller);
6597 Controller->ControllerProcEntry = ControllerProcEntry;
6602 DAC960_DestroyProcEntries destroys the /proc/rd/... entries for the
6603 DAC960 Driver.
6606 static void DAC960_DestroyProcEntries(DAC960_Controller_T *Controller)
6608 if (Controller->ControllerProcEntry == NULL)
6609 return;
6610 remove_proc_entry("initial_status", Controller->ControllerProcEntry);
6611 remove_proc_entry("current_status", Controller->ControllerProcEntry);
6612 remove_proc_entry("user_command", Controller->ControllerProcEntry);
6613 remove_proc_entry(Controller->ControllerName, DAC960_ProcDirectoryEntry);
6614 Controller->ControllerProcEntry = NULL;
6617 #ifdef DAC960_GAM_MINOR
6620 * DAC960_gam_ioctl is the ioctl function for performing RAID operations.
6623 static long DAC960_gam_ioctl(struct file *file, unsigned int Request,
6624 unsigned long Argument)
6626 long ErrorCode = 0;
6627 if (!capable(CAP_SYS_ADMIN)) return -EACCES;
6629 mutex_lock(&DAC960_mutex);
6630 switch (Request)
6632 case DAC960_IOCTL_GET_CONTROLLER_COUNT:
6633 ErrorCode = DAC960_ControllerCount;
6634 break;
6635 case DAC960_IOCTL_GET_CONTROLLER_INFO:
6637 DAC960_ControllerInfo_T __user *UserSpaceControllerInfo =
6638 (DAC960_ControllerInfo_T __user *) Argument;
6639 DAC960_ControllerInfo_T ControllerInfo;
6640 DAC960_Controller_T *Controller;
6641 int ControllerNumber;
6642 if (UserSpaceControllerInfo == NULL)
6643 ErrorCode = -EINVAL;
6644 else ErrorCode = get_user(ControllerNumber,
6645 &UserSpaceControllerInfo->ControllerNumber);
6646 if (ErrorCode != 0)
6647 break;
6648 ErrorCode = -ENXIO;
6649 if (ControllerNumber < 0 ||
6650 ControllerNumber > DAC960_ControllerCount - 1) {
6651 break;
6653 Controller = DAC960_Controllers[ControllerNumber];
6654 if (Controller == NULL)
6655 break;
6656 memset(&ControllerInfo, 0, sizeof(DAC960_ControllerInfo_T));
6657 ControllerInfo.ControllerNumber = ControllerNumber;
6658 ControllerInfo.FirmwareType = Controller->FirmwareType;
6659 ControllerInfo.Channels = Controller->Channels;
6660 ControllerInfo.Targets = Controller->Targets;
6661 ControllerInfo.PCI_Bus = Controller->Bus;
6662 ControllerInfo.PCI_Device = Controller->Device;
6663 ControllerInfo.PCI_Function = Controller->Function;
6664 ControllerInfo.IRQ_Channel = Controller->IRQ_Channel;
6665 ControllerInfo.PCI_Address = Controller->PCI_Address;
6666 strcpy(ControllerInfo.ModelName, Controller->ModelName);
6667 strcpy(ControllerInfo.FirmwareVersion, Controller->FirmwareVersion);
6668 ErrorCode = (copy_to_user(UserSpaceControllerInfo, &ControllerInfo,
6669 sizeof(DAC960_ControllerInfo_T)) ? -EFAULT : 0);
6670 break;
6672 case DAC960_IOCTL_V1_EXECUTE_COMMAND:
6674 DAC960_V1_UserCommand_T __user *UserSpaceUserCommand =
6675 (DAC960_V1_UserCommand_T __user *) Argument;
6676 DAC960_V1_UserCommand_T UserCommand;
6677 DAC960_Controller_T *Controller;
6678 DAC960_Command_T *Command = NULL;
6679 DAC960_V1_CommandOpcode_T CommandOpcode;
6680 DAC960_V1_CommandStatus_T CommandStatus;
6681 DAC960_V1_DCDB_T DCDB;
6682 DAC960_V1_DCDB_T *DCDB_IOBUF = NULL;
6683 dma_addr_t DCDB_IOBUFDMA;
6684 unsigned long flags;
6685 int ControllerNumber, DataTransferLength;
6686 unsigned char *DataTransferBuffer = NULL;
6687 dma_addr_t DataTransferBufferDMA;
6688 if (UserSpaceUserCommand == NULL) {
6689 ErrorCode = -EINVAL;
6690 break;
6692 if (copy_from_user(&UserCommand, UserSpaceUserCommand,
6693 sizeof(DAC960_V1_UserCommand_T))) {
6694 ErrorCode = -EFAULT;
6695 break;
6697 ControllerNumber = UserCommand.ControllerNumber;
6698 ErrorCode = -ENXIO;
6699 if (ControllerNumber < 0 ||
6700 ControllerNumber > DAC960_ControllerCount - 1)
6701 break;
6702 Controller = DAC960_Controllers[ControllerNumber];
6703 if (Controller == NULL)
6704 break;
6705 ErrorCode = -EINVAL;
6706 if (Controller->FirmwareType != DAC960_V1_Controller)
6707 break;
6708 CommandOpcode = UserCommand.CommandMailbox.Common.CommandOpcode;
6709 DataTransferLength = UserCommand.DataTransferLength;
6710 if (CommandOpcode & 0x80)
6711 break;
6712 if (CommandOpcode == DAC960_V1_DCDB)
6714 if (copy_from_user(&DCDB, UserCommand.DCDB,
6715 sizeof(DAC960_V1_DCDB_T))) {
6716 ErrorCode = -EFAULT;
6717 break;
6719 if (DCDB.Channel >= DAC960_V1_MaxChannels)
6720 break;
6721 if (!((DataTransferLength == 0 &&
6722 DCDB.Direction
6723 == DAC960_V1_DCDB_NoDataTransfer) ||
6724 (DataTransferLength > 0 &&
6725 DCDB.Direction
6726 == DAC960_V1_DCDB_DataTransferDeviceToSystem) ||
6727 (DataTransferLength < 0 &&
6728 DCDB.Direction
6729 == DAC960_V1_DCDB_DataTransferSystemToDevice)))
6730 break;
6731 if (((DCDB.TransferLengthHigh4 << 16) | DCDB.TransferLength)
6732 != abs(DataTransferLength))
6733 break;
6734 DCDB_IOBUF = pci_alloc_consistent(Controller->PCIDevice,
6735 sizeof(DAC960_V1_DCDB_T), &DCDB_IOBUFDMA);
6736 if (DCDB_IOBUF == NULL) {
6737 ErrorCode = -ENOMEM;
6738 break;
6741 ErrorCode = -ENOMEM;
6742 if (DataTransferLength > 0)
6744 DataTransferBuffer = pci_alloc_consistent(Controller->PCIDevice,
6745 DataTransferLength, &DataTransferBufferDMA);
6746 if (DataTransferBuffer == NULL)
6747 break;
6748 memset(DataTransferBuffer, 0, DataTransferLength);
6750 else if (DataTransferLength < 0)
6752 DataTransferBuffer = pci_alloc_consistent(Controller->PCIDevice,
6753 -DataTransferLength, &DataTransferBufferDMA);
6754 if (DataTransferBuffer == NULL)
6755 break;
6756 if (copy_from_user(DataTransferBuffer,
6757 UserCommand.DataTransferBuffer,
6758 -DataTransferLength)) {
6759 ErrorCode = -EFAULT;
6760 break;
6763 if (CommandOpcode == DAC960_V1_DCDB)
6765 spin_lock_irqsave(&Controller->queue_lock, flags);
6766 while ((Command = DAC960_AllocateCommand(Controller)) == NULL)
6767 DAC960_WaitForCommand(Controller);
6768 while (Controller->V1.DirectCommandActive[DCDB.Channel]
6769 [DCDB.TargetID])
6771 spin_unlock_irq(&Controller->queue_lock);
6772 __wait_event(Controller->CommandWaitQueue,
6773 !Controller->V1.DirectCommandActive
6774 [DCDB.Channel][DCDB.TargetID]);
6775 spin_lock_irq(&Controller->queue_lock);
6777 Controller->V1.DirectCommandActive[DCDB.Channel]
6778 [DCDB.TargetID] = true;
6779 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6780 DAC960_V1_ClearCommand(Command);
6781 Command->CommandType = DAC960_ImmediateCommand;
6782 memcpy(&Command->V1.CommandMailbox, &UserCommand.CommandMailbox,
6783 sizeof(DAC960_V1_CommandMailbox_T));
6784 Command->V1.CommandMailbox.Type3.BusAddress = DCDB_IOBUFDMA;
6785 DCDB.BusAddress = DataTransferBufferDMA;
6786 memcpy(DCDB_IOBUF, &DCDB, sizeof(DAC960_V1_DCDB_T));
6788 else
6790 spin_lock_irqsave(&Controller->queue_lock, flags);
6791 while ((Command = DAC960_AllocateCommand(Controller)) == NULL)
6792 DAC960_WaitForCommand(Controller);
6793 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6794 DAC960_V1_ClearCommand(Command);
6795 Command->CommandType = DAC960_ImmediateCommand;
6796 memcpy(&Command->V1.CommandMailbox, &UserCommand.CommandMailbox,
6797 sizeof(DAC960_V1_CommandMailbox_T));
6798 if (DataTransferBuffer != NULL)
6799 Command->V1.CommandMailbox.Type3.BusAddress =
6800 DataTransferBufferDMA;
6802 DAC960_ExecuteCommand(Command);
6803 CommandStatus = Command->V1.CommandStatus;
6804 spin_lock_irqsave(&Controller->queue_lock, flags);
6805 DAC960_DeallocateCommand(Command);
6806 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6807 if (DataTransferLength > 0)
6809 if (copy_to_user(UserCommand.DataTransferBuffer,
6810 DataTransferBuffer, DataTransferLength)) {
6811 ErrorCode = -EFAULT;
6812 goto Failure1;
6815 if (CommandOpcode == DAC960_V1_DCDB)
6818 I don't believe Target or Channel in the DCDB_IOBUF
6819 should be any different from the contents of DCDB.
6821 Controller->V1.DirectCommandActive[DCDB.Channel]
6822 [DCDB.TargetID] = false;
6823 if (copy_to_user(UserCommand.DCDB, DCDB_IOBUF,
6824 sizeof(DAC960_V1_DCDB_T))) {
6825 ErrorCode = -EFAULT;
6826 goto Failure1;
6829 ErrorCode = CommandStatus;
6830 Failure1:
6831 if (DataTransferBuffer != NULL)
6832 pci_free_consistent(Controller->PCIDevice, abs(DataTransferLength),
6833 DataTransferBuffer, DataTransferBufferDMA);
6834 if (DCDB_IOBUF != NULL)
6835 pci_free_consistent(Controller->PCIDevice, sizeof(DAC960_V1_DCDB_T),
6836 DCDB_IOBUF, DCDB_IOBUFDMA);
6837 break;
6839 case DAC960_IOCTL_V2_EXECUTE_COMMAND:
6841 DAC960_V2_UserCommand_T __user *UserSpaceUserCommand =
6842 (DAC960_V2_UserCommand_T __user *) Argument;
6843 DAC960_V2_UserCommand_T UserCommand;
6844 DAC960_Controller_T *Controller;
6845 DAC960_Command_T *Command = NULL;
6846 DAC960_V2_CommandMailbox_T *CommandMailbox;
6847 DAC960_V2_CommandStatus_T CommandStatus;
6848 unsigned long flags;
6849 int ControllerNumber, DataTransferLength;
6850 int DataTransferResidue, RequestSenseLength;
6851 unsigned char *DataTransferBuffer = NULL;
6852 dma_addr_t DataTransferBufferDMA;
6853 unsigned char *RequestSenseBuffer = NULL;
6854 dma_addr_t RequestSenseBufferDMA;
6856 ErrorCode = -EINVAL;
6857 if (UserSpaceUserCommand == NULL)
6858 break;
6859 if (copy_from_user(&UserCommand, UserSpaceUserCommand,
6860 sizeof(DAC960_V2_UserCommand_T))) {
6861 ErrorCode = -EFAULT;
6862 break;
6864 ErrorCode = -ENXIO;
6865 ControllerNumber = UserCommand.ControllerNumber;
6866 if (ControllerNumber < 0 ||
6867 ControllerNumber > DAC960_ControllerCount - 1)
6868 break;
6869 Controller = DAC960_Controllers[ControllerNumber];
6870 if (Controller == NULL)
6871 break;
6872 if (Controller->FirmwareType != DAC960_V2_Controller){
6873 ErrorCode = -EINVAL;
6874 break;
6876 DataTransferLength = UserCommand.DataTransferLength;
6877 ErrorCode = -ENOMEM;
6878 if (DataTransferLength > 0)
6880 DataTransferBuffer = pci_alloc_consistent(Controller->PCIDevice,
6881 DataTransferLength, &DataTransferBufferDMA);
6882 if (DataTransferBuffer == NULL)
6883 break;
6884 memset(DataTransferBuffer, 0, DataTransferLength);
6886 else if (DataTransferLength < 0)
6888 DataTransferBuffer = pci_alloc_consistent(Controller->PCIDevice,
6889 -DataTransferLength, &DataTransferBufferDMA);
6890 if (DataTransferBuffer == NULL)
6891 break;
6892 if (copy_from_user(DataTransferBuffer,
6893 UserCommand.DataTransferBuffer,
6894 -DataTransferLength)) {
6895 ErrorCode = -EFAULT;
6896 goto Failure2;
6899 RequestSenseLength = UserCommand.RequestSenseLength;
6900 if (RequestSenseLength > 0)
6902 RequestSenseBuffer = pci_alloc_consistent(Controller->PCIDevice,
6903 RequestSenseLength, &RequestSenseBufferDMA);
6904 if (RequestSenseBuffer == NULL)
6906 ErrorCode = -ENOMEM;
6907 goto Failure2;
6909 memset(RequestSenseBuffer, 0, RequestSenseLength);
6911 spin_lock_irqsave(&Controller->queue_lock, flags);
6912 while ((Command = DAC960_AllocateCommand(Controller)) == NULL)
6913 DAC960_WaitForCommand(Controller);
6914 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6915 DAC960_V2_ClearCommand(Command);
6916 Command->CommandType = DAC960_ImmediateCommand;
6917 CommandMailbox = &Command->V2.CommandMailbox;
6918 memcpy(CommandMailbox, &UserCommand.CommandMailbox,
6919 sizeof(DAC960_V2_CommandMailbox_T));
6920 CommandMailbox->Common.CommandControlBits
6921 .AdditionalScatterGatherListMemory = false;
6922 CommandMailbox->Common.CommandControlBits
6923 .NoAutoRequestSense = true;
6924 CommandMailbox->Common.DataTransferSize = 0;
6925 CommandMailbox->Common.DataTransferPageNumber = 0;
6926 memset(&CommandMailbox->Common.DataTransferMemoryAddress, 0,
6927 sizeof(DAC960_V2_DataTransferMemoryAddress_T));
6928 if (DataTransferLength != 0)
6930 if (DataTransferLength > 0)
6932 CommandMailbox->Common.CommandControlBits
6933 .DataTransferControllerToHost = true;
6934 CommandMailbox->Common.DataTransferSize = DataTransferLength;
6936 else
6938 CommandMailbox->Common.CommandControlBits
6939 .DataTransferControllerToHost = false;
6940 CommandMailbox->Common.DataTransferSize = -DataTransferLength;
6942 CommandMailbox->Common.DataTransferMemoryAddress
6943 .ScatterGatherSegments[0]
6944 .SegmentDataPointer = DataTransferBufferDMA;
6945 CommandMailbox->Common.DataTransferMemoryAddress
6946 .ScatterGatherSegments[0]
6947 .SegmentByteCount =
6948 CommandMailbox->Common.DataTransferSize;
6950 if (RequestSenseLength > 0)
6952 CommandMailbox->Common.CommandControlBits
6953 .NoAutoRequestSense = false;
6954 CommandMailbox->Common.RequestSenseSize = RequestSenseLength;
6955 CommandMailbox->Common.RequestSenseBusAddress =
6956 RequestSenseBufferDMA;
6958 DAC960_ExecuteCommand(Command);
6959 CommandStatus = Command->V2.CommandStatus;
6960 RequestSenseLength = Command->V2.RequestSenseLength;
6961 DataTransferResidue = Command->V2.DataTransferResidue;
6962 spin_lock_irqsave(&Controller->queue_lock, flags);
6963 DAC960_DeallocateCommand(Command);
6964 spin_unlock_irqrestore(&Controller->queue_lock, flags);
6965 if (RequestSenseLength > UserCommand.RequestSenseLength)
6966 RequestSenseLength = UserCommand.RequestSenseLength;
6967 if (copy_to_user(&UserSpaceUserCommand->DataTransferLength,
6968 &DataTransferResidue,
6969 sizeof(DataTransferResidue))) {
6970 ErrorCode = -EFAULT;
6971 goto Failure2;
6973 if (copy_to_user(&UserSpaceUserCommand->RequestSenseLength,
6974 &RequestSenseLength, sizeof(RequestSenseLength))) {
6975 ErrorCode = -EFAULT;
6976 goto Failure2;
6978 if (DataTransferLength > 0)
6980 if (copy_to_user(UserCommand.DataTransferBuffer,
6981 DataTransferBuffer, DataTransferLength)) {
6982 ErrorCode = -EFAULT;
6983 goto Failure2;
6986 if (RequestSenseLength > 0)
6988 if (copy_to_user(UserCommand.RequestSenseBuffer,
6989 RequestSenseBuffer, RequestSenseLength)) {
6990 ErrorCode = -EFAULT;
6991 goto Failure2;
6994 ErrorCode = CommandStatus;
6995 Failure2:
6996 pci_free_consistent(Controller->PCIDevice, abs(DataTransferLength),
6997 DataTransferBuffer, DataTransferBufferDMA);
6998 if (RequestSenseBuffer != NULL)
6999 pci_free_consistent(Controller->PCIDevice, RequestSenseLength,
7000 RequestSenseBuffer, RequestSenseBufferDMA);
7001 break;
7003 case DAC960_IOCTL_V2_GET_HEALTH_STATUS:
7005 DAC960_V2_GetHealthStatus_T __user *UserSpaceGetHealthStatus =
7006 (DAC960_V2_GetHealthStatus_T __user *) Argument;
7007 DAC960_V2_GetHealthStatus_T GetHealthStatus;
7008 DAC960_V2_HealthStatusBuffer_T HealthStatusBuffer;
7009 DAC960_Controller_T *Controller;
7010 int ControllerNumber;
7011 if (UserSpaceGetHealthStatus == NULL) {
7012 ErrorCode = -EINVAL;
7013 break;
7015 if (copy_from_user(&GetHealthStatus, UserSpaceGetHealthStatus,
7016 sizeof(DAC960_V2_GetHealthStatus_T))) {
7017 ErrorCode = -EFAULT;
7018 break;
7020 ErrorCode = -ENXIO;
7021 ControllerNumber = GetHealthStatus.ControllerNumber;
7022 if (ControllerNumber < 0 ||
7023 ControllerNumber > DAC960_ControllerCount - 1)
7024 break;
7025 Controller = DAC960_Controllers[ControllerNumber];
7026 if (Controller == NULL)
7027 break;
7028 if (Controller->FirmwareType != DAC960_V2_Controller) {
7029 ErrorCode = -EINVAL;
7030 break;
7032 if (copy_from_user(&HealthStatusBuffer,
7033 GetHealthStatus.HealthStatusBuffer,
7034 sizeof(DAC960_V2_HealthStatusBuffer_T))) {
7035 ErrorCode = -EFAULT;
7036 break;
7038 while (Controller->V2.HealthStatusBuffer->StatusChangeCounter
7039 == HealthStatusBuffer.StatusChangeCounter &&
7040 Controller->V2.HealthStatusBuffer->NextEventSequenceNumber
7041 == HealthStatusBuffer.NextEventSequenceNumber)
7043 interruptible_sleep_on_timeout(&Controller->HealthStatusWaitQueue,
7044 DAC960_MonitoringTimerInterval);
7045 if (signal_pending(current)) {
7046 ErrorCode = -EINTR;
7047 break;
7050 if (copy_to_user(GetHealthStatus.HealthStatusBuffer,
7051 Controller->V2.HealthStatusBuffer,
7052 sizeof(DAC960_V2_HealthStatusBuffer_T)))
7053 ErrorCode = -EFAULT;
7054 else
7055 ErrorCode = 0;
7057 default:
7058 ErrorCode = -ENOTTY;
7060 mutex_unlock(&DAC960_mutex);
7061 return ErrorCode;
7064 static const struct file_operations DAC960_gam_fops = {
7065 .owner = THIS_MODULE,
7066 .unlocked_ioctl = DAC960_gam_ioctl,
7067 .llseek = noop_llseek,
7070 static struct miscdevice DAC960_gam_dev = {
7071 DAC960_GAM_MINOR,
7072 "dac960_gam",
7073 &DAC960_gam_fops
7076 static int DAC960_gam_init(void)
7078 int ret;
7080 ret = misc_register(&DAC960_gam_dev);
7081 if (ret)
7082 printk(KERN_ERR "DAC960_gam: can't misc_register on minor %d\n", DAC960_GAM_MINOR);
7083 return ret;
7086 static void DAC960_gam_cleanup(void)
7088 misc_deregister(&DAC960_gam_dev);
7091 #endif /* DAC960_GAM_MINOR */
7093 static struct DAC960_privdata DAC960_GEM_privdata = {
7094 .HardwareType = DAC960_GEM_Controller,
7095 .FirmwareType = DAC960_V2_Controller,
7096 .InterruptHandler = DAC960_GEM_InterruptHandler,
7097 .MemoryWindowSize = DAC960_GEM_RegisterWindowSize,
7101 static struct DAC960_privdata DAC960_BA_privdata = {
7102 .HardwareType = DAC960_BA_Controller,
7103 .FirmwareType = DAC960_V2_Controller,
7104 .InterruptHandler = DAC960_BA_InterruptHandler,
7105 .MemoryWindowSize = DAC960_BA_RegisterWindowSize,
7108 static struct DAC960_privdata DAC960_LP_privdata = {
7109 .HardwareType = DAC960_LP_Controller,
7110 .FirmwareType = DAC960_V2_Controller,
7111 .InterruptHandler = DAC960_LP_InterruptHandler,
7112 .MemoryWindowSize = DAC960_LP_RegisterWindowSize,
7115 static struct DAC960_privdata DAC960_LA_privdata = {
7116 .HardwareType = DAC960_LA_Controller,
7117 .FirmwareType = DAC960_V1_Controller,
7118 .InterruptHandler = DAC960_LA_InterruptHandler,
7119 .MemoryWindowSize = DAC960_LA_RegisterWindowSize,
7122 static struct DAC960_privdata DAC960_PG_privdata = {
7123 .HardwareType = DAC960_PG_Controller,
7124 .FirmwareType = DAC960_V1_Controller,
7125 .InterruptHandler = DAC960_PG_InterruptHandler,
7126 .MemoryWindowSize = DAC960_PG_RegisterWindowSize,
7129 static struct DAC960_privdata DAC960_PD_privdata = {
7130 .HardwareType = DAC960_PD_Controller,
7131 .FirmwareType = DAC960_V1_Controller,
7132 .InterruptHandler = DAC960_PD_InterruptHandler,
7133 .MemoryWindowSize = DAC960_PD_RegisterWindowSize,
7136 static struct DAC960_privdata DAC960_P_privdata = {
7137 .HardwareType = DAC960_P_Controller,
7138 .FirmwareType = DAC960_V1_Controller,
7139 .InterruptHandler = DAC960_P_InterruptHandler,
7140 .MemoryWindowSize = DAC960_PD_RegisterWindowSize,
7143 static const struct pci_device_id DAC960_id_table[] = {
7145 .vendor = PCI_VENDOR_ID_MYLEX,
7146 .device = PCI_DEVICE_ID_MYLEX_DAC960_GEM,
7147 .subvendor = PCI_VENDOR_ID_MYLEX,
7148 .subdevice = PCI_ANY_ID,
7149 .driver_data = (unsigned long) &DAC960_GEM_privdata,
7152 .vendor = PCI_VENDOR_ID_MYLEX,
7153 .device = PCI_DEVICE_ID_MYLEX_DAC960_BA,
7154 .subvendor = PCI_ANY_ID,
7155 .subdevice = PCI_ANY_ID,
7156 .driver_data = (unsigned long) &DAC960_BA_privdata,
7159 .vendor = PCI_VENDOR_ID_MYLEX,
7160 .device = PCI_DEVICE_ID_MYLEX_DAC960_LP,
7161 .subvendor = PCI_ANY_ID,
7162 .subdevice = PCI_ANY_ID,
7163 .driver_data = (unsigned long) &DAC960_LP_privdata,
7166 .vendor = PCI_VENDOR_ID_DEC,
7167 .device = PCI_DEVICE_ID_DEC_21285,
7168 .subvendor = PCI_VENDOR_ID_MYLEX,
7169 .subdevice = PCI_DEVICE_ID_MYLEX_DAC960_LA,
7170 .driver_data = (unsigned long) &DAC960_LA_privdata,
7173 .vendor = PCI_VENDOR_ID_MYLEX,
7174 .device = PCI_DEVICE_ID_MYLEX_DAC960_PG,
7175 .subvendor = PCI_ANY_ID,
7176 .subdevice = PCI_ANY_ID,
7177 .driver_data = (unsigned long) &DAC960_PG_privdata,
7180 .vendor = PCI_VENDOR_ID_MYLEX,
7181 .device = PCI_DEVICE_ID_MYLEX_DAC960_PD,
7182 .subvendor = PCI_ANY_ID,
7183 .subdevice = PCI_ANY_ID,
7184 .driver_data = (unsigned long) &DAC960_PD_privdata,
7187 .vendor = PCI_VENDOR_ID_MYLEX,
7188 .device = PCI_DEVICE_ID_MYLEX_DAC960_P,
7189 .subvendor = PCI_ANY_ID,
7190 .subdevice = PCI_ANY_ID,
7191 .driver_data = (unsigned long) &DAC960_P_privdata,
7193 {0, },
7196 MODULE_DEVICE_TABLE(pci, DAC960_id_table);
7198 static struct pci_driver DAC960_pci_driver = {
7199 .name = "DAC960",
7200 .id_table = DAC960_id_table,
7201 .probe = DAC960_Probe,
7202 .remove = DAC960_Remove,
7205 static int __init DAC960_init_module(void)
7207 int ret;
7209 ret = pci_register_driver(&DAC960_pci_driver);
7210 #ifdef DAC960_GAM_MINOR
7211 if (!ret)
7212 DAC960_gam_init();
7213 #endif
7214 return ret;
7217 static void __exit DAC960_cleanup_module(void)
7219 int i;
7221 #ifdef DAC960_GAM_MINOR
7222 DAC960_gam_cleanup();
7223 #endif
7225 for (i = 0; i < DAC960_ControllerCount; i++) {
7226 DAC960_Controller_T *Controller = DAC960_Controllers[i];
7227 if (Controller == NULL)
7228 continue;
7229 DAC960_FinalizeController(Controller);
7231 if (DAC960_ProcDirectoryEntry != NULL) {
7232 remove_proc_entry("rd/status", NULL);
7233 remove_proc_entry("rd", NULL);
7235 DAC960_ControllerCount = 0;
7236 pci_unregister_driver(&DAC960_pci_driver);
7239 module_init(DAC960_init_module);
7240 module_exit(DAC960_cleanup_module);
7242 MODULE_LICENSE("GPL");