aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/aacraid/commsup.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/aacraid/commsup.c')
-rw-r--r--drivers/scsi/aacraid/commsup.c112
1 files changed, 47 insertions, 65 deletions
diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c
index 1b97f60652ba..5824a757a753 100644
--- a/drivers/scsi/aacraid/commsup.c
+++ b/drivers/scsi/aacraid/commsup.c
@@ -5,7 +5,7 @@
5 * based on the old aacraid driver that is.. 5 * based on the old aacraid driver that is..
6 * Adaptec aacraid device driver for Linux. 6 * Adaptec aacraid device driver for Linux.
7 * 7 *
8 * Copyright (c) 2000 Adaptec, Inc. (aacraid@adaptec.com) 8 * Copyright (c) 2000-2007 Adaptec, Inc. (aacraid@adaptec.com)
9 * 9 *
10 * This program is free software; you can redistribute it and/or modify 10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by 11 * it under the terms of the GNU General Public License as published by
@@ -94,7 +94,7 @@ void aac_fib_map_free(struct aac_dev *dev)
94int aac_fib_setup(struct aac_dev * dev) 94int aac_fib_setup(struct aac_dev * dev)
95{ 95{
96 struct fib *fibptr; 96 struct fib *fibptr;
97 struct hw_fib *hw_fib_va; 97 struct hw_fib *hw_fib;
98 dma_addr_t hw_fib_pa; 98 dma_addr_t hw_fib_pa;
99 int i; 99 int i;
100 100
@@ -106,24 +106,24 @@ int aac_fib_setup(struct aac_dev * dev)
106 if (i<0) 106 if (i<0)
107 return -ENOMEM; 107 return -ENOMEM;
108 108
109 hw_fib_va = dev->hw_fib_va; 109 hw_fib = dev->hw_fib_va;
110 hw_fib_pa = dev->hw_fib_pa; 110 hw_fib_pa = dev->hw_fib_pa;
111 memset(hw_fib_va, 0, dev->max_fib_size * (dev->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB)); 111 memset(hw_fib, 0, dev->max_fib_size * (dev->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB));
112 /* 112 /*
113 * Initialise the fibs 113 * Initialise the fibs
114 */ 114 */
115 for (i = 0, fibptr = &dev->fibs[i]; i < (dev->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB); i++, fibptr++) 115 for (i = 0, fibptr = &dev->fibs[i]; i < (dev->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB); i++, fibptr++)
116 { 116 {
117 fibptr->dev = dev; 117 fibptr->dev = dev;
118 fibptr->hw_fib = hw_fib_va; 118 fibptr->hw_fib_va = hw_fib;
119 fibptr->data = (void *) fibptr->hw_fib->data; 119 fibptr->data = (void *) fibptr->hw_fib_va->data;
120 fibptr->next = fibptr+1; /* Forward chain the fibs */ 120 fibptr->next = fibptr+1; /* Forward chain the fibs */
121 init_MUTEX_LOCKED(&fibptr->event_wait); 121 init_MUTEX_LOCKED(&fibptr->event_wait);
122 spin_lock_init(&fibptr->event_lock); 122 spin_lock_init(&fibptr->event_lock);
123 hw_fib_va->header.XferState = cpu_to_le32(0xffffffff); 123 hw_fib->header.XferState = cpu_to_le32(0xffffffff);
124 hw_fib_va->header.SenderSize = cpu_to_le16(dev->max_fib_size); 124 hw_fib->header.SenderSize = cpu_to_le16(dev->max_fib_size);
125 fibptr->hw_fib_pa = hw_fib_pa; 125 fibptr->hw_fib_pa = hw_fib_pa;
126 hw_fib_va = (struct hw_fib *)((unsigned char *)hw_fib_va + dev->max_fib_size); 126 hw_fib = (struct hw_fib *)((unsigned char *)hw_fib + dev->max_fib_size);
127 hw_fib_pa = hw_fib_pa + dev->max_fib_size; 127 hw_fib_pa = hw_fib_pa + dev->max_fib_size;
128 } 128 }
129 /* 129 /*
@@ -166,7 +166,7 @@ struct fib *aac_fib_alloc(struct aac_dev *dev)
166 * Null out fields that depend on being zero at the start of 166 * Null out fields that depend on being zero at the start of
167 * each I/O 167 * each I/O
168 */ 168 */
169 fibptr->hw_fib->header.XferState = 0; 169 fibptr->hw_fib_va->header.XferState = 0;
170 fibptr->callback = NULL; 170 fibptr->callback = NULL;
171 fibptr->callback_data = NULL; 171 fibptr->callback_data = NULL;
172 172
@@ -178,7 +178,6 @@ struct fib *aac_fib_alloc(struct aac_dev *dev)
178 * @fibptr: fib to free up 178 * @fibptr: fib to free up
179 * 179 *
180 * Frees up a fib and places it on the appropriate queue 180 * Frees up a fib and places it on the appropriate queue
181 * (either free or timed out)
182 */ 181 */
183 182
184void aac_fib_free(struct fib *fibptr) 183void aac_fib_free(struct fib *fibptr)
@@ -186,19 +185,15 @@ void aac_fib_free(struct fib *fibptr)
186 unsigned long flags; 185 unsigned long flags;
187 186
188 spin_lock_irqsave(&fibptr->dev->fib_lock, flags); 187 spin_lock_irqsave(&fibptr->dev->fib_lock, flags);
189 if (fibptr->flags & FIB_CONTEXT_FLAG_TIMED_OUT) { 188 if (unlikely(fibptr->flags & FIB_CONTEXT_FLAG_TIMED_OUT))
190 aac_config.fib_timeouts++; 189 aac_config.fib_timeouts++;
191 fibptr->next = fibptr->dev->timeout_fib; 190 if (fibptr->hw_fib_va->header.XferState != 0) {
192 fibptr->dev->timeout_fib = fibptr; 191 printk(KERN_WARNING "aac_fib_free, XferState != 0, fibptr = 0x%p, XferState = 0x%x\n",
193 } else { 192 (void*)fibptr,
194 if (fibptr->hw_fib->header.XferState != 0) { 193 le32_to_cpu(fibptr->hw_fib_va->header.XferState));
195 printk(KERN_WARNING "aac_fib_free, XferState != 0, fibptr = 0x%p, XferState = 0x%x\n", 194 }
196 (void*)fibptr, 195 fibptr->next = fibptr->dev->free_fib;
197 le32_to_cpu(fibptr->hw_fib->header.XferState)); 196 fibptr->dev->free_fib = fibptr;
198 }
199 fibptr->next = fibptr->dev->free_fib;
200 fibptr->dev->free_fib = fibptr;
201 }
202 spin_unlock_irqrestore(&fibptr->dev->fib_lock, flags); 197 spin_unlock_irqrestore(&fibptr->dev->fib_lock, flags);
203} 198}
204 199
@@ -211,7 +206,7 @@ void aac_fib_free(struct fib *fibptr)
211 206
212void aac_fib_init(struct fib *fibptr) 207void aac_fib_init(struct fib *fibptr)
213{ 208{
214 struct hw_fib *hw_fib = fibptr->hw_fib; 209 struct hw_fib *hw_fib = fibptr->hw_fib_va;
215 210
216 hw_fib->header.StructType = FIB_MAGIC; 211 hw_fib->header.StructType = FIB_MAGIC;
217 hw_fib->header.Size = cpu_to_le16(fibptr->dev->max_fib_size); 212 hw_fib->header.Size = cpu_to_le16(fibptr->dev->max_fib_size);
@@ -231,7 +226,7 @@ void aac_fib_init(struct fib *fibptr)
231 226
232static void fib_dealloc(struct fib * fibptr) 227static void fib_dealloc(struct fib * fibptr)
233{ 228{
234 struct hw_fib *hw_fib = fibptr->hw_fib; 229 struct hw_fib *hw_fib = fibptr->hw_fib_va;
235 BUG_ON(hw_fib->header.StructType != FIB_MAGIC); 230 BUG_ON(hw_fib->header.StructType != FIB_MAGIC);
236 hw_fib->header.XferState = 0; 231 hw_fib->header.XferState = 0;
237} 232}
@@ -386,7 +381,7 @@ int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
386 void *callback_data) 381 void *callback_data)
387{ 382{
388 struct aac_dev * dev = fibptr->dev; 383 struct aac_dev * dev = fibptr->dev;
389 struct hw_fib * hw_fib = fibptr->hw_fib; 384 struct hw_fib * hw_fib = fibptr->hw_fib_va;
390 unsigned long flags = 0; 385 unsigned long flags = 0;
391 unsigned long qflags; 386 unsigned long qflags;
392 387
@@ -430,7 +425,7 @@ int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
430 */ 425 */
431 hw_fib->header.Command = cpu_to_le16(command); 426 hw_fib->header.Command = cpu_to_le16(command);
432 hw_fib->header.XferState |= cpu_to_le32(SentFromHost); 427 hw_fib->header.XferState |= cpu_to_le32(SentFromHost);
433 fibptr->hw_fib->header.Flags = 0; /* 0 the flags field - internal only*/ 428 fibptr->hw_fib_va->header.Flags = 0; /* 0 the flags field - internal only*/
434 /* 429 /*
435 * Set the size of the Fib we want to send to the adapter 430 * Set the size of the Fib we want to send to the adapter
436 */ 431 */
@@ -462,7 +457,7 @@ int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
462 dprintk((KERN_DEBUG " Command = %d.\n", le32_to_cpu(hw_fib->header.Command))); 457 dprintk((KERN_DEBUG " Command = %d.\n", le32_to_cpu(hw_fib->header.Command)));
463 dprintk((KERN_DEBUG " SubCommand = %d.\n", le32_to_cpu(((struct aac_query_mount *)fib_data(fibptr))->command))); 458 dprintk((KERN_DEBUG " SubCommand = %d.\n", le32_to_cpu(((struct aac_query_mount *)fib_data(fibptr))->command)));
464 dprintk((KERN_DEBUG " XferState = %x.\n", le32_to_cpu(hw_fib->header.XferState))); 459 dprintk((KERN_DEBUG " XferState = %x.\n", le32_to_cpu(hw_fib->header.XferState)));
465 dprintk((KERN_DEBUG " hw_fib va being sent=%p\n",fibptr->hw_fib)); 460 dprintk((KERN_DEBUG " hw_fib va being sent=%p\n",fibptr->hw_fib_va));
466 dprintk((KERN_DEBUG " hw_fib pa being sent=%lx\n",(ulong)fibptr->hw_fib_pa)); 461 dprintk((KERN_DEBUG " hw_fib pa being sent=%lx\n",(ulong)fibptr->hw_fib_pa));
467 dprintk((KERN_DEBUG " fib being sent=%p\n",fibptr)); 462 dprintk((KERN_DEBUG " fib being sent=%p\n",fibptr));
468 463
@@ -513,22 +508,20 @@ int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
513 } 508 }
514 udelay(5); 509 udelay(5);
515 } 510 }
516 } else if (down_interruptible(&fibptr->event_wait)) { 511 } else
517 spin_lock_irqsave(&fibptr->event_lock, flags); 512 (void)down_interruptible(&fibptr->event_wait);
518 if (fibptr->done == 0) { 513 spin_lock_irqsave(&fibptr->event_lock, flags);
519 fibptr->done = 2; /* Tell interrupt we aborted */ 514 if (fibptr->done == 0) {
520 spin_unlock_irqrestore(&fibptr->event_lock, flags); 515 fibptr->done = 2; /* Tell interrupt we aborted */
521 return -EINTR;
522 }
523 spin_unlock_irqrestore(&fibptr->event_lock, flags); 516 spin_unlock_irqrestore(&fibptr->event_lock, flags);
517 return -EINTR;
524 } 518 }
519 spin_unlock_irqrestore(&fibptr->event_lock, flags);
525 BUG_ON(fibptr->done == 0); 520 BUG_ON(fibptr->done == 0);
526 521
527 if((fibptr->flags & FIB_CONTEXT_FLAG_TIMED_OUT)){ 522 if(unlikely(fibptr->flags & FIB_CONTEXT_FLAG_TIMED_OUT))
528 return -ETIMEDOUT; 523 return -ETIMEDOUT;
529 } else { 524 return 0;
530 return 0;
531 }
532 } 525 }
533 /* 526 /*
534 * If the user does not want a response than return success otherwise 527 * If the user does not want a response than return success otherwise
@@ -624,7 +617,7 @@ void aac_consumer_free(struct aac_dev * dev, struct aac_queue *q, u32 qid)
624 617
625int aac_fib_adapter_complete(struct fib *fibptr, unsigned short size) 618int aac_fib_adapter_complete(struct fib *fibptr, unsigned short size)
626{ 619{
627 struct hw_fib * hw_fib = fibptr->hw_fib; 620 struct hw_fib * hw_fib = fibptr->hw_fib_va;
628 struct aac_dev * dev = fibptr->dev; 621 struct aac_dev * dev = fibptr->dev;
629 struct aac_queue * q; 622 struct aac_queue * q;
630 unsigned long nointr = 0; 623 unsigned long nointr = 0;
@@ -688,7 +681,7 @@ int aac_fib_adapter_complete(struct fib *fibptr, unsigned short size)
688 681
689int aac_fib_complete(struct fib *fibptr) 682int aac_fib_complete(struct fib *fibptr)
690{ 683{
691 struct hw_fib * hw_fib = fibptr->hw_fib; 684 struct hw_fib * hw_fib = fibptr->hw_fib_va;
692 685
693 /* 686 /*
694 * Check for a fib which has already been completed 687 * Check for a fib which has already been completed
@@ -774,9 +767,8 @@ void aac_printf(struct aac_dev *dev, u32 val)
774#define AIF_SNIFF_TIMEOUT (30*HZ) 767#define AIF_SNIFF_TIMEOUT (30*HZ)
775static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr) 768static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
776{ 769{
777 struct hw_fib * hw_fib = fibptr->hw_fib; 770 struct hw_fib * hw_fib = fibptr->hw_fib_va;
778 struct aac_aifcmd * aifcmd = (struct aac_aifcmd *)hw_fib->data; 771 struct aac_aifcmd * aifcmd = (struct aac_aifcmd *)hw_fib->data;
779 int busy;
780 u32 container; 772 u32 container;
781 struct scsi_device *device; 773 struct scsi_device *device;
782 enum { 774 enum {
@@ -988,9 +980,6 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
988 * behind you. 980 * behind you.
989 */ 981 */
990 982
991 busy = 0;
992
993
994 /* 983 /*
995 * Find the scsi_device associated with the SCSI address, 984 * Find the scsi_device associated with the SCSI address,
996 * and mark it as changed, invalidating the cache. This deals 985 * and mark it as changed, invalidating the cache. This deals
@@ -1035,7 +1024,6 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
1035static int _aac_reset_adapter(struct aac_dev *aac) 1024static int _aac_reset_adapter(struct aac_dev *aac)
1036{ 1025{
1037 int index, quirks; 1026 int index, quirks;
1038 u32 ret;
1039 int retval; 1027 int retval;
1040 struct Scsi_Host *host; 1028 struct Scsi_Host *host;
1041 struct scsi_device *dev; 1029 struct scsi_device *dev;
@@ -1059,35 +1047,29 @@ static int _aac_reset_adapter(struct aac_dev *aac)
1059 * If a positive health, means in a known DEAD PANIC 1047 * If a positive health, means in a known DEAD PANIC
1060 * state and the adapter could be reset to `try again'. 1048 * state and the adapter could be reset to `try again'.
1061 */ 1049 */
1062 retval = aac_adapter_check_health(aac); 1050 retval = aac_adapter_restart(aac, aac_adapter_check_health(aac));
1063 if (retval == 0)
1064 retval = aac_adapter_sync_cmd(aac, IOP_RESET_ALWAYS,
1065 0, 0, 0, 0, 0, 0, &ret, NULL, NULL, NULL, NULL);
1066 if (retval)
1067 retval = aac_adapter_sync_cmd(aac, IOP_RESET,
1068 0, 0, 0, 0, 0, 0, &ret, NULL, NULL, NULL, NULL);
1069 1051
1070 if (retval) 1052 if (retval)
1071 goto out; 1053 goto out;
1072 if (ret != 0x00000001) {
1073 retval = -ENODEV;
1074 goto out;
1075 }
1076 1054
1077 /* 1055 /*
1078 * Loop through the fibs, close the synchronous FIBS 1056 * Loop through the fibs, close the synchronous FIBS
1079 */ 1057 */
1080 for (index = 0; index < (aac->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB); index++) { 1058 for (retval = 1, index = 0; index < (aac->scsi_host_ptr->can_queue + AAC_NUM_MGT_FIB); index++) {
1081 struct fib *fib = &aac->fibs[index]; 1059 struct fib *fib = &aac->fibs[index];
1082 if (!(fib->hw_fib->header.XferState & cpu_to_le32(NoResponseExpected | Async)) && 1060 if (!(fib->hw_fib_va->header.XferState & cpu_to_le32(NoResponseExpected | Async)) &&
1083 (fib->hw_fib->header.XferState & cpu_to_le32(ResponseExpected))) { 1061 (fib->hw_fib_va->header.XferState & cpu_to_le32(ResponseExpected))) {
1084 unsigned long flagv; 1062 unsigned long flagv;
1085 spin_lock_irqsave(&fib->event_lock, flagv); 1063 spin_lock_irqsave(&fib->event_lock, flagv);
1086 up(&fib->event_wait); 1064 up(&fib->event_wait);
1087 spin_unlock_irqrestore(&fib->event_lock, flagv); 1065 spin_unlock_irqrestore(&fib->event_lock, flagv);
1088 schedule(); 1066 schedule();
1067 retval = 0;
1089 } 1068 }
1090 } 1069 }
1070 /* Give some extra time for ioctls to complete. */
1071 if (retval == 0)
1072 ssleep(2);
1091 index = aac->cardtype; 1073 index = aac->cardtype;
1092 1074
1093 /* 1075 /*
@@ -1248,7 +1230,7 @@ int aac_check_health(struct aac_dev * aac)
1248 1230
1249 memset(hw_fib, 0, sizeof(struct hw_fib)); 1231 memset(hw_fib, 0, sizeof(struct hw_fib));
1250 memset(fib, 0, sizeof(struct fib)); 1232 memset(fib, 0, sizeof(struct fib));
1251 fib->hw_fib = hw_fib; 1233 fib->hw_fib_va = hw_fib;
1252 fib->dev = aac; 1234 fib->dev = aac;
1253 aac_fib_init(fib); 1235 aac_fib_init(fib);
1254 fib->type = FSAFS_NTC_FIB_CONTEXT; 1236 fib->type = FSAFS_NTC_FIB_CONTEXT;
@@ -1354,11 +1336,11 @@ int aac_command_thread(void *data)
1354 * do anything at this point since we don't have 1336 * do anything at this point since we don't have
1355 * anything defined for this thread to do. 1337 * anything defined for this thread to do.
1356 */ 1338 */
1357 hw_fib = fib->hw_fib; 1339 hw_fib = fib->hw_fib_va;
1358 memset(fib, 0, sizeof(struct fib)); 1340 memset(fib, 0, sizeof(struct fib));
1359 fib->type = FSAFS_NTC_FIB_CONTEXT; 1341 fib->type = FSAFS_NTC_FIB_CONTEXT;
1360 fib->size = sizeof( struct fib ); 1342 fib->size = sizeof( struct fib );
1361 fib->hw_fib = hw_fib; 1343 fib->hw_fib_va = hw_fib;
1362 fib->data = hw_fib->data; 1344 fib->data = hw_fib->data;
1363 fib->dev = dev; 1345 fib->dev = dev;
1364 /* 1346 /*
@@ -1485,7 +1467,7 @@ int aac_command_thread(void *data)
1485 */ 1467 */
1486 memcpy(hw_newfib, hw_fib, sizeof(struct hw_fib)); 1468 memcpy(hw_newfib, hw_fib, sizeof(struct hw_fib));
1487 memcpy(newfib, fib, sizeof(struct fib)); 1469 memcpy(newfib, fib, sizeof(struct fib));
1488 newfib->hw_fib = hw_newfib; 1470 newfib->hw_fib_va = hw_newfib;
1489 /* 1471 /*
1490 * Put the FIB onto the 1472 * Put the FIB onto the
1491 * fibctx's fibs 1473 * fibctx's fibs