Merge master.kernel.org:/pub/scm/linux/kernel/git/davem/sparc-2.6
[sfrench/cifs-2.6.git] / drivers / scsi / 3w-9xxx.c
1 /*
2    3w-9xxx.c -- 3ware 9000 Storage Controller device driver for Linux.
3
4    Written By: Adam Radford <linuxraid@amcc.com>
5
6    Copyright (C) 2004-2005 Applied Micro Circuits Corporation.
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; version 2 of the License.
11
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16
17    NO WARRANTY
18    THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR
19    CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT
20    LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT,
21    MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is
22    solely responsible for determining the appropriateness of using and
23    distributing the Program and assumes all risks associated with its
24    exercise of rights under this Agreement, including but not limited to
25    the risks and costs of program errors, damage to or loss of data,
26    programs or equipment, and unavailability or interruption of operations.
27
28    DISCLAIMER OF LIABILITY
29    NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY
30    DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31    DAMAGES (INCLUDING WITHOUT LIMITATION LOST PROFITS), HOWEVER CAUSED AND
32    ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
33    TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
34    USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED
35    HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES
36
37    You should have received a copy of the GNU General Public License
38    along with this program; if not, write to the Free Software
39    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
40
41    Bugs/Comments/Suggestions should be mailed to:
42    linuxraid@amcc.com
43
44    For more information, goto:
45    http://www.amcc.com
46
47    Note: This version of the driver does not contain a bundled firmware
48          image.
49
50    History
51    -------
52    2.26.02.000 - Driver cleanup for kernel submission.
53    2.26.02.001 - Replace schedule_timeout() calls with msleep().
54    2.26.02.002 - Add support for PAE mode.
55                  Add lun support.
56                  Fix twa_remove() to free irq handler/unregister_chrdev()
57                  before shutting down card.
58                  Change to new 'change_queue_depth' api.
59                  Fix 'handled=1' ISR usage, remove bogus IRQ check.
60                  Remove un-needed eh_abort handler.
61                  Add support for embedded firmware error strings.
62 */
63
64 #include <linux/module.h>
65 #include <linux/reboot.h>
66 #include <linux/spinlock.h>
67 #include <linux/interrupt.h>
68 #include <linux/moduleparam.h>
69 #include <linux/errno.h>
70 #include <linux/types.h>
71 #include <linux/delay.h>
72 #include <linux/pci.h>
73 #include <linux/time.h>
74 #include <asm/io.h>
75 #include <asm/irq.h>
76 #include <asm/uaccess.h>
77 #include <scsi/scsi.h>
78 #include <scsi/scsi_host.h>
79 #include <scsi/scsi_tcq.h>
80 #include <scsi/scsi_cmnd.h>
81 #include "3w-9xxx.h"
82
83 /* Globals */
84 #define TW_DRIVER_VERSION "2.26.02.002"
85 static TW_Device_Extension *twa_device_extension_list[TW_MAX_SLOT];
86 static unsigned int twa_device_extension_count;
87 static int twa_major = -1;
88 extern struct timezone sys_tz;
89
90 /* Module parameters */
91 MODULE_AUTHOR ("AMCC");
92 MODULE_DESCRIPTION ("3ware 9000 Storage Controller Linux Driver");
93 MODULE_LICENSE("GPL");
94 MODULE_VERSION(TW_DRIVER_VERSION);
95
96 /* Function prototypes */
97 static void twa_aen_queue_event(TW_Device_Extension *tw_dev, TW_Command_Apache_Header *header);
98 static int twa_aen_read_queue(TW_Device_Extension *tw_dev, int request_id);
99 static char *twa_aen_severity_lookup(unsigned char severity_code);
100 static void twa_aen_sync_time(TW_Device_Extension *tw_dev, int request_id);
101 static int twa_chrdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg);
102 static int twa_chrdev_open(struct inode *inode, struct file *file);
103 static int twa_fill_sense(TW_Device_Extension *tw_dev, int request_id, int copy_sense, int print_host);
104 static void twa_free_request_id(TW_Device_Extension *tw_dev,int request_id);
105 static void twa_get_request_id(TW_Device_Extension *tw_dev, int *request_id);
106 static int twa_initconnection(TW_Device_Extension *tw_dev, int message_credits,
107                               u32 set_features, unsigned short current_fw_srl, 
108                               unsigned short current_fw_arch_id, 
109                               unsigned short current_fw_branch, 
110                               unsigned short current_fw_build, 
111                               unsigned short *fw_on_ctlr_srl, 
112                               unsigned short *fw_on_ctlr_arch_id, 
113                               unsigned short *fw_on_ctlr_branch, 
114                               unsigned short *fw_on_ctlr_build, 
115                               u32 *init_connect_result);
116 static void twa_load_sgl(TW_Command_Full *full_command_packet, int request_id, dma_addr_t dma_handle, int length);
117 static int twa_poll_response(TW_Device_Extension *tw_dev, int request_id, int seconds);
118 static int twa_poll_status_gone(TW_Device_Extension *tw_dev, u32 flag, int seconds);
119 static int twa_post_command_packet(TW_Device_Extension *tw_dev, int request_id, char internal);
120 static int twa_reset_device_extension(TW_Device_Extension *tw_dev, int ioctl_reset);
121 static int twa_reset_sequence(TW_Device_Extension *tw_dev, int soft_reset);
122 static int twa_scsiop_execute_scsi(TW_Device_Extension *tw_dev, int request_id, char *cdb, int use_sg, TW_SG_Entry *sglistarg);
123 static void twa_scsiop_execute_scsi_complete(TW_Device_Extension *tw_dev, int request_id);
124 static char *twa_string_lookup(twa_message_type *table, unsigned int aen_code);
125 static void twa_unmap_scsi_data(TW_Device_Extension *tw_dev, int request_id);
126
127 /* Functions */
128
129 /* Show some statistics about the card */
130 static ssize_t twa_show_stats(struct class_device *class_dev, char *buf)
131 {
132         struct Scsi_Host *host = class_to_shost(class_dev);
133         TW_Device_Extension *tw_dev = (TW_Device_Extension *)host->hostdata;
134         unsigned long flags = 0;
135         ssize_t len;
136
137         spin_lock_irqsave(tw_dev->host->host_lock, flags);
138         len = snprintf(buf, PAGE_SIZE, "3w-9xxx Driver version: %s\n"
139                        "Current commands posted:   %4d\n"
140                        "Max commands posted:       %4d\n"
141                        "Current pending commands:  %4d\n"
142                        "Max pending commands:      %4d\n"
143                        "Last sgl length:           %4d\n"
144                        "Max sgl length:            %4d\n"
145                        "Last sector count:         %4d\n"
146                        "Max sector count:          %4d\n"
147                        "SCSI Host Resets:          %4d\n"
148                        "AEN's:                     %4d\n", 
149                        TW_DRIVER_VERSION,
150                        tw_dev->posted_request_count,
151                        tw_dev->max_posted_request_count,
152                        tw_dev->pending_request_count,
153                        tw_dev->max_pending_request_count,
154                        tw_dev->sgl_entries,
155                        tw_dev->max_sgl_entries,
156                        tw_dev->sector_count,
157                        tw_dev->max_sector_count,
158                        tw_dev->num_resets,
159                        tw_dev->aen_count);
160         spin_unlock_irqrestore(tw_dev->host->host_lock, flags);
161         return len;
162 } /* End twa_show_stats() */
163
164 /* This function will set a devices queue depth */
165 static int twa_change_queue_depth(struct scsi_device *sdev, int queue_depth)
166 {
167         if (queue_depth > TW_Q_LENGTH-2)
168                 queue_depth = TW_Q_LENGTH-2;
169         scsi_adjust_queue_depth(sdev, MSG_ORDERED_TAG, queue_depth);
170         return queue_depth;
171 } /* End twa_change_queue_depth() */
172
173 /* Create sysfs 'stats' entry */
174 static struct class_device_attribute twa_host_stats_attr = {
175         .attr = {
176                 .name =         "stats",
177                 .mode =         S_IRUGO,
178         },
179         .show = twa_show_stats
180 };
181
182 /* Host attributes initializer */
183 static struct class_device_attribute *twa_host_attrs[] = {
184         &twa_host_stats_attr,
185         NULL,
186 };
187
188 /* File operations struct for character device */
189 static struct file_operations twa_fops = {
190         .owner          = THIS_MODULE,
191         .ioctl          = twa_chrdev_ioctl,
192         .open           = twa_chrdev_open,
193         .release        = NULL
194 };
195
196 /* This function will complete an aen request from the isr */
197 static int twa_aen_complete(TW_Device_Extension *tw_dev, int request_id)
198 {
199         TW_Command_Full *full_command_packet;
200         TW_Command *command_packet;
201         TW_Command_Apache_Header *header;
202         unsigned short aen;
203         int retval = 1;
204
205         header = (TW_Command_Apache_Header *)tw_dev->generic_buffer_virt[request_id];
206         tw_dev->posted_request_count--;
207         aen = header->status_block.error;
208         full_command_packet = tw_dev->command_packet_virt[request_id];
209         command_packet = &full_command_packet->command.oldcommand;
210
211         /* First check for internal completion of set param for time sync */
212         if (TW_OP_OUT(command_packet->opcode__sgloffset) == TW_OP_SET_PARAM) {
213                 /* Keep reading the queue in case there are more aen's */
214                 if (twa_aen_read_queue(tw_dev, request_id))
215                         goto out2;
216                 else {
217                         retval = 0;
218                         goto out;
219                 }
220         }
221
222         switch (aen) {
223         case TW_AEN_QUEUE_EMPTY:
224                 /* Quit reading the queue if this is the last one */
225                 break;
226         case TW_AEN_SYNC_TIME_WITH_HOST:
227                 twa_aen_sync_time(tw_dev, request_id);
228                 retval = 0;
229                 goto out;
230         default:
231                 twa_aen_queue_event(tw_dev, header);
232
233                 /* If there are more aen's, keep reading the queue */
234                 if (twa_aen_read_queue(tw_dev, request_id))
235                         goto out2;
236                 else {
237                         retval = 0;
238                         goto out;
239                 }
240         }
241         retval = 0;
242 out2:
243         tw_dev->state[request_id] = TW_S_COMPLETED;
244         twa_free_request_id(tw_dev, request_id);
245         clear_bit(TW_IN_ATTENTION_LOOP, &tw_dev->flags);
246 out:
247         return retval;
248 } /* End twa_aen_complete() */
249
250 /* This function will drain aen queue */
251 static int twa_aen_drain_queue(TW_Device_Extension *tw_dev, int no_check_reset)
252 {
253         int request_id = 0;
254         char cdb[TW_MAX_CDB_LEN];
255         TW_SG_Entry sglist[1];
256         int finished = 0, count = 0;
257         TW_Command_Full *full_command_packet;
258         TW_Command_Apache_Header *header;
259         unsigned short aen;
260         int first_reset = 0, queue = 0, retval = 1;
261
262         if (no_check_reset)
263                 first_reset = 0;
264         else
265                 first_reset = 1;
266
267         full_command_packet = tw_dev->command_packet_virt[request_id];
268         memset(full_command_packet, 0, sizeof(TW_Command_Full));
269
270         /* Initialize cdb */
271         memset(&cdb, 0, TW_MAX_CDB_LEN);
272         cdb[0] = REQUEST_SENSE; /* opcode */
273         cdb[4] = TW_ALLOCATION_LENGTH; /* allocation length */
274
275         /* Initialize sglist */
276         memset(&sglist, 0, sizeof(TW_SG_Entry));
277         sglist[0].length = TW_SECTOR_SIZE;
278         sglist[0].address = tw_dev->generic_buffer_phys[request_id];
279
280         if (sglist[0].address & TW_ALIGNMENT_9000_SGL) {
281                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1, "Found unaligned address during AEN drain");
282                 goto out;
283         }
284
285         /* Mark internal command */
286         tw_dev->srb[request_id] = NULL;
287
288         do {
289                 /* Send command to the board */
290                 if (twa_scsiop_execute_scsi(tw_dev, request_id, cdb, 1, sglist)) {
291                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x2, "Error posting request sense");
292                         goto out;
293                 }
294
295                 /* Now poll for completion */
296                 if (twa_poll_response(tw_dev, request_id, 30)) {
297                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x3, "No valid response while draining AEN queue");
298                         tw_dev->posted_request_count--;
299                         goto out;
300                 }
301
302                 tw_dev->posted_request_count--;
303                 header = (TW_Command_Apache_Header *)tw_dev->generic_buffer_virt[request_id];
304                 aen = header->status_block.error;
305                 queue = 0;
306                 count++;
307
308                 switch (aen) {
309                 case TW_AEN_QUEUE_EMPTY:
310                         if (first_reset != 1)
311                                 goto out;
312                         else
313                                 finished = 1;
314                         break;
315                 case TW_AEN_SOFT_RESET:
316                         if (first_reset == 0)
317                                 first_reset = 1;
318                         else
319                                 queue = 1;
320                         break;
321                 case TW_AEN_SYNC_TIME_WITH_HOST:
322                         break;
323                 default:
324                         queue = 1;
325                 }
326
327                 /* Now queue an event info */
328                 if (queue)
329                         twa_aen_queue_event(tw_dev, header);
330         } while ((finished == 0) && (count < TW_MAX_AEN_DRAIN));
331
332         if (count == TW_MAX_AEN_DRAIN)
333                 goto out;
334
335         retval = 0;
336 out:
337         tw_dev->state[request_id] = TW_S_INITIAL;
338         return retval;
339 } /* End twa_aen_drain_queue() */
340
341 /* This function will queue an event */
342 static void twa_aen_queue_event(TW_Device_Extension *tw_dev, TW_Command_Apache_Header *header)
343 {
344         u32 local_time;
345         struct timeval time;
346         TW_Event *event;
347         unsigned short aen;
348         char host[16];
349         char *error_str;
350
351         tw_dev->aen_count++;
352
353         /* Fill out event info */
354         event = tw_dev->event_queue[tw_dev->error_index];
355
356         /* Check for clobber */
357         host[0] = '\0';
358         if (tw_dev->host) {
359                 sprintf(host, " scsi%d:", tw_dev->host->host_no);
360                 if (event->retrieved == TW_AEN_NOT_RETRIEVED)
361                         tw_dev->aen_clobber = 1;
362         }
363
364         aen = header->status_block.error;
365         memset(event, 0, sizeof(TW_Event));
366
367         event->severity = TW_SEV_OUT(header->status_block.severity__reserved);
368         do_gettimeofday(&time);
369         local_time = (u32)(time.tv_sec - (sys_tz.tz_minuteswest * 60));
370         event->time_stamp_sec = local_time;
371         event->aen_code = aen;
372         event->retrieved = TW_AEN_NOT_RETRIEVED;
373         event->sequence_id = tw_dev->error_sequence_id;
374         tw_dev->error_sequence_id++;
375
376         /* Check for embedded error string */
377         error_str = &(header->err_specific_desc[strlen(header->err_specific_desc)+1]);
378
379         header->err_specific_desc[sizeof(header->err_specific_desc) - 1] = '\0';
380         event->parameter_len = strlen(header->err_specific_desc);
381         memcpy(event->parameter_data, header->err_specific_desc, event->parameter_len);
382         if (event->severity != TW_AEN_SEVERITY_DEBUG)
383                 printk(KERN_WARNING "3w-9xxx:%s AEN: %s (0x%02X:0x%04X): %s:%s.\n",
384                        host,
385                        twa_aen_severity_lookup(TW_SEV_OUT(header->status_block.severity__reserved)),
386                        TW_MESSAGE_SOURCE_CONTROLLER_EVENT, aen,
387                        error_str[0] == '\0' ? twa_string_lookup(twa_aen_table, aen) : error_str,
388                        header->err_specific_desc);
389         else
390                 tw_dev->aen_count--;
391
392         if ((tw_dev->error_index + 1) == TW_Q_LENGTH)
393                 tw_dev->event_queue_wrapped = 1;
394         tw_dev->error_index = (tw_dev->error_index + 1 ) % TW_Q_LENGTH;
395 } /* End twa_aen_queue_event() */
396
397 /* This function will read the aen queue from the isr */
398 static int twa_aen_read_queue(TW_Device_Extension *tw_dev, int request_id)
399 {
400         char cdb[TW_MAX_CDB_LEN];
401         TW_SG_Entry sglist[1];
402         TW_Command_Full *full_command_packet;
403         int retval = 1;
404
405         full_command_packet = tw_dev->command_packet_virt[request_id];
406         memset(full_command_packet, 0, sizeof(TW_Command_Full));
407
408         /* Initialize cdb */
409         memset(&cdb, 0, TW_MAX_CDB_LEN);
410         cdb[0] = REQUEST_SENSE; /* opcode */
411         cdb[4] = TW_ALLOCATION_LENGTH; /* allocation length */
412
413         /* Initialize sglist */
414         memset(&sglist, 0, sizeof(TW_SG_Entry));
415         sglist[0].length = TW_SECTOR_SIZE;
416         sglist[0].address = tw_dev->generic_buffer_phys[request_id];
417
418         /* Mark internal command */
419         tw_dev->srb[request_id] = NULL;
420
421         /* Now post the command packet */
422         if (twa_scsiop_execute_scsi(tw_dev, request_id, cdb, 1, sglist)) {
423                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x4, "Post failed while reading AEN queue");
424                 goto out;
425         }
426         retval = 0;
427 out:
428         return retval;
429 } /* End twa_aen_read_queue() */
430
431 /* This function will look up an AEN severity string */
432 static char *twa_aen_severity_lookup(unsigned char severity_code)
433 {
434         char *retval = NULL;
435
436         if ((severity_code < (unsigned char) TW_AEN_SEVERITY_ERROR) ||
437             (severity_code > (unsigned char) TW_AEN_SEVERITY_DEBUG))
438                 goto out;
439
440         retval = twa_aen_severity_table[severity_code];
441 out:
442         return retval;
443 } /* End twa_aen_severity_lookup() */
444
445 /* This function will sync firmware time with the host time */
446 static void twa_aen_sync_time(TW_Device_Extension *tw_dev, int request_id)
447 {
448         u32 schedulertime;
449         struct timeval utc;
450         TW_Command_Full *full_command_packet;
451         TW_Command *command_packet;
452         TW_Param_Apache *param;
453         u32 local_time;
454
455         /* Fill out the command packet */
456         full_command_packet = tw_dev->command_packet_virt[request_id];
457         memset(full_command_packet, 0, sizeof(TW_Command_Full));
458         command_packet = &full_command_packet->command.oldcommand;
459         command_packet->opcode__sgloffset = TW_OPSGL_IN(2, TW_OP_SET_PARAM);
460         command_packet->request_id = request_id;
461         command_packet->byte8_offset.param.sgl[0].address = tw_dev->generic_buffer_phys[request_id];
462         command_packet->byte8_offset.param.sgl[0].length = TW_SECTOR_SIZE;
463         command_packet->size = TW_COMMAND_SIZE;
464         command_packet->byte6_offset.parameter_count = 1;
465
466         /* Setup the param */
467         param = (TW_Param_Apache *)tw_dev->generic_buffer_virt[request_id];
468         memset(param, 0, TW_SECTOR_SIZE);
469         param->table_id = TW_TIMEKEEP_TABLE | 0x8000; /* Controller time keep table */
470         param->parameter_id = 0x3; /* SchedulerTime */
471         param->parameter_size_bytes = 4;
472
473         /* Convert system time in UTC to local time seconds since last 
474            Sunday 12:00AM */
475         do_gettimeofday(&utc);
476         local_time = (u32)(utc.tv_sec - (sys_tz.tz_minuteswest * 60));
477         schedulertime = local_time - (3 * 86400);
478         schedulertime = schedulertime % 604800;
479
480         memcpy(param->data, &schedulertime, sizeof(u32));
481
482         /* Mark internal command */
483         tw_dev->srb[request_id] = NULL;
484
485         /* Now post the command */
486         twa_post_command_packet(tw_dev, request_id, 1);
487 } /* End twa_aen_sync_time() */
488
489 /* This function will allocate memory and check if it is correctly aligned */
490 static int twa_allocate_memory(TW_Device_Extension *tw_dev, int size, int which)
491 {
492         int i;
493         dma_addr_t dma_handle;
494         unsigned long *cpu_addr;
495         int retval = 1;
496
497         cpu_addr = pci_alloc_consistent(tw_dev->tw_pci_dev, size*TW_Q_LENGTH, &dma_handle);
498         if (!cpu_addr) {
499                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x5, "Memory allocation failed");
500                 goto out;
501         }
502
503         if ((unsigned long)cpu_addr % (TW_ALIGNMENT_9000)) {
504                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x6, "Failed to allocate correctly aligned memory");
505                 pci_free_consistent(tw_dev->tw_pci_dev, size*TW_Q_LENGTH, cpu_addr, dma_handle);
506                 goto out;
507         }
508
509         memset(cpu_addr, 0, size*TW_Q_LENGTH);
510
511         for (i = 0; i < TW_Q_LENGTH; i++) {
512                 switch(which) {
513                 case 0:
514                         tw_dev->command_packet_phys[i] = dma_handle+(i*size);
515                         tw_dev->command_packet_virt[i] = (TW_Command_Full *)((unsigned char *)cpu_addr + (i*size));
516                         break;
517                 case 1:
518                         tw_dev->generic_buffer_phys[i] = dma_handle+(i*size);
519                         tw_dev->generic_buffer_virt[i] = (unsigned long *)((unsigned char *)cpu_addr + (i*size));
520                         break;
521                 }
522         }
523         retval = 0;
524 out:
525         return retval;
526 } /* End twa_allocate_memory() */
527
528 /* This function will check the status register for unexpected bits */
529 static int twa_check_bits(u32 status_reg_value)
530 {
531         int retval = 1;
532
533         if ((status_reg_value & TW_STATUS_EXPECTED_BITS) != TW_STATUS_EXPECTED_BITS)
534                 goto out;
535         if ((status_reg_value & TW_STATUS_UNEXPECTED_BITS) != 0)
536                 goto out;
537
538         retval = 0;
539 out:
540         return retval;
541 } /* End twa_check_bits() */
542
543 /* This function will check the srl and decide if we are compatible  */
544 static int twa_check_srl(TW_Device_Extension *tw_dev, int *flashed)
545 {
546         int retval = 1;
547         unsigned short fw_on_ctlr_srl = 0, fw_on_ctlr_arch_id = 0;
548         unsigned short fw_on_ctlr_branch = 0, fw_on_ctlr_build = 0;
549         u32 init_connect_result = 0;
550
551         if (twa_initconnection(tw_dev, TW_INIT_MESSAGE_CREDITS,
552                                TW_EXTENDED_INIT_CONNECT, TW_CURRENT_DRIVER_SRL,
553                                TW_9000_ARCH_ID, TW_CURRENT_DRIVER_BRANCH,
554                                TW_CURRENT_DRIVER_BUILD, &fw_on_ctlr_srl,
555                                &fw_on_ctlr_arch_id, &fw_on_ctlr_branch,
556                                &fw_on_ctlr_build, &init_connect_result)) {
557                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x7, "Initconnection failed while checking SRL");
558                 goto out;
559         }
560
561         tw_dev->working_srl = fw_on_ctlr_srl;
562         tw_dev->working_branch = fw_on_ctlr_branch;
563         tw_dev->working_build = fw_on_ctlr_build;
564
565         /* Try base mode compatibility */
566         if (!(init_connect_result & TW_CTLR_FW_COMPATIBLE)) {
567                 if (twa_initconnection(tw_dev, TW_INIT_MESSAGE_CREDITS,
568                                        TW_EXTENDED_INIT_CONNECT,
569                                        TW_BASE_FW_SRL, TW_9000_ARCH_ID,
570                                        TW_BASE_FW_BRANCH, TW_BASE_FW_BUILD,
571                                        &fw_on_ctlr_srl, &fw_on_ctlr_arch_id,
572                                        &fw_on_ctlr_branch, &fw_on_ctlr_build,
573                                        &init_connect_result)) {
574                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0xa, "Initconnection (base mode) failed while checking SRL");
575                         goto out;
576                 }
577                 if (!(init_connect_result & TW_CTLR_FW_COMPATIBLE)) {
578                         if (TW_CURRENT_DRIVER_SRL > fw_on_ctlr_srl) {
579                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x32, "Firmware and driver incompatibility: please upgrade firmware");
580                         } else {
581                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x33, "Firmware and driver incompatibility: please upgrade driver");
582                         }
583                         goto out;
584                 }
585                 tw_dev->working_srl = TW_BASE_FW_SRL;
586                 tw_dev->working_branch = TW_BASE_FW_BRANCH;
587                 tw_dev->working_build = TW_BASE_FW_BUILD;
588         }
589         retval = 0;
590 out:
591         return retval;
592 } /* End twa_check_srl() */
593
594 /* This function handles ioctl for the character device */
595 static int twa_chrdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
596 {
597         long timeout;
598         unsigned long *cpu_addr, data_buffer_length_adjusted = 0, flags = 0;
599         dma_addr_t dma_handle;
600         int request_id = 0;
601         unsigned int sequence_id = 0;
602         unsigned char event_index, start_index;
603         TW_Ioctl_Driver_Command driver_command;
604         TW_Ioctl_Buf_Apache *tw_ioctl;
605         TW_Lock *tw_lock;
606         TW_Command_Full *full_command_packet;
607         TW_Compatibility_Info *tw_compat_info;
608         TW_Event *event;
609         struct timeval current_time;
610         u32 current_time_ms;
611         TW_Device_Extension *tw_dev = twa_device_extension_list[iminor(inode)];
612         int retval = TW_IOCTL_ERROR_OS_EFAULT;
613         void __user *argp = (void __user *)arg;
614
615         /* Only let one of these through at a time */
616         if (down_interruptible(&tw_dev->ioctl_sem)) {
617                 retval = TW_IOCTL_ERROR_OS_EINTR;
618                 goto out;
619         }
620
621         /* First copy down the driver command */
622         if (copy_from_user(&driver_command, argp, sizeof(TW_Ioctl_Driver_Command)))
623                 goto out2;
624
625         /* Check data buffer size */
626         if (driver_command.buffer_length > TW_MAX_SECTORS * 512) {
627                 retval = TW_IOCTL_ERROR_OS_EINVAL;
628                 goto out2;
629         }
630
631         /* Hardware can only do multiple of 512 byte transfers */
632         data_buffer_length_adjusted = (driver_command.buffer_length + 511) & ~511;
633
634         /* Now allocate ioctl buf memory */
635         cpu_addr = dma_alloc_coherent(&tw_dev->tw_pci_dev->dev, data_buffer_length_adjusted+sizeof(TW_Ioctl_Buf_Apache) - 1, &dma_handle, GFP_KERNEL);
636         if (!cpu_addr) {
637                 retval = TW_IOCTL_ERROR_OS_ENOMEM;
638                 goto out2;
639         }
640
641         tw_ioctl = (TW_Ioctl_Buf_Apache *)cpu_addr;
642
643         /* Now copy down the entire ioctl */
644         if (copy_from_user(tw_ioctl, argp, driver_command.buffer_length + sizeof(TW_Ioctl_Buf_Apache) - 1))
645                 goto out3;
646
647         /* See which ioctl we are doing */
648         switch (cmd) {
649         case TW_IOCTL_FIRMWARE_PASS_THROUGH:
650                 spin_lock_irqsave(tw_dev->host->host_lock, flags);
651                 twa_get_request_id(tw_dev, &request_id);
652
653                 /* Flag internal command */
654                 tw_dev->srb[request_id] = NULL;
655
656                 /* Flag chrdev ioctl */
657                 tw_dev->chrdev_request_id = request_id;
658
659                 full_command_packet = &tw_ioctl->firmware_command;
660
661                 /* Load request id and sglist for both command types */
662                 twa_load_sgl(full_command_packet, request_id, dma_handle, data_buffer_length_adjusted);
663
664                 memcpy(tw_dev->command_packet_virt[request_id], &(tw_ioctl->firmware_command), sizeof(TW_Command_Full));
665
666                 /* Now post the command packet to the controller */
667                 twa_post_command_packet(tw_dev, request_id, 1);
668                 spin_unlock_irqrestore(tw_dev->host->host_lock, flags);
669
670                 timeout = TW_IOCTL_CHRDEV_TIMEOUT*HZ;
671
672                 /* Now wait for command to complete */
673                 timeout = wait_event_timeout(tw_dev->ioctl_wqueue, tw_dev->chrdev_request_id == TW_IOCTL_CHRDEV_FREE, timeout);
674
675                 /* See if we reset while waiting for the ioctl to complete */
676                 if (test_bit(TW_IN_RESET, &tw_dev->flags)) {
677                         clear_bit(TW_IN_RESET, &tw_dev->flags);
678                         retval = TW_IOCTL_ERROR_OS_ERESTARTSYS;
679                         goto out3;
680                 }
681
682                 /* We timed out, and didn't get an interrupt */
683                 if (tw_dev->chrdev_request_id != TW_IOCTL_CHRDEV_FREE) {
684                         /* Now we need to reset the board */
685                         printk(KERN_WARNING "3w-9xxx: scsi%d: WARNING: (0x%02X:0x%04X): Character ioctl (0x%x) timed out, resetting card.\n",
686                                tw_dev->host->host_no, TW_DRIVER, 0xc,
687                                cmd);
688                         retval = TW_IOCTL_ERROR_OS_EIO;
689                         spin_lock_irqsave(tw_dev->host->host_lock, flags);
690                         tw_dev->state[request_id] = TW_S_COMPLETED;
691                         twa_free_request_id(tw_dev, request_id);
692                         tw_dev->posted_request_count--;
693                         spin_unlock_irqrestore(tw_dev->host->host_lock, flags);
694                         twa_reset_device_extension(tw_dev, 1);
695                         goto out3;
696                 }
697
698                 /* Now copy in the command packet response */
699                 memcpy(&(tw_ioctl->firmware_command), tw_dev->command_packet_virt[request_id], sizeof(TW_Command_Full));
700                 
701                 /* Now complete the io */
702                 spin_lock_irqsave(tw_dev->host->host_lock, flags);
703                 tw_dev->posted_request_count--;
704                 tw_dev->state[request_id] = TW_S_COMPLETED;
705                 twa_free_request_id(tw_dev, request_id);
706                 spin_unlock_irqrestore(tw_dev->host->host_lock, flags);
707                 break;
708         case TW_IOCTL_GET_COMPATIBILITY_INFO:
709                 tw_ioctl->driver_command.status = 0;
710                 /* Copy compatiblity struct into ioctl data buffer */
711                 tw_compat_info = (TW_Compatibility_Info *)tw_ioctl->data_buffer;
712                 strncpy(tw_compat_info->driver_version, TW_DRIVER_VERSION, strlen(TW_DRIVER_VERSION));
713                 tw_compat_info->working_srl = tw_dev->working_srl;
714                 tw_compat_info->working_branch = tw_dev->working_branch;
715                 tw_compat_info->working_build = tw_dev->working_build;
716                 tw_compat_info->driver_srl_high = TW_CURRENT_DRIVER_SRL;
717                 tw_compat_info->driver_branch_high = TW_CURRENT_DRIVER_BRANCH;
718                 tw_compat_info->driver_build_high = TW_CURRENT_DRIVER_BUILD;
719                 tw_compat_info->driver_srl_low = TW_BASE_FW_SRL;
720                 tw_compat_info->driver_branch_low = TW_BASE_FW_BRANCH;
721                 tw_compat_info->driver_build_low = TW_BASE_FW_BUILD;
722                 break;
723         case TW_IOCTL_GET_LAST_EVENT:
724                 if (tw_dev->event_queue_wrapped) {
725                         if (tw_dev->aen_clobber) {
726                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_AEN_CLOBBER;
727                                 tw_dev->aen_clobber = 0;
728                         } else
729                                 tw_ioctl->driver_command.status = 0;
730                 } else {
731                         if (!tw_dev->error_index) {
732                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
733                                 break;
734                         }
735                         tw_ioctl->driver_command.status = 0;
736                 }
737                 event_index = (tw_dev->error_index - 1 + TW_Q_LENGTH) % TW_Q_LENGTH;
738                 memcpy(tw_ioctl->data_buffer, tw_dev->event_queue[event_index], sizeof(TW_Event));
739                 tw_dev->event_queue[event_index]->retrieved = TW_AEN_RETRIEVED;
740                 break;
741         case TW_IOCTL_GET_FIRST_EVENT:
742                 if (tw_dev->event_queue_wrapped) {
743                         if (tw_dev->aen_clobber) {
744                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_AEN_CLOBBER;
745                                 tw_dev->aen_clobber = 0;
746                         } else 
747                                 tw_ioctl->driver_command.status = 0;
748                         event_index = tw_dev->error_index;
749                 } else {
750                         if (!tw_dev->error_index) {
751                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
752                                 break;
753                         }
754                         tw_ioctl->driver_command.status = 0;
755                         event_index = 0;
756                 }
757                 memcpy(tw_ioctl->data_buffer, tw_dev->event_queue[event_index], sizeof(TW_Event));
758                 tw_dev->event_queue[event_index]->retrieved = TW_AEN_RETRIEVED;
759                 break;
760         case TW_IOCTL_GET_NEXT_EVENT:
761                 event = (TW_Event *)tw_ioctl->data_buffer;
762                 sequence_id = event->sequence_id;
763                 tw_ioctl->driver_command.status = 0;
764
765                 if (tw_dev->event_queue_wrapped) {
766                         if (tw_dev->aen_clobber) {
767                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_AEN_CLOBBER;
768                                 tw_dev->aen_clobber = 0;
769                         }
770                         start_index = tw_dev->error_index;
771                 } else {
772                         if (!tw_dev->error_index) {
773                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
774                                 break;
775                         }
776                         start_index = 0;
777                 }
778                 event_index = (start_index + sequence_id - tw_dev->event_queue[start_index]->sequence_id + 1) % TW_Q_LENGTH;
779
780                 if (!(tw_dev->event_queue[event_index]->sequence_id > sequence_id)) {
781                         if (tw_ioctl->driver_command.status == TW_IOCTL_ERROR_STATUS_AEN_CLOBBER)
782                                 tw_dev->aen_clobber = 1;
783                         tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
784                         break;
785                 }
786                 memcpy(tw_ioctl->data_buffer, tw_dev->event_queue[event_index], sizeof(TW_Event));
787                 tw_dev->event_queue[event_index]->retrieved = TW_AEN_RETRIEVED;
788                 break;
789         case TW_IOCTL_GET_PREVIOUS_EVENT:
790                 event = (TW_Event *)tw_ioctl->data_buffer;
791                 sequence_id = event->sequence_id;
792                 tw_ioctl->driver_command.status = 0;
793
794                 if (tw_dev->event_queue_wrapped) {
795                         if (tw_dev->aen_clobber) {
796                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_AEN_CLOBBER;
797                                 tw_dev->aen_clobber = 0;
798                         }
799                         start_index = tw_dev->error_index;
800                 } else {
801                         if (!tw_dev->error_index) {
802                                 tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
803                                 break;
804                         }
805                         start_index = 0;
806                 }
807                 event_index = (start_index + sequence_id - tw_dev->event_queue[start_index]->sequence_id - 1) % TW_Q_LENGTH;
808
809                 if (!(tw_dev->event_queue[event_index]->sequence_id < sequence_id)) {
810                         if (tw_ioctl->driver_command.status == TW_IOCTL_ERROR_STATUS_AEN_CLOBBER)
811                                 tw_dev->aen_clobber = 1;
812                         tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NO_MORE_EVENTS;
813                         break;
814                 }
815                 memcpy(tw_ioctl->data_buffer, tw_dev->event_queue[event_index], sizeof(TW_Event));
816                 tw_dev->event_queue[event_index]->retrieved = TW_AEN_RETRIEVED;
817                 break;
818         case TW_IOCTL_GET_LOCK:
819                 tw_lock = (TW_Lock *)tw_ioctl->data_buffer;
820                 do_gettimeofday(&current_time);
821                 current_time_ms = (current_time.tv_sec * 1000) + (current_time.tv_usec / 1000);
822
823                 if ((tw_lock->force_flag == 1) || (tw_dev->ioctl_sem_lock == 0) || (current_time_ms >= tw_dev->ioctl_msec)) {
824                         tw_dev->ioctl_sem_lock = 1;
825                         tw_dev->ioctl_msec = current_time_ms + tw_lock->timeout_msec;
826                         tw_ioctl->driver_command.status = 0;
827                         tw_lock->time_remaining_msec = tw_lock->timeout_msec;
828                 } else {
829                         tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_LOCKED;
830                         tw_lock->time_remaining_msec = tw_dev->ioctl_msec - current_time_ms;
831                 }
832                 break;
833         case TW_IOCTL_RELEASE_LOCK:
834                 if (tw_dev->ioctl_sem_lock == 1) {
835                         tw_dev->ioctl_sem_lock = 0;
836                         tw_ioctl->driver_command.status = 0;
837                 } else {
838                         tw_ioctl->driver_command.status = TW_IOCTL_ERROR_STATUS_NOT_LOCKED;
839                 }
840                 break;
841         default:
842                 retval = TW_IOCTL_ERROR_OS_ENOTTY;
843                 goto out3;
844         }
845
846         /* Now copy the entire response to userspace */
847         if (copy_to_user(argp, tw_ioctl, sizeof(TW_Ioctl_Buf_Apache) + driver_command.buffer_length - 1) == 0)
848                 retval = 0;
849 out3:
850         /* Now free ioctl buf memory */
851         dma_free_coherent(&tw_dev->tw_pci_dev->dev, data_buffer_length_adjusted+sizeof(TW_Ioctl_Buf_Apache) - 1, cpu_addr, dma_handle);
852 out2:
853         up(&tw_dev->ioctl_sem);
854 out:
855         return retval;
856 } /* End twa_chrdev_ioctl() */
857
858 /* This function handles open for the character device */
859 static int twa_chrdev_open(struct inode *inode, struct file *file)
860 {
861         unsigned int minor_number;
862         int retval = TW_IOCTL_ERROR_OS_ENODEV;
863
864         minor_number = iminor(inode);
865         if (minor_number >= twa_device_extension_count)
866                 goto out;
867         retval = 0;
868 out:
869         return retval;
870 } /* End twa_chrdev_open() */
871
872 /* This function will print readable messages from status register errors */
873 static int twa_decode_bits(TW_Device_Extension *tw_dev, u32 status_reg_value)
874 {
875         int retval = 1;
876
877         /* Check for various error conditions and handle them appropriately */
878         if (status_reg_value & TW_STATUS_PCI_PARITY_ERROR) {
879                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0xc, "PCI Parity Error: clearing");
880                 writel(TW_CONTROL_CLEAR_PARITY_ERROR, TW_CONTROL_REG_ADDR(tw_dev));
881         }
882
883         if (status_reg_value & TW_STATUS_PCI_ABORT) {
884                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0xd, "PCI Abort: clearing");
885                 writel(TW_CONTROL_CLEAR_PCI_ABORT, TW_CONTROL_REG_ADDR(tw_dev));
886                 pci_write_config_word(tw_dev->tw_pci_dev, PCI_STATUS, TW_PCI_CLEAR_PCI_ABORT);
887         }
888
889         if (status_reg_value & TW_STATUS_QUEUE_ERROR) {
890                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0xe, "Controller Queue Error: clearing");
891                 writel(TW_CONTROL_CLEAR_QUEUE_ERROR, TW_CONTROL_REG_ADDR(tw_dev));
892         }
893
894         if (status_reg_value & TW_STATUS_SBUF_WRITE_ERROR) {
895                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0xf, "SBUF Write Error: clearing");
896                 writel(TW_CONTROL_CLEAR_SBUF_WRITE_ERROR, TW_CONTROL_REG_ADDR(tw_dev));
897         }
898
899         if (status_reg_value & TW_STATUS_MICROCONTROLLER_ERROR) {
900                 if (tw_dev->reset_print == 0) {
901                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x10, "Microcontroller Error: clearing");
902                         tw_dev->reset_print = 1;
903                 }
904                 goto out;
905         }
906         retval = 0;
907 out:
908         return retval;
909 } /* End twa_decode_bits() */
910
911 /* This function will empty the response queue */
912 static int twa_empty_response_queue(TW_Device_Extension *tw_dev)
913 {
914         u32 status_reg_value, response_que_value;
915         int count = 0, retval = 1;
916
917         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
918
919         while (((status_reg_value & TW_STATUS_RESPONSE_QUEUE_EMPTY) == 0) && (count < TW_MAX_RESPONSE_DRAIN)) {
920                 response_que_value = readl(TW_RESPONSE_QUEUE_REG_ADDR(tw_dev));
921                 status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
922                 count++;
923         }
924         if (count == TW_MAX_RESPONSE_DRAIN)
925                 goto out;
926
927         retval = 0;
928 out:
929         return retval;
930 } /* End twa_empty_response_queue() */
931
932 /* This function passes sense keys from firmware to scsi layer */
933 static int twa_fill_sense(TW_Device_Extension *tw_dev, int request_id, int copy_sense, int print_host)
934 {
935         TW_Command_Full *full_command_packet;
936         unsigned short error;
937         int retval = 1;
938         char *error_str;
939
940         full_command_packet = tw_dev->command_packet_virt[request_id];
941
942         /* Check for embedded error string */
943         error_str = &(full_command_packet->header.err_specific_desc[strlen(full_command_packet->header.err_specific_desc) + 1]);
944
945         /* Don't print error for Logical unit not supported during rollcall */
946         error = full_command_packet->header.status_block.error;
947         if ((error != TW_ERROR_LOGICAL_UNIT_NOT_SUPPORTED) && (error != TW_ERROR_UNIT_OFFLINE)) {
948                 if (print_host)
949                         printk(KERN_WARNING "3w-9xxx: scsi%d: ERROR: (0x%02X:0x%04X): %s:%s.\n",
950                                tw_dev->host->host_no,
951                                TW_MESSAGE_SOURCE_CONTROLLER_ERROR,
952                                full_command_packet->header.status_block.error,
953                                error_str[0] == '\0' ?
954                                twa_string_lookup(twa_error_table,
955                                                  full_command_packet->header.status_block.error) : error_str,
956                                full_command_packet->header.err_specific_desc);
957                 else
958                         printk(KERN_WARNING "3w-9xxx: ERROR: (0x%02X:0x%04X): %s:%s.\n",
959                                TW_MESSAGE_SOURCE_CONTROLLER_ERROR,
960                                full_command_packet->header.status_block.error,
961                                error_str[0] == '\0' ?
962                                twa_string_lookup(twa_error_table,
963                                                  full_command_packet->header.status_block.error) : error_str,
964                                full_command_packet->header.err_specific_desc);
965         }
966
967         if (copy_sense) {
968                 memcpy(tw_dev->srb[request_id]->sense_buffer, full_command_packet->header.sense_data, TW_SENSE_DATA_LENGTH);
969                 tw_dev->srb[request_id]->result = (full_command_packet->command.newcommand.status << 1);
970                 retval = TW_ISR_DONT_RESULT;
971                 goto out;
972         }
973         retval = 0;
974 out:
975         return retval;
976 } /* End twa_fill_sense() */
977
978 /* This function will free up device extension resources */
979 static void twa_free_device_extension(TW_Device_Extension *tw_dev)
980 {
981         if (tw_dev->command_packet_virt[0])
982                 pci_free_consistent(tw_dev->tw_pci_dev,
983                                     sizeof(TW_Command_Full)*TW_Q_LENGTH,
984                                     tw_dev->command_packet_virt[0],
985                                     tw_dev->command_packet_phys[0]);
986
987         if (tw_dev->generic_buffer_virt[0])
988                 pci_free_consistent(tw_dev->tw_pci_dev,
989                                     TW_SECTOR_SIZE*TW_Q_LENGTH,
990                                     tw_dev->generic_buffer_virt[0],
991                                     tw_dev->generic_buffer_phys[0]);
992
993         if (tw_dev->event_queue[0])
994                 kfree(tw_dev->event_queue[0]);
995 } /* End twa_free_device_extension() */
996
997 /* This function will free a request id */
998 static void twa_free_request_id(TW_Device_Extension *tw_dev, int request_id)
999 {
1000         tw_dev->free_queue[tw_dev->free_tail] = request_id;
1001         tw_dev->state[request_id] = TW_S_FINISHED;
1002         tw_dev->free_tail = (tw_dev->free_tail + 1) % TW_Q_LENGTH;
1003 } /* End twa_free_request_id() */
1004
1005 /* This function will get parameter table entires from the firmware */
1006 static void *twa_get_param(TW_Device_Extension *tw_dev, int request_id, int table_id, int parameter_id, int parameter_size_bytes)
1007 {
1008         TW_Command_Full *full_command_packet;
1009         TW_Command *command_packet;
1010         TW_Param_Apache *param;
1011         unsigned long param_value;
1012         void *retval = NULL;
1013
1014         /* Setup the command packet */
1015         full_command_packet = tw_dev->command_packet_virt[request_id];
1016         memset(full_command_packet, 0, sizeof(TW_Command_Full));
1017         command_packet = &full_command_packet->command.oldcommand;
1018
1019         command_packet->opcode__sgloffset = TW_OPSGL_IN(2, TW_OP_GET_PARAM);
1020         command_packet->size              = TW_COMMAND_SIZE;
1021         command_packet->request_id        = request_id;
1022         command_packet->byte6_offset.block_count = 1;
1023
1024         /* Now setup the param */
1025         param = (TW_Param_Apache *)tw_dev->generic_buffer_virt[request_id];
1026         memset(param, 0, TW_SECTOR_SIZE);
1027         param->table_id = table_id | 0x8000;
1028         param->parameter_id = parameter_id;
1029         param->parameter_size_bytes = parameter_size_bytes;
1030         param_value = tw_dev->generic_buffer_phys[request_id];
1031
1032         command_packet->byte8_offset.param.sgl[0].address = param_value;
1033         command_packet->byte8_offset.param.sgl[0].length = TW_SECTOR_SIZE;
1034
1035         /* Post the command packet to the board */
1036         twa_post_command_packet(tw_dev, request_id, 1);
1037
1038         /* Poll for completion */
1039         if (twa_poll_response(tw_dev, request_id, 30))
1040                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x13, "No valid response during get param")
1041         else
1042                 retval = (void *)&(param->data[0]);
1043
1044         tw_dev->posted_request_count--;
1045         tw_dev->state[request_id] = TW_S_INITIAL;
1046
1047         return retval;
1048 } /* End twa_get_param() */
1049
1050 /* This function will assign an available request id */
1051 static void twa_get_request_id(TW_Device_Extension *tw_dev, int *request_id)
1052 {
1053         *request_id = tw_dev->free_queue[tw_dev->free_head];
1054         tw_dev->free_head = (tw_dev->free_head + 1) % TW_Q_LENGTH;
1055         tw_dev->state[*request_id] = TW_S_STARTED;
1056 } /* End twa_get_request_id() */
1057
1058 /* This function will send an initconnection command to controller */
1059 static int twa_initconnection(TW_Device_Extension *tw_dev, int message_credits,
1060                               u32 set_features, unsigned short current_fw_srl, 
1061                               unsigned short current_fw_arch_id, 
1062                               unsigned short current_fw_branch, 
1063                               unsigned short current_fw_build, 
1064                               unsigned short *fw_on_ctlr_srl, 
1065                               unsigned short *fw_on_ctlr_arch_id, 
1066                               unsigned short *fw_on_ctlr_branch, 
1067                               unsigned short *fw_on_ctlr_build, 
1068                               u32 *init_connect_result)
1069 {
1070         TW_Command_Full *full_command_packet;
1071         TW_Initconnect *tw_initconnect;
1072         int request_id = 0, retval = 1;
1073
1074         /* Initialize InitConnection command packet */
1075         full_command_packet = tw_dev->command_packet_virt[request_id];
1076         memset(full_command_packet, 0, sizeof(TW_Command_Full));
1077         full_command_packet->header.header_desc.size_header = 128;
1078         
1079         tw_initconnect = (TW_Initconnect *)&full_command_packet->command.oldcommand;
1080         tw_initconnect->opcode__reserved = TW_OPRES_IN(0, TW_OP_INIT_CONNECTION);
1081         tw_initconnect->request_id = request_id;
1082         tw_initconnect->message_credits = message_credits;
1083         tw_initconnect->features = set_features;
1084
1085         /* Turn on 64-bit sgl support if we need to */
1086         tw_initconnect->features |= sizeof(dma_addr_t) > 4 ? 1 : 0;
1087
1088         if (set_features & TW_EXTENDED_INIT_CONNECT) {
1089                 tw_initconnect->size = TW_INIT_COMMAND_PACKET_SIZE_EXTENDED;
1090                 tw_initconnect->fw_srl = current_fw_srl;
1091                 tw_initconnect->fw_arch_id = current_fw_arch_id;
1092                 tw_initconnect->fw_branch = current_fw_branch;
1093                 tw_initconnect->fw_build = current_fw_build;
1094         } else 
1095                 tw_initconnect->size = TW_INIT_COMMAND_PACKET_SIZE;
1096
1097         /* Send command packet to the board */
1098         twa_post_command_packet(tw_dev, request_id, 1);
1099
1100         /* Poll for completion */
1101         if (twa_poll_response(tw_dev, request_id, 30)) {
1102                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x15, "No valid response during init connection");
1103         } else {
1104                 if (set_features & TW_EXTENDED_INIT_CONNECT) {
1105                         *fw_on_ctlr_srl = tw_initconnect->fw_srl;
1106                         *fw_on_ctlr_arch_id = tw_initconnect->fw_arch_id;
1107                         *fw_on_ctlr_branch = tw_initconnect->fw_branch;
1108                         *fw_on_ctlr_build = tw_initconnect->fw_build;
1109                         *init_connect_result = tw_initconnect->result;
1110                 }
1111                 retval = 0;
1112         }
1113
1114         tw_dev->posted_request_count--;
1115         tw_dev->state[request_id] = TW_S_INITIAL;
1116
1117         return retval;
1118 } /* End twa_initconnection() */
1119
1120 /* This function will initialize the fields of a device extension */
1121 static int twa_initialize_device_extension(TW_Device_Extension *tw_dev)
1122 {
1123         int i, retval = 1;
1124
1125         /* Initialize command packet buffers */
1126         if (twa_allocate_memory(tw_dev, sizeof(TW_Command_Full), 0)) {
1127                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x16, "Command packet memory allocation failed");
1128                 goto out;
1129         }
1130
1131         /* Initialize generic buffer */
1132         if (twa_allocate_memory(tw_dev, TW_SECTOR_SIZE, 1)) {
1133                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x17, "Generic memory allocation failed");
1134                 goto out;
1135         }
1136
1137         /* Allocate event info space */
1138         tw_dev->event_queue[0] = kmalloc(sizeof(TW_Event) * TW_Q_LENGTH, GFP_KERNEL);
1139         if (!tw_dev->event_queue[0]) {
1140                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x18, "Event info memory allocation failed");
1141                 goto out;
1142         }
1143
1144         memset(tw_dev->event_queue[0], 0, sizeof(TW_Event) * TW_Q_LENGTH);
1145
1146         for (i = 0; i < TW_Q_LENGTH; i++) {
1147                 tw_dev->event_queue[i] = (TW_Event *)((unsigned char *)tw_dev->event_queue[0] + (i * sizeof(TW_Event)));
1148                 tw_dev->free_queue[i] = i;
1149                 tw_dev->state[i] = TW_S_INITIAL;
1150         }
1151
1152         tw_dev->pending_head = TW_Q_START;
1153         tw_dev->pending_tail = TW_Q_START;
1154         tw_dev->free_head = TW_Q_START;
1155         tw_dev->free_tail = TW_Q_START;
1156         tw_dev->error_sequence_id = 1;
1157         tw_dev->chrdev_request_id = TW_IOCTL_CHRDEV_FREE;
1158
1159         init_MUTEX(&tw_dev->ioctl_sem);
1160         init_waitqueue_head(&tw_dev->ioctl_wqueue);
1161
1162         retval = 0;
1163 out:
1164         return retval;
1165 } /* End twa_initialize_device_extension() */
1166
1167 /* This function is the interrupt service routine */
1168 static irqreturn_t twa_interrupt(int irq, void *dev_instance, struct pt_regs *regs)
1169 {
1170         int request_id, error = 0;
1171         u32 status_reg_value;
1172         TW_Response_Queue response_que;
1173         TW_Command_Full *full_command_packet;
1174         TW_Command *command_packet;
1175         TW_Device_Extension *tw_dev = (TW_Device_Extension *)dev_instance;
1176         int handled = 0;
1177
1178         /* Get the per adapter lock */
1179         spin_lock(tw_dev->host->host_lock);
1180
1181         /* Read the registers */
1182         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1183
1184         /* Check if this is our interrupt, otherwise bail */
1185         if (!(status_reg_value & TW_STATUS_VALID_INTERRUPT))
1186                 goto twa_interrupt_bail;
1187
1188         handled = 1;
1189
1190         /* Check controller for errors */
1191         if (twa_check_bits(status_reg_value)) {
1192                 if (twa_decode_bits(tw_dev, status_reg_value)) {
1193                         TW_CLEAR_ALL_INTERRUPTS(tw_dev);
1194                         goto twa_interrupt_bail;
1195                 }
1196         }
1197
1198         /* Handle host interrupt */
1199         if (status_reg_value & TW_STATUS_HOST_INTERRUPT)
1200                 TW_CLEAR_HOST_INTERRUPT(tw_dev);
1201
1202         /* Handle attention interrupt */
1203         if (status_reg_value & TW_STATUS_ATTENTION_INTERRUPT) {
1204                 TW_CLEAR_ATTENTION_INTERRUPT(tw_dev);
1205                 if (!(test_and_set_bit(TW_IN_ATTENTION_LOOP, &tw_dev->flags))) {
1206                         twa_get_request_id(tw_dev, &request_id);
1207
1208                         error = twa_aen_read_queue(tw_dev, request_id);
1209                         if (error) {
1210                                 tw_dev->state[request_id] = TW_S_COMPLETED;
1211                                 twa_free_request_id(tw_dev, request_id);
1212                                 clear_bit(TW_IN_ATTENTION_LOOP, &tw_dev->flags);
1213                         }
1214                 }
1215         }
1216
1217         /* Handle command interrupt */
1218         if (status_reg_value & TW_STATUS_COMMAND_INTERRUPT) {
1219                 TW_MASK_COMMAND_INTERRUPT(tw_dev);
1220                 /* Drain as many pending commands as we can */
1221                 while (tw_dev->pending_request_count > 0) {
1222                         request_id = tw_dev->pending_queue[tw_dev->pending_head];
1223                         if (tw_dev->state[request_id] != TW_S_PENDING) {
1224                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x19, "Found request id that wasn't pending");
1225                                 TW_CLEAR_ALL_INTERRUPTS(tw_dev);
1226                                 goto twa_interrupt_bail;
1227                         }
1228                         if (twa_post_command_packet(tw_dev, request_id, 1)==0) {
1229                                 tw_dev->pending_head = (tw_dev->pending_head + 1) % TW_Q_LENGTH;
1230                                 tw_dev->pending_request_count--;
1231                         } else {
1232                                 /* If we get here, we will continue re-posting on the next command interrupt */
1233                                 break;
1234                         }
1235                 }
1236         }
1237
1238         /* Handle response interrupt */
1239         if (status_reg_value & TW_STATUS_RESPONSE_INTERRUPT) {
1240
1241                 /* Drain the response queue from the board */
1242                 while ((status_reg_value & TW_STATUS_RESPONSE_QUEUE_EMPTY) == 0) {
1243                         /* Complete the response */
1244                         response_que.value = readl(TW_RESPONSE_QUEUE_REG_ADDR(tw_dev));
1245                         request_id = TW_RESID_OUT(response_que.response_id);
1246                         full_command_packet = tw_dev->command_packet_virt[request_id];
1247                         error = 0;
1248                         command_packet = &full_command_packet->command.oldcommand;
1249                         /* Check for command packet errors */
1250                         if (full_command_packet->command.newcommand.status != 0) {
1251                                 if (tw_dev->srb[request_id] != 0) {
1252                                         error = twa_fill_sense(tw_dev, request_id, 1, 1);
1253                                 } else {
1254                                         /* Skip ioctl error prints */
1255                                         if (request_id != tw_dev->chrdev_request_id) {
1256                                                 error = twa_fill_sense(tw_dev, request_id, 0, 1);
1257                                         }
1258                                 }
1259                         }
1260
1261                         /* Check for correct state */
1262                         if (tw_dev->state[request_id] != TW_S_POSTED) {
1263                                 if (tw_dev->srb[request_id] != 0) {
1264                                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1a, "Received a request id that wasn't posted");
1265                                         TW_CLEAR_ALL_INTERRUPTS(tw_dev);
1266                                         goto twa_interrupt_bail;
1267                                 }
1268                         }
1269
1270                         /* Check for internal command completion */
1271                         if (tw_dev->srb[request_id] == 0) {
1272                                 if (request_id != tw_dev->chrdev_request_id) {
1273                                         if (twa_aen_complete(tw_dev, request_id))
1274                                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1b, "Error completing AEN during attention interrupt");
1275                                 } else {
1276                                         tw_dev->chrdev_request_id = TW_IOCTL_CHRDEV_FREE;
1277                                         wake_up(&tw_dev->ioctl_wqueue);
1278                                 }
1279                         } else {
1280                                 twa_scsiop_execute_scsi_complete(tw_dev, request_id);
1281                                 /* If no error command was a success */
1282                                 if (error == 0) {
1283                                         tw_dev->srb[request_id]->result = (DID_OK << 16);
1284                                 }
1285
1286                                 /* If error, command failed */
1287                                 if (error == 1) {
1288                                         /* Ask for a host reset */
1289                                         tw_dev->srb[request_id]->result = (DID_OK << 16) | (CHECK_CONDITION << 1);
1290                                 }
1291
1292                                 /* Report residual bytes for single sgl */
1293                                 if ((tw_dev->srb[request_id]->use_sg <= 1) && (full_command_packet->command.newcommand.status == 0)) {
1294                                         if (full_command_packet->command.newcommand.sg_list[0].length < tw_dev->srb[request_id]->request_bufflen)
1295                                                 tw_dev->srb[request_id]->resid = tw_dev->srb[request_id]->request_bufflen - full_command_packet->command.newcommand.sg_list[0].length;
1296                                 }
1297
1298                                 /* Now complete the io */
1299                                 tw_dev->state[request_id] = TW_S_COMPLETED;
1300                                 twa_free_request_id(tw_dev, request_id);
1301                                 tw_dev->posted_request_count--;
1302                                 tw_dev->srb[request_id]->scsi_done(tw_dev->srb[request_id]);
1303                                 twa_unmap_scsi_data(tw_dev, request_id);
1304                         }
1305
1306                         /* Check for valid status after each drain */
1307                         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1308                         if (twa_check_bits(status_reg_value)) {
1309                                 if (twa_decode_bits(tw_dev, status_reg_value)) {
1310                                         TW_CLEAR_ALL_INTERRUPTS(tw_dev);
1311                                         goto twa_interrupt_bail;
1312                                 }
1313                         }
1314                 }
1315         }
1316
1317 twa_interrupt_bail:
1318         spin_unlock(tw_dev->host->host_lock);
1319         return IRQ_RETVAL(handled);
1320 } /* End twa_interrupt() */
1321
1322 /* This function will load the request id and various sgls for ioctls */
1323 static void twa_load_sgl(TW_Command_Full *full_command_packet, int request_id, dma_addr_t dma_handle, int length)
1324 {
1325         TW_Command *oldcommand;
1326         TW_Command_Apache *newcommand;
1327         TW_SG_Entry *sgl;
1328
1329         if (TW_OP_OUT(full_command_packet->command.newcommand.opcode__reserved) == TW_OP_EXECUTE_SCSI) {
1330                 newcommand = &full_command_packet->command.newcommand;
1331                 newcommand->request_id__lunl = 
1332                         TW_REQ_LUN_IN(TW_LUN_OUT(newcommand->request_id__lunl), request_id);
1333                 newcommand->sg_list[0].address = dma_handle + sizeof(TW_Ioctl_Buf_Apache) - 1;
1334                 newcommand->sg_list[0].length = length;
1335                 newcommand->sgl_entries__lunh =
1336                         TW_REQ_LUN_IN(TW_LUN_OUT(newcommand->sgl_entries__lunh), 1);
1337         } else {
1338                 oldcommand = &full_command_packet->command.oldcommand;
1339                 oldcommand->request_id = request_id;
1340
1341                 if (TW_SGL_OUT(oldcommand->opcode__sgloffset)) {
1342                         /* Load the sg list */
1343                         sgl = (TW_SG_Entry *)((u32 *)oldcommand+TW_SGL_OUT(oldcommand->opcode__sgloffset));
1344                         sgl->address = dma_handle + sizeof(TW_Ioctl_Buf_Apache) - 1;
1345                         sgl->length = length;
1346
1347                         if ((sizeof(long) < 8) && (sizeof(dma_addr_t) > 4))
1348                                 oldcommand->size += 1;
1349                 }
1350         }
1351 } /* End twa_load_sgl() */
1352
1353 /* This function will perform a pci-dma mapping for a scatter gather list */
1354 static int twa_map_scsi_sg_data(TW_Device_Extension *tw_dev, int request_id)
1355 {
1356         int use_sg;
1357         struct scsi_cmnd *cmd = tw_dev->srb[request_id];
1358         struct pci_dev *pdev = tw_dev->tw_pci_dev;
1359         int retval = 0;
1360
1361         if (cmd->use_sg == 0)
1362                 goto out;
1363
1364         use_sg = pci_map_sg(pdev, cmd->buffer, cmd->use_sg, DMA_BIDIRECTIONAL);
1365
1366         if (use_sg == 0) {
1367                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1c, "Failed to map scatter gather list");
1368                 goto out;
1369         }
1370
1371         cmd->SCp.phase = TW_PHASE_SGLIST;
1372         cmd->SCp.have_data_in = use_sg;
1373         retval = use_sg;
1374 out:
1375         return retval;
1376 } /* End twa_map_scsi_sg_data() */
1377
1378 /* This function will perform a pci-dma map for a single buffer */
1379 static dma_addr_t twa_map_scsi_single_data(TW_Device_Extension *tw_dev, int request_id)
1380 {
1381         dma_addr_t mapping;
1382         struct scsi_cmnd *cmd = tw_dev->srb[request_id];
1383         struct pci_dev *pdev = tw_dev->tw_pci_dev;
1384         int retval = 0;
1385
1386         if (cmd->request_bufflen == 0) {
1387                 retval = 0;
1388                 goto out;
1389         }
1390
1391         mapping = pci_map_single(pdev, cmd->request_buffer, cmd->request_bufflen, DMA_BIDIRECTIONAL);
1392
1393         if (mapping == 0) {
1394                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1d, "Failed to map page");
1395                 goto out;
1396         }
1397
1398         cmd->SCp.phase = TW_PHASE_SINGLE;
1399         cmd->SCp.have_data_in = mapping;
1400         retval = mapping;
1401 out:
1402         return retval;
1403 } /* End twa_map_scsi_single_data() */
1404
1405 /* This function will poll for a response interrupt of a request */
1406 static int twa_poll_response(TW_Device_Extension *tw_dev, int request_id, int seconds)
1407 {
1408         int retval = 1, found = 0, response_request_id;
1409         TW_Response_Queue response_queue;
1410         TW_Command_Full *full_command_packet = tw_dev->command_packet_virt[request_id];
1411
1412         if (twa_poll_status_gone(tw_dev, TW_STATUS_RESPONSE_QUEUE_EMPTY, seconds) == 0) {
1413                 response_queue.value = readl(TW_RESPONSE_QUEUE_REG_ADDR(tw_dev));
1414                 response_request_id = TW_RESID_OUT(response_queue.response_id);
1415                 if (request_id != response_request_id) {
1416                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1e, "Found unexpected request id while polling for response");
1417                         goto out;
1418                 }
1419                 if (TW_OP_OUT(full_command_packet->command.newcommand.opcode__reserved) == TW_OP_EXECUTE_SCSI) {
1420                         if (full_command_packet->command.newcommand.status != 0) {
1421                                 /* bad response */
1422                                 twa_fill_sense(tw_dev, request_id, 0, 0);
1423                                 goto out;
1424                         }
1425                         found = 1;
1426                 } else {
1427                         if (full_command_packet->command.oldcommand.status != 0) {
1428                                 /* bad response */
1429                                 twa_fill_sense(tw_dev, request_id, 0, 0);
1430                                 goto out;
1431                         }
1432                         found = 1;
1433                 }
1434         }
1435
1436         if (found)
1437                 retval = 0;
1438 out:
1439         return retval;
1440 } /* End twa_poll_response() */
1441
1442 /* This function will poll the status register for a flag */
1443 static int twa_poll_status(TW_Device_Extension *tw_dev, u32 flag, int seconds)
1444 {
1445         u32 status_reg_value; 
1446         unsigned long before;
1447         int retval = 1;
1448
1449         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1450         before = jiffies;
1451
1452         if (twa_check_bits(status_reg_value))
1453                 twa_decode_bits(tw_dev, status_reg_value);
1454
1455         while ((status_reg_value & flag) != flag) {
1456                 status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1457
1458                 if (twa_check_bits(status_reg_value))
1459                         twa_decode_bits(tw_dev, status_reg_value);
1460
1461                 if (time_after(jiffies, before + HZ * seconds))
1462                         goto out;
1463
1464                 msleep(50);
1465         }
1466         retval = 0;
1467 out:
1468         return retval;
1469 } /* End twa_poll_status() */
1470
1471 /* This function will poll the status register for disappearance of a flag */
1472 static int twa_poll_status_gone(TW_Device_Extension *tw_dev, u32 flag, int seconds)
1473 {
1474         u32 status_reg_value;
1475         unsigned long before;
1476         int retval = 1;
1477
1478         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1479         before = jiffies;
1480
1481         if (twa_check_bits(status_reg_value))
1482                 twa_decode_bits(tw_dev, status_reg_value);
1483
1484         while ((status_reg_value & flag) != 0) {
1485                 status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1486                 if (twa_check_bits(status_reg_value))
1487                         twa_decode_bits(tw_dev, status_reg_value);
1488
1489                 if (time_after(jiffies, before + HZ * seconds))
1490                         goto out;
1491
1492                 msleep(50);
1493         }
1494         retval = 0;
1495 out:
1496         return retval;
1497 } /* End twa_poll_status_gone() */
1498
1499 /* This function will attempt to post a command packet to the board */
1500 static int twa_post_command_packet(TW_Device_Extension *tw_dev, int request_id, char internal)
1501 {
1502         u32 status_reg_value;
1503         dma_addr_t command_que_value;
1504         int retval = 1;
1505
1506         command_que_value = tw_dev->command_packet_phys[request_id];
1507         status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev));
1508
1509         if (twa_check_bits(status_reg_value))
1510                 twa_decode_bits(tw_dev, status_reg_value);
1511
1512         if (((tw_dev->pending_request_count > 0) && (tw_dev->state[request_id] != TW_S_PENDING)) || (status_reg_value & TW_STATUS_COMMAND_QUEUE_FULL)) {
1513
1514                 /* Only pend internal driver commands */
1515                 if (!internal) {
1516                         retval = SCSI_MLQUEUE_HOST_BUSY;
1517                         goto out;
1518                 }
1519
1520                 /* Couldn't post the command packet, so we do it later */
1521                 if (tw_dev->state[request_id] != TW_S_PENDING) {
1522                         tw_dev->state[request_id] = TW_S_PENDING;
1523                         tw_dev->pending_request_count++;
1524                         if (tw_dev->pending_request_count > tw_dev->max_pending_request_count) {
1525                                 tw_dev->max_pending_request_count = tw_dev->pending_request_count;
1526                         }
1527                         tw_dev->pending_queue[tw_dev->pending_tail] = request_id;
1528                         tw_dev->pending_tail = (tw_dev->pending_tail + 1) % TW_Q_LENGTH;
1529                 }
1530                 TW_UNMASK_COMMAND_INTERRUPT(tw_dev);
1531                 goto out;
1532         } else {
1533                 /* We successfully posted the command packet */
1534                 if (sizeof(dma_addr_t) > 4) {
1535                         command_que_value += TW_COMMAND_OFFSET;
1536                         writel((u32)command_que_value, TW_COMMAND_QUEUE_REG_ADDR(tw_dev));
1537                         writel((u32)((u64)command_que_value >> 32), TW_COMMAND_QUEUE_REG_ADDR(tw_dev) + 0x4);
1538                 } else {
1539                         writel(TW_COMMAND_OFFSET + command_que_value, TW_COMMAND_QUEUE_REG_ADDR(tw_dev));
1540                 }
1541                 tw_dev->state[request_id] = TW_S_POSTED;
1542                 tw_dev->posted_request_count++;
1543                 if (tw_dev->posted_request_count > tw_dev->max_posted_request_count) {
1544                         tw_dev->max_posted_request_count = tw_dev->posted_request_count;
1545                 }
1546         }
1547         retval = 0;
1548 out:
1549         return retval;
1550 } /* End twa_post_command_packet() */
1551
1552 /* This function will reset a device extension */
1553 static int twa_reset_device_extension(TW_Device_Extension *tw_dev, int ioctl_reset)
1554 {
1555         int i = 0;
1556         int retval = 1;
1557         unsigned long flags = 0;
1558
1559         set_bit(TW_IN_RESET, &tw_dev->flags);
1560         TW_DISABLE_INTERRUPTS(tw_dev);
1561         TW_MASK_COMMAND_INTERRUPT(tw_dev);
1562         spin_lock_irqsave(tw_dev->host->host_lock, flags);
1563
1564         /* Abort all requests that are in progress */
1565         for (i = 0; i < TW_Q_LENGTH; i++) {
1566                 if ((tw_dev->state[i] != TW_S_FINISHED) &&
1567                     (tw_dev->state[i] != TW_S_INITIAL) &&
1568                     (tw_dev->state[i] != TW_S_COMPLETED)) {
1569                         if (tw_dev->srb[i]) {
1570                                 tw_dev->srb[i]->result = (DID_RESET << 16);
1571                                 tw_dev->srb[i]->scsi_done(tw_dev->srb[i]);
1572                                 twa_unmap_scsi_data(tw_dev, i);
1573                         }
1574                 }
1575         }
1576
1577         /* Reset queues and counts */
1578         for (i = 0; i < TW_Q_LENGTH; i++) {
1579                 tw_dev->free_queue[i] = i;
1580                 tw_dev->state[i] = TW_S_INITIAL;
1581         }
1582         tw_dev->free_head = TW_Q_START;
1583         tw_dev->free_tail = TW_Q_START;
1584         tw_dev->posted_request_count = 0;
1585         tw_dev->pending_request_count = 0;
1586         tw_dev->pending_head = TW_Q_START;
1587         tw_dev->pending_tail = TW_Q_START;
1588         tw_dev->reset_print = 0;
1589
1590         spin_unlock_irqrestore(tw_dev->host->host_lock, flags);
1591
1592         if (twa_reset_sequence(tw_dev, 1))
1593                 goto out;
1594
1595         TW_ENABLE_AND_CLEAR_INTERRUPTS(tw_dev);
1596
1597         /* Wake up any ioctl that was pending before the reset */
1598         if ((tw_dev->chrdev_request_id == TW_IOCTL_CHRDEV_FREE) || (ioctl_reset)) {
1599                 clear_bit(TW_IN_RESET, &tw_dev->flags);
1600         } else {
1601                 tw_dev->chrdev_request_id = TW_IOCTL_CHRDEV_FREE;
1602                 wake_up(&tw_dev->ioctl_wqueue);
1603         }
1604         retval = 0;
1605 out:
1606         return retval;
1607 } /* End twa_reset_device_extension() */
1608
1609 /* This function will reset a controller */
1610 static int twa_reset_sequence(TW_Device_Extension *tw_dev, int soft_reset)
1611 {
1612         int tries = 0, retval = 1, flashed = 0, do_soft_reset = soft_reset;
1613
1614         while (tries < TW_MAX_RESET_TRIES) {
1615                 if (do_soft_reset)
1616                         TW_SOFT_RESET(tw_dev);
1617
1618                 /* Make sure controller is in a good state */
1619                 if (twa_poll_status(tw_dev, TW_STATUS_MICROCONTROLLER_READY | (do_soft_reset == 1 ? TW_STATUS_ATTENTION_INTERRUPT : 0), 60)) {
1620                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x1f, "Microcontroller not ready during reset sequence");
1621                         do_soft_reset = 1;
1622                         tries++;
1623                         continue;
1624                 }
1625
1626                 /* Empty response queue */
1627                 if (twa_empty_response_queue(tw_dev)) {
1628                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x20, "Response queue empty failed during reset sequence");
1629                         do_soft_reset = 1;
1630                         tries++;
1631                         continue;
1632                 }
1633
1634                 flashed = 0;
1635
1636                 /* Check for compatibility/flash */
1637                 if (twa_check_srl(tw_dev, &flashed)) {
1638                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x21, "Compatibility check failed during reset sequence");
1639                         do_soft_reset = 1;
1640                         tries++;
1641                         continue;
1642                 } else {
1643                         if (flashed) {
1644                                 tries++;
1645                                 continue;
1646                         }
1647                 }
1648
1649                 /* Drain the AEN queue */
1650                 if (twa_aen_drain_queue(tw_dev, soft_reset)) {
1651                         TW_PRINTK(tw_dev->host, TW_DRIVER, 0x22, "AEN drain failed during reset sequence");
1652                         do_soft_reset = 1;
1653                         tries++;
1654                         continue;
1655                 }
1656
1657                 /* If we got here, controller is in a good state */
1658                 retval = 0;
1659                 goto out;
1660         }
1661 out:
1662         return retval;
1663 } /* End twa_reset_sequence() */
1664
1665 /* This funciton returns unit geometry in cylinders/heads/sectors */
1666 static int twa_scsi_biosparam(struct scsi_device *sdev, struct block_device *bdev, sector_t capacity, int geom[])
1667 {
1668         int heads, sectors, cylinders;
1669         TW_Device_Extension *tw_dev;
1670
1671         tw_dev = (TW_Device_Extension *)sdev->host->hostdata;
1672
1673         if (capacity >= 0x200000) {
1674                 heads = 255;
1675                 sectors = 63;
1676                 cylinders = sector_div(capacity, heads * sectors);
1677         } else {
1678                 heads = 64;
1679                 sectors = 32;
1680                 cylinders = sector_div(capacity, heads * sectors);
1681         }
1682
1683         geom[0] = heads;
1684         geom[1] = sectors;
1685         geom[2] = cylinders;
1686
1687         return 0;
1688 } /* End twa_scsi_biosparam() */
1689
1690 /* This is the new scsi eh reset function */
1691 static int twa_scsi_eh_reset(struct scsi_cmnd *SCpnt)
1692 {
1693         TW_Device_Extension *tw_dev = NULL;
1694         int retval = FAILED;
1695
1696         tw_dev = (TW_Device_Extension *)SCpnt->device->host->hostdata;
1697
1698         tw_dev->num_resets++;
1699
1700         printk(KERN_WARNING "3w-9xxx: scsi%d: WARNING: (0x%02X:0x%04X): Unit #%d: Command (0x%x) timed out, resetting card.\n", tw_dev->host->host_no, TW_DRIVER, 0x2c, SCpnt->device->id, SCpnt->cmnd[0]);
1701
1702         /* Now reset the card and some of the device extension data */
1703         if (twa_reset_device_extension(tw_dev, 0)) {
1704                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x2b, "Controller reset failed during scsi host reset");
1705                 goto out;
1706         }
1707
1708         retval = SUCCESS;
1709 out:
1710         return retval;
1711 } /* End twa_scsi_eh_reset() */
1712
1713 /* This is the main scsi queue function to handle scsi opcodes */
1714 static int twa_scsi_queue(struct scsi_cmnd *SCpnt, void (*done)(struct scsi_cmnd *))
1715 {
1716         int request_id, retval;
1717         TW_Device_Extension *tw_dev = (TW_Device_Extension *)SCpnt->device->host->hostdata;
1718
1719         /* Check if this FW supports luns */
1720         if ((SCpnt->device->lun != 0) && (tw_dev->working_srl < TW_FW_SRL_LUNS_SUPPORTED)) {
1721                 SCpnt->result = (DID_BAD_TARGET << 16);
1722                 done(SCpnt);
1723                 retval = 0;
1724                 goto out;
1725         }
1726
1727         /* Save done function into scsi_cmnd struct */
1728         SCpnt->scsi_done = done;
1729                 
1730         /* Get a free request id */
1731         twa_get_request_id(tw_dev, &request_id);
1732
1733         /* Save the scsi command for use by the ISR */
1734         tw_dev->srb[request_id] = SCpnt;
1735
1736         /* Initialize phase to zero */
1737         SCpnt->SCp.phase = TW_PHASE_INITIAL;
1738
1739         retval = twa_scsiop_execute_scsi(tw_dev, request_id, NULL, 0, NULL);
1740         switch (retval) {
1741         case SCSI_MLQUEUE_HOST_BUSY:
1742                 twa_free_request_id(tw_dev, request_id);
1743                 break;
1744         case 1:
1745                 tw_dev->state[request_id] = TW_S_COMPLETED;
1746                 twa_free_request_id(tw_dev, request_id);
1747                 SCpnt->result = (DID_ERROR << 16);
1748                 done(SCpnt);
1749                 retval = 0;
1750         }
1751 out:
1752         return retval;
1753 } /* End twa_scsi_queue() */
1754
1755 /* This function hands scsi cdb's to the firmware */
1756 static int twa_scsiop_execute_scsi(TW_Device_Extension *tw_dev, int request_id, char *cdb, int use_sg, TW_SG_Entry *sglistarg)
1757 {
1758         TW_Command_Full *full_command_packet;
1759         TW_Command_Apache *command_packet;
1760         u32 num_sectors = 0x0;
1761         int i, sg_count;
1762         struct scsi_cmnd *srb = NULL;
1763         struct scatterlist *sglist = NULL;
1764         u32 buffaddr = 0x0;
1765         int retval = 1;
1766
1767         if (tw_dev->srb[request_id]) {
1768                 if (tw_dev->srb[request_id]->request_buffer) {
1769                         sglist = (struct scatterlist *)tw_dev->srb[request_id]->request_buffer;
1770                 }
1771                 srb = tw_dev->srb[request_id];
1772         }
1773
1774         /* Initialize command packet */
1775         full_command_packet = tw_dev->command_packet_virt[request_id];
1776         full_command_packet->header.header_desc.size_header = 128;
1777         full_command_packet->header.status_block.error = 0;
1778         full_command_packet->header.status_block.severity__reserved = 0;
1779
1780         command_packet = &full_command_packet->command.newcommand;
1781         command_packet->status = 0;
1782         command_packet->opcode__reserved = TW_OPRES_IN(0, TW_OP_EXECUTE_SCSI);
1783
1784         /* We forced 16 byte cdb use earlier */
1785         if (!cdb)
1786                 memcpy(command_packet->cdb, srb->cmnd, TW_MAX_CDB_LEN);
1787         else
1788                 memcpy(command_packet->cdb, cdb, TW_MAX_CDB_LEN);
1789
1790         if (srb) {
1791                 command_packet->unit = srb->device->id;
1792                 command_packet->request_id__lunl =
1793                         TW_REQ_LUN_IN(srb->device->lun, request_id);
1794         } else {
1795                 command_packet->request_id__lunl =
1796                         TW_REQ_LUN_IN(0, request_id);
1797                 command_packet->unit = 0;
1798         }
1799
1800         command_packet->sgl_offset = 16;
1801
1802         if (!sglistarg) {
1803                 /* Map sglist from scsi layer to cmd packet */
1804                 if (tw_dev->srb[request_id]->use_sg == 0) {
1805                         if (tw_dev->srb[request_id]->request_bufflen < TW_MIN_SGL_LENGTH) {
1806                                 command_packet->sg_list[0].address = tw_dev->generic_buffer_phys[request_id];
1807                                 command_packet->sg_list[0].length = TW_MIN_SGL_LENGTH;
1808                         } else {
1809                                 buffaddr = twa_map_scsi_single_data(tw_dev, request_id);
1810                                 if (buffaddr == 0)
1811                                         goto out;
1812
1813                                 command_packet->sg_list[0].address = buffaddr;
1814                                 command_packet->sg_list[0].length = tw_dev->srb[request_id]->request_bufflen;
1815                         }
1816                         command_packet->sgl_entries__lunh = TW_REQ_LUN_IN((srb->device->lun >> 4), 1);
1817
1818                         if (command_packet->sg_list[0].address & TW_ALIGNMENT_9000_SGL) {
1819                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x2d, "Found unaligned address during execute scsi");
1820                                 goto out;
1821                         }
1822                 }
1823
1824                 if (tw_dev->srb[request_id]->use_sg > 0) {
1825                         if ((tw_dev->srb[request_id]->use_sg == 1) && (tw_dev->srb[request_id]->request_bufflen < TW_MIN_SGL_LENGTH)) {
1826                                 command_packet->sg_list[0].address = tw_dev->generic_buffer_phys[request_id];
1827                                 command_packet->sg_list[0].length = TW_MIN_SGL_LENGTH;
1828                         } else {
1829                                 sg_count = twa_map_scsi_sg_data(tw_dev, request_id);
1830                                 if (sg_count == 0)
1831                                         goto out;
1832
1833                                 for (i = 0; i < sg_count; i++) {
1834                                         command_packet->sg_list[i].address = sg_dma_address(&sglist[i]);
1835                                         command_packet->sg_list[i].length = sg_dma_len(&sglist[i]);
1836                                         if (command_packet->sg_list[i].address & TW_ALIGNMENT_9000_SGL) {
1837                                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x2e, "Found unaligned sgl address during execute scsi");
1838                                                 goto out;
1839                                         }
1840                                 }
1841                         }
1842                         command_packet->sgl_entries__lunh = TW_REQ_LUN_IN((srb->device->lun >> 4), tw_dev->srb[request_id]->use_sg);
1843                 }
1844         } else {
1845                 /* Internal cdb post */
1846                 for (i = 0; i < use_sg; i++) {
1847                         command_packet->sg_list[i].address = sglistarg[i].address;
1848                         command_packet->sg_list[i].length = sglistarg[i].length;
1849                         if (command_packet->sg_list[i].address & TW_ALIGNMENT_9000_SGL) {
1850                                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x2f, "Found unaligned sgl address during internal post");
1851                                 goto out;
1852                         }
1853                 }
1854                 command_packet->sgl_entries__lunh = TW_REQ_LUN_IN(0, use_sg);
1855         }
1856
1857         if (srb) {
1858                 if (srb->cmnd[0] == READ_6 || srb->cmnd[0] == WRITE_6)
1859                         num_sectors = (u32)srb->cmnd[4];
1860
1861                 if (srb->cmnd[0] == READ_10 || srb->cmnd[0] == WRITE_10)
1862                         num_sectors = (u32)srb->cmnd[8] | ((u32)srb->cmnd[7] << 8);
1863         }
1864
1865         /* Update sector statistic */
1866         tw_dev->sector_count = num_sectors;
1867         if (tw_dev->sector_count > tw_dev->max_sector_count)
1868                 tw_dev->max_sector_count = tw_dev->sector_count;
1869
1870         /* Update SG statistics */
1871         if (srb) {
1872                 tw_dev->sgl_entries = tw_dev->srb[request_id]->use_sg;
1873                 if (tw_dev->sgl_entries > tw_dev->max_sgl_entries)
1874                         tw_dev->max_sgl_entries = tw_dev->sgl_entries;
1875         }
1876
1877         /* Now post the command to the board */
1878         if (srb) {
1879                 retval = twa_post_command_packet(tw_dev, request_id, 0);
1880         } else {
1881                 twa_post_command_packet(tw_dev, request_id, 1);
1882                 retval = 0;
1883         }
1884 out:
1885         return retval;
1886 } /* End twa_scsiop_execute_scsi() */
1887
1888 /* This function completes an execute scsi operation */
1889 static void twa_scsiop_execute_scsi_complete(TW_Device_Extension *tw_dev, int request_id)
1890 {
1891         /* Copy the response if too small */
1892         if ((tw_dev->srb[request_id]->request_buffer) && (tw_dev->srb[request_id]->request_bufflen < TW_MIN_SGL_LENGTH)) {
1893                 memcpy(tw_dev->srb[request_id]->request_buffer,
1894                        tw_dev->generic_buffer_virt[request_id],
1895                        tw_dev->srb[request_id]->request_bufflen);
1896         }
1897 } /* End twa_scsiop_execute_scsi_complete() */
1898
1899 /* This function tells the controller to shut down */
1900 static void __twa_shutdown(TW_Device_Extension *tw_dev)
1901 {
1902         /* Disable interrupts */
1903         TW_DISABLE_INTERRUPTS(tw_dev);
1904
1905         printk(KERN_WARNING "3w-9xxx: Shutting down host %d.\n", tw_dev->host->host_no);
1906
1907         /* Tell the card we are shutting down */
1908         if (twa_initconnection(tw_dev, 1, 0, 0, 0, 0, 0, NULL, NULL, NULL, NULL, NULL)) {
1909                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x31, "Connection shutdown failed");
1910         } else {
1911                 printk(KERN_WARNING "3w-9xxx: Shutdown complete.\n");
1912         }
1913
1914         /* Clear all interrupts just before exit */
1915         TW_CLEAR_ALL_INTERRUPTS(tw_dev);
1916 } /* End __twa_shutdown() */
1917
1918 /* Wrapper for __twa_shutdown */
1919 static void twa_shutdown(struct pci_dev *pdev)
1920 {
1921         struct Scsi_Host *host = pci_get_drvdata(pdev);
1922         TW_Device_Extension *tw_dev = (TW_Device_Extension *)host->hostdata;
1923
1924         __twa_shutdown(tw_dev);
1925 } /* End twa_shutdown() */
1926
1927 /* This function will look up a string */
1928 static char *twa_string_lookup(twa_message_type *table, unsigned int code)
1929 {
1930         int index;
1931
1932         for (index = 0; ((code != table[index].code) &&
1933                       (table[index].text != (char *)0)); index++);
1934         return(table[index].text);
1935 } /* End twa_string_lookup() */
1936
1937 /* This function will perform a pci-dma unmap */
1938 static void twa_unmap_scsi_data(TW_Device_Extension *tw_dev, int request_id)
1939 {
1940         struct scsi_cmnd *cmd = tw_dev->srb[request_id];
1941         struct pci_dev *pdev = tw_dev->tw_pci_dev;
1942
1943         switch(cmd->SCp.phase) {
1944         case TW_PHASE_SINGLE:
1945                 pci_unmap_single(pdev, cmd->SCp.have_data_in, cmd->request_bufflen, DMA_BIDIRECTIONAL);
1946                 break;
1947         case TW_PHASE_SGLIST:
1948                 pci_unmap_sg(pdev, cmd->request_buffer, cmd->use_sg, DMA_BIDIRECTIONAL);
1949                 break;
1950         }
1951 } /* End twa_unmap_scsi_data() */
1952
1953 /* scsi_host_template initializer */
1954 static struct scsi_host_template driver_template = {
1955         .module                 = THIS_MODULE,
1956         .name                   = "3ware 9000 Storage Controller",
1957         .queuecommand           = twa_scsi_queue,
1958         .eh_host_reset_handler  = twa_scsi_eh_reset,
1959         .bios_param             = twa_scsi_biosparam,
1960         .change_queue_depth     = twa_change_queue_depth,
1961         .can_queue              = TW_Q_LENGTH-2,
1962         .this_id                = -1,
1963         .sg_tablesize           = TW_APACHE_MAX_SGL_LENGTH,
1964         .max_sectors            = TW_MAX_SECTORS,
1965         .cmd_per_lun            = TW_MAX_CMDS_PER_LUN,
1966         .use_clustering         = ENABLE_CLUSTERING,
1967         .shost_attrs            = twa_host_attrs,
1968         .emulated               = 1
1969 };
1970
1971 /* This function will probe and initialize a card */
1972 static int __devinit twa_probe(struct pci_dev *pdev, const struct pci_device_id *dev_id)
1973 {
1974         struct Scsi_Host *host = NULL;
1975         TW_Device_Extension *tw_dev;
1976         u32 mem_addr;
1977         int retval = -ENODEV;
1978
1979         retval = pci_enable_device(pdev);
1980         if (retval) {
1981                 TW_PRINTK(host, TW_DRIVER, 0x34, "Failed to enable pci device");
1982                 goto out_disable_device;
1983         }
1984
1985         pci_set_master(pdev);
1986
1987         retval = pci_set_dma_mask(pdev, sizeof(dma_addr_t) > 4 ? DMA_64BIT_MASK : DMA_32BIT_MASK);
1988         if (retval) {
1989                 TW_PRINTK(host, TW_DRIVER, 0x23, "Failed to set dma mask");
1990                 goto out_disable_device;
1991         }
1992
1993         host = scsi_host_alloc(&driver_template, sizeof(TW_Device_Extension));
1994         if (!host) {
1995                 TW_PRINTK(host, TW_DRIVER, 0x24, "Failed to allocate memory for device extension");
1996                 retval = -ENOMEM;
1997                 goto out_disable_device;
1998         }
1999         tw_dev = (TW_Device_Extension *)host->hostdata;
2000
2001         memset(tw_dev, 0, sizeof(TW_Device_Extension));
2002
2003         /* Save values to device extension */
2004         tw_dev->host = host;
2005         tw_dev->tw_pci_dev = pdev;
2006
2007         if (twa_initialize_device_extension(tw_dev)) {
2008                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x25, "Failed to initialize device extension");
2009                 goto out_free_device_extension;
2010         }
2011
2012         /* Request IO regions */
2013         retval = pci_request_regions(pdev, "3w-9xxx");
2014         if (retval) {
2015                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x26, "Failed to get mem region");
2016                 goto out_free_device_extension;
2017         }
2018
2019         mem_addr = pci_resource_start(pdev, 1);
2020
2021         /* Save base address */
2022         tw_dev->base_addr = ioremap(mem_addr, PAGE_SIZE);
2023         if (!tw_dev->base_addr) {
2024                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x35, "Failed to ioremap");
2025                 goto out_release_mem_region;
2026         }
2027
2028         /* Disable interrupts on the card */
2029         TW_DISABLE_INTERRUPTS(tw_dev);
2030
2031         /* Initialize the card */
2032         if (twa_reset_sequence(tw_dev, 0))
2033                 goto out_release_mem_region;
2034
2035         /* Set host specific parameters */
2036         host->max_id = TW_MAX_UNITS;
2037         host->max_cmd_len = TW_MAX_CDB_LEN;
2038
2039         /* Channels aren't supported by adapter */
2040         host->max_lun = TW_MAX_LUNS(tw_dev->working_srl);
2041         host->max_channel = 0;
2042
2043         /* Register the card with the kernel SCSI layer */
2044         retval = scsi_add_host(host, &pdev->dev);
2045         if (retval) {
2046                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x27, "scsi add host failed");
2047                 goto out_release_mem_region;
2048         }
2049
2050         pci_set_drvdata(pdev, host);
2051
2052         printk(KERN_WARNING "3w-9xxx: scsi%d: Found a 3ware 9000 Storage Controller at 0x%x, IRQ: %d.\n",
2053                host->host_no, mem_addr, pdev->irq);
2054         printk(KERN_WARNING "3w-9xxx: scsi%d: Firmware %s, BIOS %s, Ports: %d.\n",
2055                host->host_no,
2056                (char *)twa_get_param(tw_dev, 0, TW_VERSION_TABLE,
2057                                      TW_PARAM_FWVER, TW_PARAM_FWVER_LENGTH),
2058                (char *)twa_get_param(tw_dev, 1, TW_VERSION_TABLE,
2059                                      TW_PARAM_BIOSVER, TW_PARAM_BIOSVER_LENGTH),
2060                *(int *)twa_get_param(tw_dev, 2, TW_INFORMATION_TABLE,
2061                                      TW_PARAM_PORTCOUNT, TW_PARAM_PORTCOUNT_LENGTH));
2062
2063         /* Now setup the interrupt handler */
2064         retval = request_irq(pdev->irq, twa_interrupt, SA_SHIRQ, "3w-9xxx", tw_dev);
2065         if (retval) {
2066                 TW_PRINTK(tw_dev->host, TW_DRIVER, 0x30, "Error requesting IRQ");
2067                 goto out_remove_host;
2068         }
2069
2070         twa_device_extension_list[twa_device_extension_count] = tw_dev;
2071         twa_device_extension_count++;
2072
2073         /* Re-enable interrupts on the card */
2074         TW_ENABLE_AND_CLEAR_INTERRUPTS(tw_dev);
2075
2076         /* Finally, scan the host */
2077         scsi_scan_host(host);
2078
2079         if (twa_major == -1) {
2080                 if ((twa_major = register_chrdev (0, "twa", &twa_fops)) < 0)
2081                         TW_PRINTK(host, TW_DRIVER, 0x29, "Failed to register character device");
2082         }
2083         return 0;
2084
2085 out_remove_host:
2086         scsi_remove_host(host);
2087 out_release_mem_region:
2088         pci_release_regions(pdev);
2089 out_free_device_extension:
2090         twa_free_device_extension(tw_dev);
2091         scsi_host_put(host);
2092 out_disable_device:
2093         pci_disable_device(pdev);
2094
2095         return retval;
2096 } /* End twa_probe() */
2097
2098 /* This function is called to remove a device */
2099 static void twa_remove(struct pci_dev *pdev)
2100 {
2101         struct Scsi_Host *host = pci_get_drvdata(pdev);
2102         TW_Device_Extension *tw_dev = (TW_Device_Extension *)host->hostdata;
2103
2104         scsi_remove_host(tw_dev->host);
2105
2106         /* Unregister character device */
2107         if (twa_major >= 0) {
2108                 unregister_chrdev(twa_major, "twa");
2109                 twa_major = -1;
2110         }
2111
2112         /* Free up the IRQ */
2113         free_irq(tw_dev->tw_pci_dev->irq, tw_dev);
2114
2115         /* Shutdown the card */
2116         __twa_shutdown(tw_dev);
2117
2118         /* Free up the mem region */
2119         pci_release_regions(pdev);
2120
2121         /* Free up device extension resources */
2122         twa_free_device_extension(tw_dev);
2123
2124         scsi_host_put(tw_dev->host);
2125         pci_disable_device(pdev);
2126         twa_device_extension_count--;
2127 } /* End twa_remove() */
2128
2129 /* PCI Devices supported by this driver */
2130 static struct pci_device_id twa_pci_tbl[] __devinitdata = {
2131         { PCI_VENDOR_ID_3WARE, PCI_DEVICE_ID_3WARE_9000,
2132           PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
2133         { }
2134 };
2135 MODULE_DEVICE_TABLE(pci, twa_pci_tbl);
2136
2137 /* pci_driver initializer */
2138 static struct pci_driver twa_driver = {
2139         .name           = "3w-9xxx",
2140         .id_table       = twa_pci_tbl,
2141         .probe          = twa_probe,
2142         .remove         = twa_remove,
2143         .shutdown       = twa_shutdown
2144 };
2145
2146 /* This function is called on driver initialization */
2147 static int __init twa_init(void)
2148 {
2149         printk(KERN_WARNING "3ware 9000 Storage Controller device driver for Linux v%s.\n", TW_DRIVER_VERSION);
2150
2151         return pci_module_init(&twa_driver);
2152 } /* End twa_init() */
2153
2154 /* This function is called on driver exit */
2155 static void __exit twa_exit(void)
2156 {
2157         pci_unregister_driver(&twa_driver);
2158 } /* End twa_exit() */
2159
2160 module_init(twa_init);
2161 module_exit(twa_exit);
2162