[SCSI] advansys: Clean up proc_info implementation
[safe/jmp/linux-2.6] / drivers / scsi / advansys.c
1 #define ASC_VERSION "3.4"       /* AdvanSys Driver Version */
2
3 /*
4  * advansys.c - Linux Host Driver for AdvanSys SCSI Adapters
5  *
6  * Copyright (c) 1995-2000 Advanced System Products, Inc.
7  * Copyright (c) 2000-2001 ConnectCom Solutions, Inc.
8  * Copyright (c) 2007 Matthew Wilcox <matthew@wil.cx>
9  * All Rights Reserved.
10  *
11  * This program is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  */
16
17 /*
18  * As of March 8, 2000 Advanced System Products, Inc. (AdvanSys)
19  * changed its name to ConnectCom Solutions, Inc.
20  * On June 18, 2001 Initio Corp. acquired ConnectCom's SCSI assets
21  */
22
23 /*
24
25   Documentation for the AdvanSys Driver
26
27   A. Linux Kernels Supported by this Driver
28   B. Adapters Supported by this Driver
29   C. Linux source files modified by AdvanSys Driver
30   D. Source Comments
31   E. Driver Compile Time Options and Debugging
32   F. Driver LILO Option
33   G. Tests to run before releasing new driver
34   H. Release History
35   I. Known Problems/Fix List
36   J. Credits (Chronological Order)
37
38   A. Linux Kernels Supported by this Driver
39
40      This driver has been tested in the following Linux kernels: v2.2.18
41      v2.4.0. The driver is supported on v2.2 and v2.4 kernels and on x86,
42      alpha, and PowerPC platforms.
43
44   B. Adapters Supported by this Driver
45
46      AdvanSys (Advanced System Products, Inc.) manufactures the following
47      RISC-based, Bus-Mastering, Fast (10 Mhz) and Ultra (20 Mhz) Narrow
48      (8-bit transfer) SCSI Host Adapters for the ISA, EISA, VL, and PCI
49      buses and RISC-based, Bus-Mastering, Ultra (20 Mhz) Wide (16-bit
50      transfer) SCSI Host Adapters for the PCI bus.
51
52      The CDB counts below indicate the number of SCSI CDB (Command
53      Descriptor Block) requests that can be stored in the RISC chip
54      cache and board LRAM. A CDB is a single SCSI command. The driver
55      detect routine will display the number of CDBs available for each
56      adapter detected. The number of CDBs used by the driver can be
57      lowered in the BIOS by changing the 'Host Queue Size' adapter setting.
58
59      Laptop Products:
60         ABP-480 - Bus-Master CardBus (16 CDB) (2.4 kernel and greater)
61
62      Connectivity Products:
63         ABP510/5150 - Bus-Master ISA (240 CDB)
64         ABP5140 - Bus-Master ISA PnP (16 CDB)
65         ABP5142 - Bus-Master ISA PnP with floppy (16 CDB)
66         ABP902/3902 - Bus-Master PCI (16 CDB)
67         ABP3905 - Bus-Master PCI (16 CDB)
68         ABP915 - Bus-Master PCI (16 CDB)
69         ABP920 - Bus-Master PCI (16 CDB)
70         ABP3922 - Bus-Master PCI (16 CDB)
71         ABP3925 - Bus-Master PCI (16 CDB)
72         ABP930 - Bus-Master PCI (16 CDB)
73         ABP930U - Bus-Master PCI Ultra (16 CDB)
74         ABP930UA - Bus-Master PCI Ultra (16 CDB)
75         ABP960 - Bus-Master PCI MAC/PC (16 CDB)
76         ABP960U - Bus-Master PCI MAC/PC Ultra (16 CDB)
77
78      Single Channel Products:
79         ABP542 - Bus-Master ISA with floppy (240 CDB)
80         ABP742 - Bus-Master EISA (240 CDB)
81         ABP842 - Bus-Master VL (240 CDB)
82         ABP940 - Bus-Master PCI (240 CDB)
83         ABP940U - Bus-Master PCI Ultra (240 CDB)
84         ABP940UA/3940UA - Bus-Master PCI Ultra (240 CDB)
85         ABP970 - Bus-Master PCI MAC/PC (240 CDB)
86         ABP970U - Bus-Master PCI MAC/PC Ultra (240 CDB)
87         ABP3960UA - Bus-Master PCI MAC/PC Ultra (240 CDB)
88         ABP940UW/3940UW - Bus-Master PCI Ultra-Wide (253 CDB)
89         ABP970UW - Bus-Master PCI MAC/PC Ultra-Wide (253 CDB)
90         ABP3940U2W - Bus-Master PCI LVD/Ultra2-Wide (253 CDB)
91
92      Multi-Channel Products:
93         ABP752 - Dual Channel Bus-Master EISA (240 CDB Per Channel)
94         ABP852 - Dual Channel Bus-Master VL (240 CDB Per Channel)
95         ABP950 - Dual Channel Bus-Master PCI (240 CDB Per Channel)
96         ABP950UW - Dual Channel Bus-Master PCI Ultra-Wide (253 CDB Per Channel)
97         ABP980 - Four Channel Bus-Master PCI (240 CDB Per Channel)
98         ABP980U - Four Channel Bus-Master PCI Ultra (240 CDB Per Channel)
99         ABP980UA/3980UA - Four Channel Bus-Master PCI Ultra (16 CDB Per Chan.)
100         ABP3950U2W - Bus-Master PCI LVD/Ultra2-Wide and Ultra-Wide (253 CDB)
101         ABP3950U3W - Bus-Master PCI Dual LVD2/Ultra3-Wide (253 CDB)
102
103   C. Linux source files modified by AdvanSys Driver
104
105      This section for historical purposes documents the changes
106      originally made to the Linux kernel source to add the advansys
107      driver. As Linux has changed some of these files have also
108      been modified.
109
110      1. linux/arch/i386/config.in:
111
112           bool 'AdvanSys SCSI support' CONFIG_SCSI_ADVANSYS y
113
114      2. linux/drivers/scsi/hosts.c:
115
116           #ifdef CONFIG_SCSI_ADVANSYS
117           #include "advansys.h"
118           #endif
119
120         and after "static struct scsi_host_template builtin_scsi_hosts[] =":
121
122           #ifdef CONFIG_SCSI_ADVANSYS
123           ADVANSYS,
124           #endif
125
126      3. linux/drivers/scsi/Makefile:
127
128           ifdef CONFIG_SCSI_ADVANSYS
129           SCSI_SRCS := $(SCSI_SRCS) advansys.c
130           SCSI_OBJS := $(SCSI_OBJS) advansys.o
131           else
132           SCSI_MODULE_OBJS := $(SCSI_MODULE_OBJS) advansys.o
133           endif
134
135      4. linux/init/main.c:
136
137           extern void advansys_setup(char *str, int *ints);
138
139         and add the following lines to the bootsetups[] array.
140
141           #ifdef CONFIG_SCSI_ADVANSYS
142              { "advansys=", advansys_setup },
143           #endif
144
145   D. Source Comments
146
147      1. Use tab stops set to 4 for the source files. For vi use 'se tabstops=4'.
148
149      2. This driver should be maintained in multiple files. But to make
150         it easier to include with Linux and to follow Linux conventions,
151         the whole driver is maintained in the source files advansys.h and
152         advansys.c. In this file logical sections of the driver begin with
153         a comment that contains '---'. The following are the logical sections
154         of the driver below.
155
156            --- Linux Version
157            --- Linux Include File
158            --- Driver Options
159            --- Debugging Header
160            --- Asc Library Constants and Macros
161            --- Adv Library Constants and Macros
162            --- Driver Constants and Macros
163            --- Driver Structures
164            --- Driver Data
165            --- Driver Function Prototypes
166            --- Linux 'struct scsi_host_template' and advansys_setup() Functions
167            --- Loadable Driver Support
168            --- Miscellaneous Driver Functions
169            --- Functions Required by the Asc Library
170            --- Functions Required by the Adv Library
171            --- Tracing and Debugging Functions
172            --- Asc Library Functions
173            --- Adv Library Functions
174
175      3. The string 'XXX' is used to flag code that needs to be re-written
176         or that contains a problem that needs to be addressed.
177
178      4. I have stripped comments from and reformatted the source for the
179         Asc Library and Adv Library to reduce the size of this file. This
180         source can be found under the following headings. The Asc Library
181         is used to support Narrow Boards. The Adv Library is used to
182         support Wide Boards.
183
184            --- Asc Library Constants and Macros
185            --- Adv Library Constants and Macros
186            --- Asc Library Functions
187            --- Adv Library Functions
188
189   E. Driver Compile Time Options and Debugging
190
191      In this source file the following constants can be defined. They are
192      defined in the source below. Both of these options are enabled by
193      default.
194
195      1. ADVANSYS_ASSERT - Enable driver assertions (Def: Enabled)
196
197         Enabling this option adds assertion logic statements to the
198         driver. If an assertion fails a message will be displayed to
199         the console, but the system will continue to operate. Any
200         assertions encountered should be reported to the person
201         responsible for the driver. Assertion statements may proactively
202         detect problems with the driver and facilitate fixing these
203         problems. Enabling assertions will add a small overhead to the
204         execution of the driver.
205
206      2. ADVANSYS_DEBUG - Enable driver debugging (Def: Disabled)
207
208         Enabling this option adds tracing functions to the driver and
209         the ability to set a driver tracing level at boot time. This
210         option will also export symbols not required outside the driver to
211         the kernel name space. This option is very useful for debugging
212         the driver, but it will add to the size of the driver execution
213         image and add overhead to the execution of the driver.
214
215         The amount of debugging output can be controlled with the global
216         variable 'asc_dbglvl'. The higher the number the more output. By
217         default the debug level is 0.
218
219         If the driver is loaded at boot time and the LILO Driver Option
220         is included in the system, the debug level can be changed by
221         specifying a 5th (ASC_NUM_IOPORT_PROBE + 1) I/O Port. The
222         first three hex digits of the pseudo I/O Port must be set to
223         'deb' and the fourth hex digit specifies the debug level: 0 - F.
224         The following command line will look for an adapter at 0x330
225         and set the debug level to 2.
226
227            linux advansys=0x330,0,0,0,0xdeb2
228
229         If the driver is built as a loadable module this variable can be
230         defined when the driver is loaded. The following insmod command
231         will set the debug level to one.
232
233            insmod advansys.o asc_dbglvl=1
234
235         Debugging Message Levels:
236            0: Errors Only
237            1: High-Level Tracing
238            2-N: Verbose Tracing
239
240         To enable debug output to console, please make sure that:
241
242         a. System and kernel logging is enabled (syslogd, klogd running).
243         b. Kernel messages are routed to console output. Check
244            /etc/syslog.conf for an entry similar to this:
245
246                 kern.*                  /dev/console
247
248         c. klogd is started with the appropriate -c parameter
249            (e.g. klogd -c 8)
250
251         This will cause printk() messages to be be displayed on the
252         current console. Refer to the klogd(8) and syslogd(8) man pages
253         for details.
254
255         Alternatively you can enable printk() to console with this
256         program. However, this is not the 'official' way to do this.
257         Debug output is logged in /var/log/messages.
258
259           main()
260           {
261                   syscall(103, 7, 0, 0);
262           }
263
264         Increasing LOG_BUF_LEN in kernel/printk.c to something like
265         40960 allows more debug messages to be buffered in the kernel
266         and written to the console or log file.
267
268      3. ADVANSYS_STATS - Enable statistics (Def: Enabled >= v1.3.0)
269
270         Enabling this option adds statistics collection and display
271         through /proc to the driver. The information is useful for
272         monitoring driver and device performance. It will add to the
273         size of the driver execution image and add minor overhead to
274         the execution of the driver.
275
276         Statistics are maintained on a per adapter basis. Driver entry
277         point call counts and transfer size counts are maintained.
278         Statistics are only available for kernels greater than or equal
279         to v1.3.0 with the CONFIG_PROC_FS (/proc) file system configured.
280
281         AdvanSys SCSI adapter files have the following path name format:
282
283            /proc/scsi/advansys/[0-(ASC_NUM_BOARD_SUPPORTED-1)]
284
285         This information can be displayed with cat. For example:
286
287            cat /proc/scsi/advansys/0
288
289         When ADVANSYS_STATS is not defined the AdvanSys /proc files only
290         contain adapter and device configuration information.
291
292   F. Driver LILO Option
293
294      If init/main.c is modified as described in the 'Directions for Adding
295      the AdvanSys Driver to Linux' section (B.4.) above, the driver will
296      recognize the 'advansys' LILO command line and /etc/lilo.conf option.
297      This option can be used to either disable I/O port scanning or to limit
298      scanning to 1 - 4 I/O ports. Regardless of the option setting EISA and
299      PCI boards will still be searched for and detected. This option only
300      affects searching for ISA and VL boards.
301
302      Examples:
303        1. Eliminate I/O port scanning:
304             boot: linux advansys=
305               or
306             boot: linux advansys=0x0
307        2. Limit I/O port scanning to one I/O port:
308             boot: linux advansys=0x110
309        3. Limit I/O port scanning to four I/O ports:
310             boot: linux advansys=0x110,0x210,0x230,0x330
311
312      For a loadable module the same effect can be achieved by setting
313      the 'asc_iopflag' variable and 'asc_ioport' array when loading
314      the driver, e.g.
315
316            insmod advansys.o asc_iopflag=1 asc_ioport=0x110,0x330
317
318      If ADVANSYS_DEBUG is defined a 5th (ASC_NUM_IOPORT_PROBE + 1)
319      I/O Port may be added to specify the driver debug level. Refer to
320      the 'Driver Compile Time Options and Debugging' section above for
321      more information.
322
323   G. Tests to run before releasing new driver
324
325      1. In the supported kernels verify there are no warning or compile
326         errors when the kernel is built as both a driver and as a module
327         and with the following options:
328
329         ADVANSYS_DEBUG - enabled and disabled
330         CONFIG_SMP - enabled and disabled
331         CONFIG_PROC_FS - enabled and disabled
332
333      2. Run tests on an x86, alpha, and PowerPC with at least one narrow
334         card and one wide card attached to a hard disk and CD-ROM drive:
335         fdisk, mkfs, fsck, bonnie, copy/compare test from the
336         CD-ROM to the hard drive.
337
338   H. Release History
339
340      BETA-1.0 (12/23/95):
341          First Release
342
343      BETA-1.1 (12/28/95):
344          1. Prevent advansys_detect() from being called twice.
345          2. Add LILO 0xdeb[0-f] option to set 'asc_dbglvl'.
346
347      1.2 (1/12/96):
348          1. Prevent re-entrancy in the interrupt handler which
349             resulted in the driver hanging Linux.
350          2. Fix problem that prevented ABP-940 cards from being
351             recognized on some PCI motherboards.
352          3. Add support for the ABP-5140 PnP ISA card.
353          4. Fix check condition return status.
354          5. Add conditionally compiled code for Linux v1.3.X.
355
356      1.3 (2/23/96):
357          1. Fix problem in advansys_biosparam() that resulted in the
358             wrong drive geometry being returned for drives > 1GB with
359             extended translation enabled.
360          2. Add additional tracing during device initialization.
361          3. Change code that only applies to ISA PnP adapter.
362          4. Eliminate 'make dep' warning.
363          5. Try to fix problem with handling resets by increasing their
364             timeout value.
365
366      1.4 (5/8/96):
367          1. Change definitions to eliminate conflicts with other subsystems.
368          2. Add versioning code for the shared interrupt changes.
369          3. Eliminate problem in asc_rmqueue() with iterating after removing
370             a request.
371          4. Remove reset request loop problem from the "Known Problems or
372             Issues" section. This problem was isolated and fixed in the
373             mid-level SCSI driver.
374
375      1.5 (8/8/96):
376          1. Add support for ABP-940U (PCI Ultra) adapter.
377          2. Add support for IRQ sharing by setting the IRQF_SHARED flag for
378             request_irq and supplying a dev_id pointer to both request_irq()
379             and free_irq().
380          3. In AscSearchIOPortAddr11() restore a call to check_region() which
381             should be used before I/O port probing.
382          4. Fix bug in asc_prt_hex() which resulted in the displaying
383             the wrong data.
384          5. Incorporate miscellaneous Asc Library bug fixes and new microcode.
385          6. Change driver versioning to be specific to each Linux sub-level.
386          7. Change statistics gathering to be per adapter instead of global
387             to the driver.
388          8. Add more information and statistics to the adapter /proc file:
389             /proc/scsi/advansys[0...].
390          9. Remove 'cmd_per_lun' from the "Known Problems or Issues" list.
391             This problem has been addressed with the SCSI mid-level changes
392             made in v1.3.89. The advansys_select_queue_depths() function
393             was added for the v1.3.89 changes.
394
395      1.6 (9/10/96):
396          1. Incorporate miscellaneous Asc Library bug fixes and new microcode.
397
398      1.7 (9/25/96):
399          1. Enable clustering and optimize the setting of the maximum number
400             of scatter gather elements for any particular board. Clustering
401             increases CPU utilization, but results in a relatively larger
402             increase in I/O throughput.
403          2. Improve the performance of the request queuing functions by
404             adding a last pointer to the queue structure.
405          3. Correct problems with reset and abort request handling that
406             could have hung or crashed Linux.
407          4. Add more information to the adapter /proc file:
408             /proc/scsi/advansys[0...].
409          5. Remove the request timeout issue form the driver issues list.
410          6. Miscellaneous documentation additions and changes.
411
412      1.8 (10/4/96):
413          1. Make changes to handle the new v2.1.0 kernel memory mapping
414             in which a kernel virtual address may not be equivalent to its
415             bus or DMA memory address.
416          2. Change abort and reset request handling to make it yet even
417             more robust.
418          3. Try to mitigate request starvation by sending ordered requests
419             to heavily loaded, tag queuing enabled devices.
420          4. Maintain statistics on request response time.
421          5. Add request response time statistics and other information to
422             the adapter /proc file: /proc/scsi/advansys[0...].
423
424      1.9 (10/21/96):
425          1. Add conditionally compiled code (ASC_QUEUE_FLOW_CONTROL) to
426             make use of mid-level SCSI driver device queue depth flow
427             control mechanism. This will eliminate aborts caused by a
428             device being unable to keep up with requests and eliminate
429             repeat busy or QUEUE FULL status returned by a device.
430          2. Incorporate miscellaneous Asc Library bug fixes.
431          3. To allow the driver to work in kernels with broken module
432             support set 'cmd_per_lun' if the driver is compiled as a
433             module. This change affects kernels v1.3.89 to present.
434          4. Remove PCI BIOS address from the driver banner. The PCI BIOS
435             is relocated by the motherboard BIOS and its new address can
436             not be determined by the driver.
437          5. Add mid-level SCSI queue depth information to the adapter
438             /proc file: /proc/scsi/advansys[0...].
439
440      2.0 (11/14/96):
441          1. Change allocation of global structures used for device
442             initialization to guarantee they are in DMA-able memory.
443             Previously when the driver was loaded as a module these
444             structures might not have been in DMA-able memory, causing
445             device initialization to fail.
446
447      2.1 (12/30/96):
448          1. In advansys_reset(), if the request is a synchronous reset
449             request, even if the request serial number has changed, then
450             complete the request.
451          2. Add Asc Library bug fixes including new microcode.
452          3. Clear inquiry buffer before using it.
453          4. Correct ifdef typo.
454
455      2.2 (1/15/97):
456          1. Add Asc Library bug fixes including new microcode.
457          2. Add synchronous data transfer rate information to the
458             adapter /proc file: /proc/scsi/advansys[0...].
459          3. Change ADVANSYS_DEBUG to be disabled by default. This
460             will reduce the size of the driver image, eliminate execution
461             overhead, and remove unneeded symbols from the kernel symbol
462             space that were previously added by the driver.
463          4. Add new compile-time option ADVANSYS_ASSERT for assertion
464             code that used to be defined within ADVANSYS_DEBUG. This
465             option is enabled by default.
466
467      2.8 (5/26/97):
468          1. Change version number to 2.8 to synchronize the Linux driver
469             version numbering with other AdvanSys drivers.
470          2. Reformat source files without tabs to present the same view
471             of the file to everyone regardless of the editor tab setting
472             being used.
473          3. Add Asc Library bug fixes.
474
475      3.1A (1/8/98):
476          1. Change version number to 3.1 to indicate that support for
477             Ultra-Wide adapters (ABP-940UW) is included in this release.
478          2. Add Asc Library (Narrow Board) bug fixes.
479          3. Report an underrun condition with the host status byte set
480             to DID_UNDERRUN. Currently DID_UNDERRUN is defined to 0 which
481             causes the underrun condition to be ignored. When Linux defines
482             its own DID_UNDERRUN the constant defined in this file can be
483             removed.
484          4. Add patch to AscWaitTixISRDone().
485          5. Add support for up to 16 different AdvanSys host adapter SCSI
486             channels in one system. This allows four cards with four channels
487             to be used in one system.
488
489      3.1B (1/9/98):
490          1. Handle that PCI register base addresses are not always page
491             aligned even though ioremap() requires that the address argument
492             be page aligned.
493
494      3.1C (1/10/98):
495          1. Update latest BIOS version checked for from the /proc file.
496          2. Don't set microcode SDTR variable at initialization. Instead
497             wait until device capabilities have been detected from an Inquiry
498             command.
499
500      3.1D (1/21/98):
501          1. Improve performance when the driver is compiled as module by
502             allowing up to 64 scatter-gather elements instead of 8.
503
504      3.1E (5/1/98):
505          1. Set time delay in AscWaitTixISRDone() to 1000 ms.
506          2. Include SMP locking changes.
507          3. For v2.1.93 and newer kernels use CONFIG_PCI and new PCI BIOS
508             access functions.
509          4. Update board serial number printing.
510          5. Try allocating an IRQ both with and without the IRQF_DISABLED
511             flag set to allow IRQ sharing with drivers that do not set
512             the IRQF_DISABLED flag. Also display a more descriptive error
513             message if request_irq() fails.
514          6. Update to latest Asc and Adv Libraries.
515
516      3.2A (7/22/99):
517          1. Update Adv Library to 4.16 which includes support for
518             the ASC38C0800 (Ultra2/LVD) IC.
519
520      3.2B (8/23/99):
521          1. Correct PCI compile time option for v2.1.93 and greater
522             kernels, advansys_info() string, and debug compile time
523             option.
524          2. Correct DvcSleepMilliSecond() for v2.1.0 and greater
525             kernels. This caused an LVD detection/BIST problem problem
526             among other things.
527          3. Sort PCI cards by PCI Bus, Slot, Function ascending order
528             to be consistent with the BIOS.
529          4. Update to Asc Library S121 and Adv Library 5.2.
530
531      3.2C (8/24/99):
532          1. Correct PCI card detection bug introduced in 3.2B that
533             prevented PCI cards from being detected in kernels older
534             than v2.1.93.
535
536      3.2D (8/26/99):
537          1. Correct /proc device synchronous speed information display.
538             Also when re-negotiation is pending for a target device
539             note this condition with an * and footnote.
540          2. Correct initialization problem with Ultra-Wide cards that
541             have a pre-3.2 BIOS. A microcode variable changed locations
542             in 3.2 and greater BIOSes which caused WDTR to be attempted
543             erroneously with drives that don't support WDTR.
544
545      3.2E (8/30/99):
546          1. Fix compile error caused by v2.3.13 PCI structure change.
547          2. Remove field from ASCEEP_CONFIG that resulted in an EEPROM
548             checksum error for ISA cards.
549          3. Remove ASC_QUEUE_FLOW_CONTROL conditional code. The mid-level
550             SCSI changes that it depended on were never included in Linux.
551
552      3.2F (9/3/99):
553          1. Handle new initial function code added in v2.3.16 for all
554             driver versions.
555
556      3.2G (9/8/99):
557          1. Fix PCI board detection in v2.3.13 and greater kernels.
558          2. Fix comiple errors in v2.3.X with debugging enabled.
559
560      3.2H (9/13/99):
561          1. Add 64-bit address, long support for Alpha and UltraSPARC.
562             The driver has been verified to work on an Alpha system.
563          2. Add partial byte order handling support for Power PC and
564             other big-endian platforms. This support has not yet been
565             completed or verified.
566          3. For wide boards replace block zeroing of request and
567             scatter-gather structures with individual field initialization
568             to improve performance.
569          4. Correct and clarify ROM BIOS version detection.
570
571      3.2I (10/8/99):
572          1. Update to Adv Library 5.4.
573          2. Add v2.3.19 underrun reporting to asc_isr_callback() and
574             adv_isr_callback().  Remove DID_UNDERRUN constant and other
575             no longer needed code that previously documented the lack
576             of underrun handling.
577
578      3.2J (10/14/99):
579          1. Eliminate compile errors for v2.0 and earlier kernels.
580
581      3.2K (11/15/99):
582          1. Correct debug compile error in asc_prt_adv_scsi_req_q().
583          2. Update Adv Library to 5.5.
584          3. Add ifdef handling for /proc changes added in v2.3.28.
585          4. Increase Wide board scatter-gather list maximum length to
586             255 when the driver is compiled into the kernel.
587
588      3.2L (11/18/99):
589          1. Fix bug in adv_get_sglist() that caused an assertion failure
590             at line 7475. The reqp->sgblkp pointer must be initialized
591             to NULL in adv_get_sglist().
592
593      3.2M (11/29/99):
594          1. Really fix bug in adv_get_sglist().
595          2. Incorporate v2.3.29 changes into driver.
596
597      3.2N (4/1/00):
598          1. Add CONFIG_ISA ifdef code.
599          2. Include advansys_interrupts_enabled name change patch.
600          3. For >= v2.3.28 use new SCSI error handling with new function
601             advansys_eh_bus_reset(). Don't include an abort function
602             because of base library limitations.
603          4. For >= v2.3.28 use per board lock instead of io_request_lock.
604          5. For >= v2.3.28 eliminate advansys_command() and
605             advansys_command_done().
606          6. Add some changes for PowerPC (Big Endian) support, but it isn't
607             working yet.
608          7. Fix "nonexistent resource free" problem that occurred on a module
609             unload for boards with an I/O space >= 255. The 'n_io_port' field
610             is only one byte and can not be used to hold an ioport length more
611             than 255.
612
613      3.3A (4/4/00):
614          1. Update to Adv Library 5.8.
615          2. For wide cards add support for CDBs up to 16 bytes.
616          3. Eliminate warnings when CONFIG_PROC_FS is not defined.
617
618      3.3B (5/1/00):
619          1. Support for PowerPC (Big Endian) wide cards. Narrow cards
620             still need work.
621          2. Change bitfields to shift and mask access for endian
622             portability.
623
624      3.3C (10/13/00):
625          1. Update for latest 2.4 kernel.
626          2. Test ABP-480 CardBus support in 2.4 kernel - works!
627          3. Update to Asc Library S123.
628          4. Update to Adv Library 5.12.
629
630      3.3D (11/22/00):
631          1. Update for latest 2.4 kernel.
632          2. Create patches for 2.2 and 2.4 kernels.
633
634      3.3E (1/9/01):
635          1. Now that 2.4 is released remove ifdef code for kernel versions
636             less than 2.2. The driver is now only supported in kernels 2.2,
637             2.4, and greater.
638          2. Add code to release and acquire the io_request_lock in
639             the driver entrypoint functions: advansys_detect and
640             advansys_queuecommand. In kernel 2.4 the SCSI mid-level driver
641             still holds the io_request_lock on entry to SCSI low-level drivers.
642             This was supposed to be removed before 2.4 was released but never
643             happened. When the mid-level SCSI driver is changed all references
644             to the io_request_lock should be removed from the driver.
645          3. Simplify error handling by removing advansys_abort(),
646             AscAbortSRB(), AscResetDevice(). SCSI bus reset requests are
647             now handled by resetting the SCSI bus and fully re-initializing
648             the chip. This simple method of error recovery has proven to work
649             most reliably after attempts at different methods. Also now only
650             support the "new" error handling method and remove the obsolete
651             error handling interface.
652          4. Fix debug build errors.
653
654      3.3F (1/24/01):
655          1. Merge with ConnectCom version from Andy Kellner which
656             updates Adv Library to 5.14.
657          2. Make PowerPC (Big Endian) work for narrow cards and
658             fix problems writing EEPROM for wide cards.
659          3. Remove interrupts_enabled assertion function.
660
661      3.3G (2/16/01):
662          1. Return an error from narrow boards if passed a 16 byte
663             CDB. The wide board can already handle 16 byte CDBs.
664
665      3.3GJ (4/15/02):
666          1. hacks for lk 2.5 series (D. Gilbert)
667
668      3.3GJD (10/14/02):
669          1. change select_queue_depths to slave_configure
670          2. make cmd_per_lun be sane again
671
672      3.3K [2004/06/24]:
673          1. continuing cleanup for lk 2.6 series
674          2. Fix problem in lk 2.6.7-bk2 that broke PCI wide cards
675          3. Fix problem that oopsed ISA cards
676
677   I. Known Problems/Fix List (XXX)
678
679      1. Need to add memory mapping workaround. Test the memory mapping.
680         If it doesn't work revert to I/O port access. Can a test be done
681         safely?
682      2. Handle an interrupt not working. Keep an interrupt counter in
683         the interrupt handler. In the timeout function if the interrupt
684         has not occurred then print a message and run in polled mode.
685      3. Allow bus type scanning order to be changed.
686      4. Need to add support for target mode commands, cf. CAM XPT.
687
688   J. Credits (Chronological Order)
689
690      Bob Frey <bfrey@turbolinux.com.cn> wrote the AdvanSys SCSI driver
691      and maintained it up to 3.3F. He continues to answer questions
692      and help maintain the driver.
693
694      Nathan Hartwell <mage@cdc3.cdc.net> provided the directions and
695      basis for the Linux v1.3.X changes which were included in the
696      1.2 release.
697
698      Thomas E Zerucha <zerucha@shell.portal.com> pointed out a bug
699      in advansys_biosparam() which was fixed in the 1.3 release.
700
701      Erik Ratcliffe <erik@caldera.com> has done testing of the
702      AdvanSys driver in the Caldera releases.
703
704      Rik van Riel <H.H.vanRiel@fys.ruu.nl> provided a patch to
705      AscWaitTixISRDone() which he found necessary to make the
706      driver work with a SCSI-1 disk.
707
708      Mark Moran <mmoran@mmoran.com> has helped test Ultra-Wide
709      support in the 3.1A driver.
710
711      Doug Gilbert <dgilbert@interlog.com> has made changes and
712      suggestions to improve the driver and done a lot of testing.
713
714      Ken Mort <ken@mort.net> reported a DEBUG compile bug fixed
715      in 3.2K.
716
717      Tom Rini <trini@kernel.crashing.org> provided the CONFIG_ISA
718      patch and helped with PowerPC wide and narrow board support.
719
720      Philip Blundell <philb@gnu.org> provided an
721      advansys_interrupts_enabled patch.
722
723      Dave Jones <dave@denial.force9.co.uk> reported the compiler
724      warnings generated when CONFIG_PROC_FS was not defined in
725      the 3.2M driver.
726
727      Jerry Quinn <jlquinn@us.ibm.com> fixed PowerPC support (endian
728      problems) for wide cards.
729
730      Bryan Henderson <bryanh@giraffe-data.com> helped debug narrow
731      card error handling.
732
733      Manuel Veloso <veloso@pobox.com> worked hard on PowerPC narrow
734      board support and fixed a bug in AscGetEEPConfig().
735
736      Arnaldo Carvalho de Melo <acme@conectiva.com.br> made
737      save_flags/restore_flags changes.
738
739      Andy Kellner <AKellner@connectcom.net> continues the Advansys SCSI
740      driver development for ConnectCom (Version > 3.3F).
741
742   K. ConnectCom (AdvanSys) Contact Information
743
744      Mail:                   ConnectCom Solutions, Inc.
745                              1150 Ringwood Court
746                              San Jose, CA 95131
747      Operator/Sales:         1-408-383-9400
748      FAX:                    1-408-383-9612
749      Tech Support:           1-408-467-2930
750      Tech Support E-Mail:    linux@connectcom.net
751      FTP Site:               ftp.connectcom.net (login: anonymous)
752      Web Site:               http://www.connectcom.net
753
754 */
755
756 /*
757  * --- Linux Include Files
758  */
759
760 #include <linux/module.h>
761 #include <linux/string.h>
762 #include <linux/kernel.h>
763 #include <linux/types.h>
764 #include <linux/ioport.h>
765 #include <linux/interrupt.h>
766 #include <linux/delay.h>
767 #include <linux/slab.h>
768 #include <linux/mm.h>
769 #include <linux/proc_fs.h>
770 #include <linux/init.h>
771 #include <linux/blkdev.h>
772 #include <linux/pci.h>
773 #include <linux/spinlock.h>
774 #include <linux/dma-mapping.h>
775
776 #include <asm/io.h>
777 #include <asm/system.h>
778 #include <asm/dma.h>
779
780 #include <scsi/scsi_cmnd.h>
781 #include <scsi/scsi_device.h>
782 #include <scsi/scsi_tcq.h>
783 #include <scsi/scsi.h>
784 #include <scsi/scsi_host.h>
785
786 /* FIXME: (by jejb@steeleye.com) This warning is present for two
787  * reasons:
788  *
789  * 1) This driver badly needs converting to the correct driver model
790  *    probing API
791  *
792  * 2) Although all of the necessary command mapping places have the
793  * appropriate dma_map.. APIs, the driver still processes its internal
794  * queue using bus_to_virt() and virt_to_bus() which are illegal under
795  * the API.  The entire queue processing structure will need to be
796  * altered to fix this.
797  */
798 #warning this driver is still not properly converted to the DMA API
799
800 /*
801  * --- Driver Options
802  */
803
804 /* Enable driver assertions. */
805 #define ADVANSYS_ASSERT
806
807 /* Enable driver /proc statistics. */
808 #define ADVANSYS_STATS
809
810 /* Enable driver tracing. */
811 /* #define ADVANSYS_DEBUG */
812
813 /*
814  * --- Asc Library Constants and Macros
815  */
816
817 #define ASC_LIB_VERSION_MAJOR  1
818 #define ASC_LIB_VERSION_MINOR  24
819 #define ASC_LIB_SERIAL_NUMBER  123
820
821 /*
822  * Portable Data Types
823  *
824  * Any instance where a 32-bit long or pointer type is assumed
825  * for precision or HW defined structures, the following define
826  * types must be used. In Linux the char, short, and int types
827  * are all consistent at 8, 16, and 32 bits respectively. Pointers
828  * and long types are 64 bits on Alpha and UltraSPARC.
829  */
830 #define ASC_PADDR __u32         /* Physical/Bus address data type. */
831 #define ASC_VADDR __u32         /* Virtual address data type. */
832 #define ASC_DCNT  __u32         /* Unsigned Data count type. */
833 #define ASC_SDCNT __s32         /* Signed Data count type. */
834
835 /*
836  * These macros are used to convert a virtual address to a
837  * 32-bit value. This currently can be used on Linux Alpha
838  * which uses 64-bit virtual address but a 32-bit bus address.
839  * This is likely to break in the future, but doing this now
840  * will give us time to change the HW and FW to handle 64-bit
841  * addresses.
842  */
843 #define ASC_VADDR_TO_U32   virt_to_bus
844 #define ASC_U32_TO_VADDR   bus_to_virt
845
846 typedef unsigned char uchar;
847
848 #ifndef TRUE
849 #define TRUE     (1)
850 #endif
851 #ifndef FALSE
852 #define FALSE    (0)
853 #endif
854
855 #define EOF      (-1)
856 #define ERR      (-1)
857 #define UW_ERR   (uint)(0xFFFF)
858 #define isodd_word(val)   ((((uint)val) & (uint)0x0001) != 0)
859 #define AscPCIConfigVendorIDRegister      0x0000
860 #define AscPCIConfigDeviceIDRegister      0x0002
861 #define AscPCIConfigCommandRegister       0x0004
862 #define AscPCIConfigStatusRegister        0x0006
863 #define AscPCIConfigRevisionIDRegister    0x0008
864 #define AscPCIConfigCacheSize             0x000C
865 #define AscPCIConfigLatencyTimer          0x000D
866 #define AscPCIIOBaseRegister              0x0010
867 #define AscPCICmdRegBits_IOMemBusMaster   0x0007
868 #define ASC_PCI_ID2BUS(id)    ((id) & 0xFF)
869 #define ASC_PCI_ID2DEV(id)    (((id) >> 11) & 0x1F)
870 #define ASC_PCI_ID2FUNC(id)   (((id) >> 8) & 0x7)
871 #define ASC_PCI_MKID(bus, dev, func) ((((dev) & 0x1F) << 11) | (((func) & 0x7) << 8) | ((bus) & 0xFF))
872 #define ASC_PCI_REVISION_3150             0x02
873 #define ASC_PCI_REVISION_3050             0x03
874
875 #define  ASC_DVCLIB_CALL_DONE     (1)
876 #define  ASC_DVCLIB_CALL_FAILED   (0)
877 #define  ASC_DVCLIB_CALL_ERROR    (-1)
878
879 #define PCI_VENDOR_ID_ASP               0x10cd
880 #define PCI_DEVICE_ID_ASP_1200A         0x1100
881 #define PCI_DEVICE_ID_ASP_ABP940        0x1200
882 #define PCI_DEVICE_ID_ASP_ABP940U       0x1300
883 #define PCI_DEVICE_ID_ASP_ABP940UW      0x2300
884 #define PCI_DEVICE_ID_38C0800_REV1      0x2500
885 #define PCI_DEVICE_ID_38C1600_REV1      0x2700
886
887 /*
888  * Enable CC_VERY_LONG_SG_LIST to support up to 64K element SG lists.
889  * The SRB structure will have to be changed and the ASC_SRB2SCSIQ()
890  * macro re-defined to be able to obtain a ASC_SCSI_Q pointer from the
891  * SRB structure.
892  */
893 #define CC_VERY_LONG_SG_LIST 0
894 #define ASC_SRB2SCSIQ(srb_ptr)  (srb_ptr)
895
896 #define PortAddr                 unsigned short /* port address size  */
897 #define inp(port)                inb(port)
898 #define outp(port, byte)         outb((byte), (port))
899
900 #define inpw(port)               inw(port)
901 #define outpw(port, word)        outw((word), (port))
902
903 #define ASC_MAX_SG_QUEUE    7
904 #define ASC_MAX_SG_LIST     255
905
906 #define ASC_CS_TYPE  unsigned short
907
908 #define ASC_IS_ISA          (0x0001)
909 #define ASC_IS_ISAPNP       (0x0081)
910 #define ASC_IS_EISA         (0x0002)
911 #define ASC_IS_PCI          (0x0004)
912 #define ASC_IS_PCI_ULTRA    (0x0104)
913 #define ASC_IS_PCMCIA       (0x0008)
914 #define ASC_IS_MCA          (0x0020)
915 #define ASC_IS_VL           (0x0040)
916 #define ASC_ISA_PNP_PORT_ADDR  (0x279)
917 #define ASC_ISA_PNP_PORT_WRITE (ASC_ISA_PNP_PORT_ADDR+0x800)
918 #define ASC_IS_WIDESCSI_16  (0x0100)
919 #define ASC_IS_WIDESCSI_32  (0x0200)
920 #define ASC_IS_BIG_ENDIAN   (0x8000)
921 #define ASC_CHIP_MIN_VER_VL      (0x01)
922 #define ASC_CHIP_MAX_VER_VL      (0x07)
923 #define ASC_CHIP_MIN_VER_PCI     (0x09)
924 #define ASC_CHIP_MAX_VER_PCI     (0x0F)
925 #define ASC_CHIP_VER_PCI_BIT     (0x08)
926 #define ASC_CHIP_MIN_VER_ISA     (0x11)
927 #define ASC_CHIP_MIN_VER_ISA_PNP (0x21)
928 #define ASC_CHIP_MAX_VER_ISA     (0x27)
929 #define ASC_CHIP_VER_ISA_BIT     (0x30)
930 #define ASC_CHIP_VER_ISAPNP_BIT  (0x20)
931 #define ASC_CHIP_VER_ASYN_BUG    (0x21)
932 #define ASC_CHIP_VER_PCI             0x08
933 #define ASC_CHIP_VER_PCI_ULTRA_3150  (ASC_CHIP_VER_PCI | 0x02)
934 #define ASC_CHIP_VER_PCI_ULTRA_3050  (ASC_CHIP_VER_PCI | 0x03)
935 #define ASC_CHIP_MIN_VER_EISA (0x41)
936 #define ASC_CHIP_MAX_VER_EISA (0x47)
937 #define ASC_CHIP_VER_EISA_BIT (0x40)
938 #define ASC_CHIP_LATEST_VER_EISA   ((ASC_CHIP_MIN_VER_EISA - 1) + 3)
939 #define ASC_MAX_LIB_SUPPORTED_ISA_CHIP_VER   0x21
940 #define ASC_MAX_LIB_SUPPORTED_PCI_CHIP_VER   0x0A
941 #define ASC_MAX_VL_DMA_ADDR     (0x07FFFFFFL)
942 #define ASC_MAX_VL_DMA_COUNT    (0x07FFFFFFL)
943 #define ASC_MAX_PCI_DMA_ADDR    (0xFFFFFFFFL)
944 #define ASC_MAX_PCI_DMA_COUNT   (0xFFFFFFFFL)
945 #define ASC_MAX_ISA_DMA_ADDR    (0x00FFFFFFL)
946 #define ASC_MAX_ISA_DMA_COUNT   (0x00FFFFFFL)
947 #define ASC_MAX_EISA_DMA_ADDR   (0x07FFFFFFL)
948 #define ASC_MAX_EISA_DMA_COUNT  (0x07FFFFFFL)
949
950 #define ASC_SCSI_ID_BITS  3
951 #define ASC_SCSI_TIX_TYPE     uchar
952 #define ASC_ALL_DEVICE_BIT_SET  0xFF
953 #define ASC_SCSI_BIT_ID_TYPE  uchar
954 #define ASC_MAX_TID       7
955 #define ASC_MAX_LUN       7
956 #define ASC_SCSI_WIDTH_BIT_SET  0xFF
957 #define ASC_MAX_SENSE_LEN   32
958 #define ASC_MIN_SENSE_LEN   14
959 #define ASC_MAX_CDB_LEN     12
960 #define ASC_SCSI_RESET_HOLD_TIME_US  60
961
962 #define ADV_INQ_CLOCKING_ST_ONLY    0x0
963 #define ADV_INQ_CLOCKING_DT_ONLY    0x1
964 #define ADV_INQ_CLOCKING_ST_AND_DT  0x3
965
966 /*
967  * Inquiry SPC-2 SPI Byte 1 EVPD (Enable Vital Product Data)
968  * and CmdDt (Command Support Data) field bit definitions.
969  */
970 #define ADV_INQ_RTN_VPD_AND_CMDDT           0x3
971 #define ADV_INQ_RTN_CMDDT_FOR_OP_CODE       0x2
972 #define ADV_INQ_RTN_VPD_FOR_PG_CODE         0x1
973 #define ADV_INQ_RTN_STD_INQUIRY_DATA        0x0
974
975 #define ASC_SCSIDIR_NOCHK    0x00
976 #define ASC_SCSIDIR_T2H      0x08
977 #define ASC_SCSIDIR_H2T      0x10
978 #define ASC_SCSIDIR_NODATA   0x18
979 #define SCSI_ASC_NOMEDIA          0x3A
980 #define ASC_SRB_HOST(x)  ((uchar)((uchar)(x) >> 4))
981 #define ASC_SRB_TID(x)   ((uchar)((uchar)(x) & (uchar)0x0F))
982 #define ASC_SRB_LUN(x)   ((uchar)((uint)(x) >> 13))
983 #define PUT_CDB1(x)   ((uchar)((uint)(x) >> 8))
984 #define MS_CMD_DONE    0x00
985 #define MS_EXTEND      0x01
986 #define MS_SDTR_LEN    0x03
987 #define MS_SDTR_CODE   0x01
988 #define MS_WDTR_LEN    0x02
989 #define MS_WDTR_CODE   0x03
990 #define MS_MDP_LEN    0x05
991 #define MS_MDP_CODE   0x00
992
993 /*
994  * Inquiry data structure and bitfield macros
995  *
996  * Only quantities of more than 1 bit are shifted, since the others are
997  * just tested for true or false. C bitfields aren't portable between big
998  * and little-endian platforms so they are not used.
999  */
1000
1001 #define ASC_INQ_DVC_TYPE(inq)       ((inq)->periph & 0x1f)
1002 #define ASC_INQ_QUALIFIER(inq)      (((inq)->periph & 0xe0) >> 5)
1003 #define ASC_INQ_DVC_TYPE_MOD(inq)   ((inq)->devtype & 0x7f)
1004 #define ASC_INQ_REMOVABLE(inq)      ((inq)->devtype & 0x80)
1005 #define ASC_INQ_ANSI_VER(inq)       ((inq)->ver & 0x07)
1006 #define ASC_INQ_ECMA_VER(inq)       (((inq)->ver & 0x38) >> 3)
1007 #define ASC_INQ_ISO_VER(inq)        (((inq)->ver & 0xc0) >> 6)
1008 #define ASC_INQ_RESPONSE_FMT(inq)   ((inq)->byte3 & 0x0f)
1009 #define ASC_INQ_TERM_IO(inq)        ((inq)->byte3 & 0x40)
1010 #define ASC_INQ_ASYNC_NOTIF(inq)    ((inq)->byte3 & 0x80)
1011 #define ASC_INQ_SOFT_RESET(inq)     ((inq)->flags & 0x01)
1012 #define ASC_INQ_CMD_QUEUE(inq)      ((inq)->flags & 0x02)
1013 #define ASC_INQ_LINK_CMD(inq)       ((inq)->flags & 0x08)
1014 #define ASC_INQ_SYNC(inq)           ((inq)->flags & 0x10)
1015 #define ASC_INQ_WIDE16(inq)         ((inq)->flags & 0x20)
1016 #define ASC_INQ_WIDE32(inq)         ((inq)->flags & 0x40)
1017 #define ASC_INQ_REL_ADDR(inq)       ((inq)->flags & 0x80)
1018 #define ASC_INQ_INFO_UNIT(inq)      ((inq)->info & 0x01)
1019 #define ASC_INQ_QUICK_ARB(inq)      ((inq)->info & 0x02)
1020 #define ASC_INQ_CLOCKING(inq)       (((inq)->info & 0x0c) >> 2)
1021
1022 typedef struct {
1023         uchar periph;
1024         uchar devtype;
1025         uchar ver;
1026         uchar byte3;
1027         uchar add_len;
1028         uchar res1;
1029         uchar res2;
1030         uchar flags;
1031         uchar vendor_id[8];
1032         uchar product_id[16];
1033         uchar product_rev_level[4];
1034 } ASC_SCSI_INQUIRY;
1035
1036 #define ASC_SG_LIST_PER_Q   7
1037 #define QS_FREE        0x00
1038 #define QS_READY       0x01
1039 #define QS_DISC1       0x02
1040 #define QS_DISC2       0x04
1041 #define QS_BUSY        0x08
1042 #define QS_ABORTED     0x40
1043 #define QS_DONE        0x80
1044 #define QC_NO_CALLBACK   0x01
1045 #define QC_SG_SWAP_QUEUE 0x02
1046 #define QC_SG_HEAD       0x04
1047 #define QC_DATA_IN       0x08
1048 #define QC_DATA_OUT      0x10
1049 #define QC_URGENT        0x20
1050 #define QC_MSG_OUT       0x40
1051 #define QC_REQ_SENSE     0x80
1052 #define QCSG_SG_XFER_LIST  0x02
1053 #define QCSG_SG_XFER_MORE  0x04
1054 #define QCSG_SG_XFER_END   0x08
1055 #define QD_IN_PROGRESS       0x00
1056 #define QD_NO_ERROR          0x01
1057 #define QD_ABORTED_BY_HOST   0x02
1058 #define QD_WITH_ERROR        0x04
1059 #define QD_INVALID_REQUEST   0x80
1060 #define QD_INVALID_HOST_NUM  0x81
1061 #define QD_INVALID_DEVICE    0x82
1062 #define QD_ERR_INTERNAL      0xFF
1063 #define QHSTA_NO_ERROR               0x00
1064 #define QHSTA_M_SEL_TIMEOUT          0x11
1065 #define QHSTA_M_DATA_OVER_RUN        0x12
1066 #define QHSTA_M_DATA_UNDER_RUN       0x12
1067 #define QHSTA_M_UNEXPECTED_BUS_FREE  0x13
1068 #define QHSTA_M_BAD_BUS_PHASE_SEQ    0x14
1069 #define QHSTA_D_QDONE_SG_LIST_CORRUPTED 0x21
1070 #define QHSTA_D_ASC_DVC_ERROR_CODE_SET  0x22
1071 #define QHSTA_D_HOST_ABORT_FAILED       0x23
1072 #define QHSTA_D_EXE_SCSI_Q_FAILED       0x24
1073 #define QHSTA_D_EXE_SCSI_Q_BUSY_TIMEOUT 0x25
1074 #define QHSTA_D_ASPI_NO_BUF_POOL        0x26
1075 #define QHSTA_M_WTM_TIMEOUT         0x41
1076 #define QHSTA_M_BAD_CMPL_STATUS_IN  0x42
1077 #define QHSTA_M_NO_AUTO_REQ_SENSE   0x43
1078 #define QHSTA_M_AUTO_REQ_SENSE_FAIL 0x44
1079 #define QHSTA_M_TARGET_STATUS_BUSY  0x45
1080 #define QHSTA_M_BAD_TAG_CODE        0x46
1081 #define QHSTA_M_BAD_QUEUE_FULL_OR_BUSY  0x47
1082 #define QHSTA_M_HUNG_REQ_SCSI_BUS_RESET 0x48
1083 #define QHSTA_D_LRAM_CMP_ERROR        0x81
1084 #define QHSTA_M_MICRO_CODE_ERROR_HALT 0xA1
1085 #define ASC_FLAG_SCSIQ_REQ        0x01
1086 #define ASC_FLAG_BIOS_SCSIQ_REQ   0x02
1087 #define ASC_FLAG_BIOS_ASYNC_IO    0x04
1088 #define ASC_FLAG_SRB_LINEAR_ADDR  0x08
1089 #define ASC_FLAG_WIN16            0x10
1090 #define ASC_FLAG_WIN32            0x20
1091 #define ASC_FLAG_ISA_OVER_16MB    0x40
1092 #define ASC_FLAG_DOS_VM_CALLBACK  0x80
1093 #define ASC_TAG_FLAG_EXTRA_BYTES               0x10
1094 #define ASC_TAG_FLAG_DISABLE_DISCONNECT        0x04
1095 #define ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX  0x08
1096 #define ASC_TAG_FLAG_DISABLE_CHK_COND_INT_HOST 0x40
1097 #define ASC_SCSIQ_CPY_BEG              4
1098 #define ASC_SCSIQ_SGHD_CPY_BEG         2
1099 #define ASC_SCSIQ_B_FWD                0
1100 #define ASC_SCSIQ_B_BWD                1
1101 #define ASC_SCSIQ_B_STATUS             2
1102 #define ASC_SCSIQ_B_QNO                3
1103 #define ASC_SCSIQ_B_CNTL               4
1104 #define ASC_SCSIQ_B_SG_QUEUE_CNT       5
1105 #define ASC_SCSIQ_D_DATA_ADDR          8
1106 #define ASC_SCSIQ_D_DATA_CNT          12
1107 #define ASC_SCSIQ_B_SENSE_LEN         20
1108 #define ASC_SCSIQ_DONE_INFO_BEG       22
1109 #define ASC_SCSIQ_D_SRBPTR            22
1110 #define ASC_SCSIQ_B_TARGET_IX         26
1111 #define ASC_SCSIQ_B_CDB_LEN           28
1112 #define ASC_SCSIQ_B_TAG_CODE          29
1113 #define ASC_SCSIQ_W_VM_ID             30
1114 #define ASC_SCSIQ_DONE_STATUS         32
1115 #define ASC_SCSIQ_HOST_STATUS         33
1116 #define ASC_SCSIQ_SCSI_STATUS         34
1117 #define ASC_SCSIQ_CDB_BEG             36
1118 #define ASC_SCSIQ_DW_REMAIN_XFER_ADDR 56
1119 #define ASC_SCSIQ_DW_REMAIN_XFER_CNT  60
1120 #define ASC_SCSIQ_B_FIRST_SG_WK_QP    48
1121 #define ASC_SCSIQ_B_SG_WK_QP          49
1122 #define ASC_SCSIQ_B_SG_WK_IX          50
1123 #define ASC_SCSIQ_W_ALT_DC1           52
1124 #define ASC_SCSIQ_B_LIST_CNT          6
1125 #define ASC_SCSIQ_B_CUR_LIST_CNT      7
1126 #define ASC_SGQ_B_SG_CNTL             4
1127 #define ASC_SGQ_B_SG_HEAD_QP          5
1128 #define ASC_SGQ_B_SG_LIST_CNT         6
1129 #define ASC_SGQ_B_SG_CUR_LIST_CNT     7
1130 #define ASC_SGQ_LIST_BEG              8
1131 #define ASC_DEF_SCSI1_QNG    4
1132 #define ASC_MAX_SCSI1_QNG    4
1133 #define ASC_DEF_SCSI2_QNG    16
1134 #define ASC_MAX_SCSI2_QNG    32
1135 #define ASC_TAG_CODE_MASK    0x23
1136 #define ASC_STOP_REQ_RISC_STOP      0x01
1137 #define ASC_STOP_ACK_RISC_STOP      0x03
1138 #define ASC_STOP_CLEAN_UP_BUSY_Q    0x10
1139 #define ASC_STOP_CLEAN_UP_DISC_Q    0x20
1140 #define ASC_STOP_HOST_REQ_RISC_HALT 0x40
1141 #define ASC_TIDLUN_TO_IX(tid, lun)  (ASC_SCSI_TIX_TYPE)((tid) + ((lun)<<ASC_SCSI_ID_BITS))
1142 #define ASC_TID_TO_TARGET_ID(tid)   (ASC_SCSI_BIT_ID_TYPE)(0x01 << (tid))
1143 #define ASC_TIX_TO_TARGET_ID(tix)   (0x01 << ((tix) & ASC_MAX_TID))
1144 #define ASC_TIX_TO_TID(tix)         ((tix) & ASC_MAX_TID)
1145 #define ASC_TID_TO_TIX(tid)         ((tid) & ASC_MAX_TID)
1146 #define ASC_TIX_TO_LUN(tix)         (((tix) >> ASC_SCSI_ID_BITS) & ASC_MAX_LUN)
1147 #define ASC_QNO_TO_QADDR(q_no)      ((ASC_QADR_BEG)+((int)(q_no) << 6))
1148
1149 typedef struct asc_scsiq_1 {
1150         uchar status;
1151         uchar q_no;
1152         uchar cntl;
1153         uchar sg_queue_cnt;
1154         uchar target_id;
1155         uchar target_lun;
1156         ASC_PADDR data_addr;
1157         ASC_DCNT data_cnt;
1158         ASC_PADDR sense_addr;
1159         uchar sense_len;
1160         uchar extra_bytes;
1161 } ASC_SCSIQ_1;
1162
1163 typedef struct asc_scsiq_2 {
1164         ASC_VADDR srb_ptr;
1165         uchar target_ix;
1166         uchar flag;
1167         uchar cdb_len;
1168         uchar tag_code;
1169         ushort vm_id;
1170 } ASC_SCSIQ_2;
1171
1172 typedef struct asc_scsiq_3 {
1173         uchar done_stat;
1174         uchar host_stat;
1175         uchar scsi_stat;
1176         uchar scsi_msg;
1177 } ASC_SCSIQ_3;
1178
1179 typedef struct asc_scsiq_4 {
1180         uchar cdb[ASC_MAX_CDB_LEN];
1181         uchar y_first_sg_list_qp;
1182         uchar y_working_sg_qp;
1183         uchar y_working_sg_ix;
1184         uchar y_res;
1185         ushort x_req_count;
1186         ushort x_reconnect_rtn;
1187         ASC_PADDR x_saved_data_addr;
1188         ASC_DCNT x_saved_data_cnt;
1189 } ASC_SCSIQ_4;
1190
1191 typedef struct asc_q_done_info {
1192         ASC_SCSIQ_2 d2;
1193         ASC_SCSIQ_3 d3;
1194         uchar q_status;
1195         uchar q_no;
1196         uchar cntl;
1197         uchar sense_len;
1198         uchar extra_bytes;
1199         uchar res;
1200         ASC_DCNT remain_bytes;
1201 } ASC_QDONE_INFO;
1202
1203 typedef struct asc_sg_list {
1204         ASC_PADDR addr;
1205         ASC_DCNT bytes;
1206 } ASC_SG_LIST;
1207
1208 typedef struct asc_sg_head {
1209         ushort entry_cnt;
1210         ushort queue_cnt;
1211         ushort entry_to_copy;
1212         ushort res;
1213         ASC_SG_LIST sg_list[ASC_MAX_SG_LIST];
1214 } ASC_SG_HEAD;
1215
1216 #define ASC_MIN_SG_LIST   2
1217
1218 typedef struct asc_min_sg_head {
1219         ushort entry_cnt;
1220         ushort queue_cnt;
1221         ushort entry_to_copy;
1222         ushort res;
1223         ASC_SG_LIST sg_list[ASC_MIN_SG_LIST];
1224 } ASC_MIN_SG_HEAD;
1225
1226 #define QCX_SORT        (0x0001)
1227 #define QCX_COALEASE    (0x0002)
1228
1229 typedef struct asc_scsi_q {
1230         ASC_SCSIQ_1 q1;
1231         ASC_SCSIQ_2 q2;
1232         uchar *cdbptr;
1233         ASC_SG_HEAD *sg_head;
1234         ushort remain_sg_entry_cnt;
1235         ushort next_sg_index;
1236 } ASC_SCSI_Q;
1237
1238 typedef struct asc_scsi_req_q {
1239         ASC_SCSIQ_1 r1;
1240         ASC_SCSIQ_2 r2;
1241         uchar *cdbptr;
1242         ASC_SG_HEAD *sg_head;
1243         uchar *sense_ptr;
1244         ASC_SCSIQ_3 r3;
1245         uchar cdb[ASC_MAX_CDB_LEN];
1246         uchar sense[ASC_MIN_SENSE_LEN];
1247 } ASC_SCSI_REQ_Q;
1248
1249 typedef struct asc_scsi_bios_req_q {
1250         ASC_SCSIQ_1 r1;
1251         ASC_SCSIQ_2 r2;
1252         uchar *cdbptr;
1253         ASC_SG_HEAD *sg_head;
1254         uchar *sense_ptr;
1255         ASC_SCSIQ_3 r3;
1256         uchar cdb[ASC_MAX_CDB_LEN];
1257         uchar sense[ASC_MIN_SENSE_LEN];
1258 } ASC_SCSI_BIOS_REQ_Q;
1259
1260 typedef struct asc_risc_q {
1261         uchar fwd;
1262         uchar bwd;
1263         ASC_SCSIQ_1 i1;
1264         ASC_SCSIQ_2 i2;
1265         ASC_SCSIQ_3 i3;
1266         ASC_SCSIQ_4 i4;
1267 } ASC_RISC_Q;
1268
1269 typedef struct asc_sg_list_q {
1270         uchar seq_no;
1271         uchar q_no;
1272         uchar cntl;
1273         uchar sg_head_qp;
1274         uchar sg_list_cnt;
1275         uchar sg_cur_list_cnt;
1276 } ASC_SG_LIST_Q;
1277
1278 typedef struct asc_risc_sg_list_q {
1279         uchar fwd;
1280         uchar bwd;
1281         ASC_SG_LIST_Q sg;
1282         ASC_SG_LIST sg_list[7];
1283 } ASC_RISC_SG_LIST_Q;
1284
1285 #define ASC_EXE_SCSI_IO_MAX_IDLE_LOOP  0x1000000UL
1286 #define ASC_EXE_SCSI_IO_MAX_WAIT_LOOP  1024
1287 #define ASCQ_ERR_NO_ERROR             0
1288 #define ASCQ_ERR_IO_NOT_FOUND         1
1289 #define ASCQ_ERR_LOCAL_MEM            2
1290 #define ASCQ_ERR_CHKSUM               3
1291 #define ASCQ_ERR_START_CHIP           4
1292 #define ASCQ_ERR_INT_TARGET_ID        5
1293 #define ASCQ_ERR_INT_LOCAL_MEM        6
1294 #define ASCQ_ERR_HALT_RISC            7
1295 #define ASCQ_ERR_GET_ASPI_ENTRY       8
1296 #define ASCQ_ERR_CLOSE_ASPI           9
1297 #define ASCQ_ERR_HOST_INQUIRY         0x0A
1298 #define ASCQ_ERR_SAVED_SRB_BAD        0x0B
1299 #define ASCQ_ERR_QCNTL_SG_LIST        0x0C
1300 #define ASCQ_ERR_Q_STATUS             0x0D
1301 #define ASCQ_ERR_WR_SCSIQ             0x0E
1302 #define ASCQ_ERR_PC_ADDR              0x0F
1303 #define ASCQ_ERR_SYN_OFFSET           0x10
1304 #define ASCQ_ERR_SYN_XFER_TIME        0x11
1305 #define ASCQ_ERR_LOCK_DMA             0x12
1306 #define ASCQ_ERR_UNLOCK_DMA           0x13
1307 #define ASCQ_ERR_VDS_CHK_INSTALL      0x14
1308 #define ASCQ_ERR_MICRO_CODE_HALT      0x15
1309 #define ASCQ_ERR_SET_LRAM_ADDR        0x16
1310 #define ASCQ_ERR_CUR_QNG              0x17
1311 #define ASCQ_ERR_SG_Q_LINKS           0x18
1312 #define ASCQ_ERR_SCSIQ_PTR            0x19
1313 #define ASCQ_ERR_ISR_RE_ENTRY         0x1A
1314 #define ASCQ_ERR_CRITICAL_RE_ENTRY    0x1B
1315 #define ASCQ_ERR_ISR_ON_CRITICAL      0x1C
1316 #define ASCQ_ERR_SG_LIST_ODD_ADDRESS  0x1D
1317 #define ASCQ_ERR_XFER_ADDRESS_TOO_BIG 0x1E
1318 #define ASCQ_ERR_SCSIQ_NULL_PTR       0x1F
1319 #define ASCQ_ERR_SCSIQ_BAD_NEXT_PTR   0x20
1320 #define ASCQ_ERR_GET_NUM_OF_FREE_Q    0x21
1321 #define ASCQ_ERR_SEND_SCSI_Q          0x22
1322 #define ASCQ_ERR_HOST_REQ_RISC_HALT   0x23
1323 #define ASCQ_ERR_RESET_SDTR           0x24
1324
1325 /*
1326  * Warning code values are set in ASC_DVC_VAR  'warn_code'.
1327  */
1328 #define ASC_WARN_NO_ERROR             0x0000
1329 #define ASC_WARN_IO_PORT_ROTATE       0x0001
1330 #define ASC_WARN_EEPROM_CHKSUM        0x0002
1331 #define ASC_WARN_IRQ_MODIFIED         0x0004
1332 #define ASC_WARN_AUTO_CONFIG          0x0008
1333 #define ASC_WARN_CMD_QNG_CONFLICT     0x0010
1334 #define ASC_WARN_EEPROM_RECOVER       0x0020
1335 #define ASC_WARN_CFG_MSW_RECOVER      0x0040
1336 #define ASC_WARN_SET_PCI_CONFIG_SPACE 0x0080
1337
1338 /*
1339  * Error code values are set in ASC_DVC_VAR  'err_code'.
1340  */
1341 #define ASC_IERR_WRITE_EEPROM         0x0001
1342 #define ASC_IERR_MCODE_CHKSUM         0x0002
1343 #define ASC_IERR_SET_PC_ADDR          0x0004
1344 #define ASC_IERR_START_STOP_CHIP      0x0008
1345 #define ASC_IERR_IRQ_NO               0x0010
1346 #define ASC_IERR_SET_IRQ_NO           0x0020
1347 #define ASC_IERR_CHIP_VERSION         0x0040
1348 #define ASC_IERR_SET_SCSI_ID          0x0080
1349 #define ASC_IERR_GET_PHY_ADDR         0x0100
1350 #define ASC_IERR_BAD_SIGNATURE        0x0200
1351 #define ASC_IERR_NO_BUS_TYPE          0x0400
1352 #define ASC_IERR_SCAM                 0x0800
1353 #define ASC_IERR_SET_SDTR             0x1000
1354 #define ASC_IERR_RW_LRAM              0x8000
1355
1356 #define ASC_DEF_IRQ_NO  10
1357 #define ASC_MAX_IRQ_NO  15
1358 #define ASC_MIN_IRQ_NO  10
1359 #define ASC_MIN_REMAIN_Q        (0x02)
1360 #define ASC_DEF_MAX_TOTAL_QNG   (0xF0)
1361 #define ASC_MIN_TAG_Q_PER_DVC   (0x04)
1362 #define ASC_DEF_TAG_Q_PER_DVC   (0x04)
1363 #define ASC_MIN_FREE_Q        ASC_MIN_REMAIN_Q
1364 #define ASC_MIN_TOTAL_QNG     ((ASC_MAX_SG_QUEUE)+(ASC_MIN_FREE_Q))
1365 #define ASC_MAX_TOTAL_QNG 240
1366 #define ASC_MAX_PCI_ULTRA_INRAM_TOTAL_QNG 16
1367 #define ASC_MAX_PCI_ULTRA_INRAM_TAG_QNG   8
1368 #define ASC_MAX_PCI_INRAM_TOTAL_QNG  20
1369 #define ASC_MAX_INRAM_TAG_QNG   16
1370 #define ASC_IOADR_TABLE_MAX_IX  11
1371 #define ASC_IOADR_GAP   0x10
1372 #define ASC_SEARCH_IOP_GAP 0x10
1373 #define ASC_MIN_IOP_ADDR   (PortAddr)0x0100
1374 #define ASC_MAX_IOP_ADDR   (PortAddr)0x3F0
1375 #define ASC_IOADR_1     (PortAddr)0x0110
1376 #define ASC_IOADR_2     (PortAddr)0x0130
1377 #define ASC_IOADR_3     (PortAddr)0x0150
1378 #define ASC_IOADR_4     (PortAddr)0x0190
1379 #define ASC_IOADR_5     (PortAddr)0x0210
1380 #define ASC_IOADR_6     (PortAddr)0x0230
1381 #define ASC_IOADR_7     (PortAddr)0x0250
1382 #define ASC_IOADR_8     (PortAddr)0x0330
1383 #define ASC_IOADR_DEF   ASC_IOADR_8
1384 #define ASC_LIB_SCSIQ_WK_SP        256
1385 #define ASC_MAX_SYN_XFER_NO        16
1386 #define ASC_SYN_MAX_OFFSET         0x0F
1387 #define ASC_DEF_SDTR_OFFSET        0x0F
1388 #define ASC_DEF_SDTR_INDEX         0x00
1389 #define ASC_SDTR_ULTRA_PCI_10MB_INDEX  0x02
1390 #define SYN_XFER_NS_0  25
1391 #define SYN_XFER_NS_1  30
1392 #define SYN_XFER_NS_2  35
1393 #define SYN_XFER_NS_3  40
1394 #define SYN_XFER_NS_4  50
1395 #define SYN_XFER_NS_5  60
1396 #define SYN_XFER_NS_6  70
1397 #define SYN_XFER_NS_7  85
1398 #define SYN_ULTRA_XFER_NS_0    12
1399 #define SYN_ULTRA_XFER_NS_1    19
1400 #define SYN_ULTRA_XFER_NS_2    25
1401 #define SYN_ULTRA_XFER_NS_3    32
1402 #define SYN_ULTRA_XFER_NS_4    38
1403 #define SYN_ULTRA_XFER_NS_5    44
1404 #define SYN_ULTRA_XFER_NS_6    50
1405 #define SYN_ULTRA_XFER_NS_7    57
1406 #define SYN_ULTRA_XFER_NS_8    63
1407 #define SYN_ULTRA_XFER_NS_9    69
1408 #define SYN_ULTRA_XFER_NS_10   75
1409 #define SYN_ULTRA_XFER_NS_11   82
1410 #define SYN_ULTRA_XFER_NS_12   88
1411 #define SYN_ULTRA_XFER_NS_13   94
1412 #define SYN_ULTRA_XFER_NS_14  100
1413 #define SYN_ULTRA_XFER_NS_15  107
1414
1415 typedef struct ext_msg {
1416         uchar msg_type;
1417         uchar msg_len;
1418         uchar msg_req;
1419         union {
1420                 struct {
1421                         uchar sdtr_xfer_period;
1422                         uchar sdtr_req_ack_offset;
1423                 } sdtr;
1424                 struct {
1425                         uchar wdtr_width;
1426                 } wdtr;
1427                 struct {
1428                         uchar mdp_b3;
1429                         uchar mdp_b2;
1430                         uchar mdp_b1;
1431                         uchar mdp_b0;
1432                 } mdp;
1433         } u_ext_msg;
1434         uchar res;
1435 } EXT_MSG;
1436
1437 #define xfer_period     u_ext_msg.sdtr.sdtr_xfer_period
1438 #define req_ack_offset  u_ext_msg.sdtr.sdtr_req_ack_offset
1439 #define wdtr_width      u_ext_msg.wdtr.wdtr_width
1440 #define mdp_b3          u_ext_msg.mdp_b3
1441 #define mdp_b2          u_ext_msg.mdp_b2
1442 #define mdp_b1          u_ext_msg.mdp_b1
1443 #define mdp_b0          u_ext_msg.mdp_b0
1444
1445 typedef struct asc_dvc_cfg {
1446         ASC_SCSI_BIT_ID_TYPE can_tagged_qng;
1447         ASC_SCSI_BIT_ID_TYPE cmd_qng_enabled;
1448         ASC_SCSI_BIT_ID_TYPE disc_enable;
1449         ASC_SCSI_BIT_ID_TYPE sdtr_enable;
1450         uchar chip_scsi_id;
1451         uchar isa_dma_speed;
1452         uchar isa_dma_channel;
1453         uchar chip_version;
1454         ushort lib_serial_no;
1455         ushort lib_version;
1456         ushort mcode_date;
1457         ushort mcode_version;
1458         uchar max_tag_qng[ASC_MAX_TID + 1];
1459         uchar *overrun_buf;
1460         uchar sdtr_period_offset[ASC_MAX_TID + 1];
1461         ushort pci_slot_info;
1462         uchar adapter_info[6];
1463         struct device *dev;
1464 } ASC_DVC_CFG;
1465
1466 #define ASC_DEF_DVC_CNTL       0xFFFF
1467 #define ASC_DEF_CHIP_SCSI_ID   7
1468 #define ASC_DEF_ISA_DMA_SPEED  4
1469 #define ASC_INIT_STATE_NULL          0x0000
1470 #define ASC_INIT_STATE_BEG_GET_CFG   0x0001
1471 #define ASC_INIT_STATE_END_GET_CFG   0x0002
1472 #define ASC_INIT_STATE_BEG_SET_CFG   0x0004
1473 #define ASC_INIT_STATE_END_SET_CFG   0x0008
1474 #define ASC_INIT_STATE_BEG_LOAD_MC   0x0010
1475 #define ASC_INIT_STATE_END_LOAD_MC   0x0020
1476 #define ASC_INIT_STATE_BEG_INQUIRY   0x0040
1477 #define ASC_INIT_STATE_END_INQUIRY   0x0080
1478 #define ASC_INIT_RESET_SCSI_DONE     0x0100
1479 #define ASC_INIT_STATE_WITHOUT_EEP   0x8000
1480 #define ASC_BUG_FIX_IF_NOT_DWB       0x0001
1481 #define ASC_BUG_FIX_ASYN_USE_SYN     0x0002
1482 #define ASYN_SDTR_DATA_FIX_PCI_REV_AB 0x41
1483 #define ASC_MIN_TAGGED_CMD  7
1484 #define ASC_MAX_SCSI_RESET_WAIT      30
1485
1486 struct asc_dvc_var;             /* Forward Declaration. */
1487
1488 typedef void (*ASC_ISR_CALLBACK) (struct asc_dvc_var *, ASC_QDONE_INFO *);
1489 typedef int (*ASC_EXE_CALLBACK) (struct asc_dvc_var *, ASC_SCSI_Q *);
1490
1491 typedef struct asc_dvc_var {
1492         PortAddr iop_base;
1493         ushort err_code;
1494         ushort dvc_cntl;
1495         ushort bug_fix_cntl;
1496         ushort bus_type;
1497         ASC_ISR_CALLBACK isr_callback;
1498         ASC_EXE_CALLBACK exe_callback;
1499         ASC_SCSI_BIT_ID_TYPE init_sdtr;
1500         ASC_SCSI_BIT_ID_TYPE sdtr_done;
1501         ASC_SCSI_BIT_ID_TYPE use_tagged_qng;
1502         ASC_SCSI_BIT_ID_TYPE unit_not_ready;
1503         ASC_SCSI_BIT_ID_TYPE queue_full_or_busy;
1504         ASC_SCSI_BIT_ID_TYPE start_motor;
1505         uchar scsi_reset_wait;
1506         uchar chip_no;
1507         char is_in_int;
1508         uchar max_total_qng;
1509         uchar cur_total_qng;
1510         uchar in_critical_cnt;
1511         uchar irq_no;
1512         uchar last_q_shortage;
1513         ushort init_state;
1514         uchar cur_dvc_qng[ASC_MAX_TID + 1];
1515         uchar max_dvc_qng[ASC_MAX_TID + 1];
1516         ASC_SCSI_Q *scsiq_busy_head[ASC_MAX_TID + 1];
1517         ASC_SCSI_Q *scsiq_busy_tail[ASC_MAX_TID + 1];
1518         uchar sdtr_period_tbl[ASC_MAX_SYN_XFER_NO];
1519         ASC_DVC_CFG *cfg;
1520         ASC_SCSI_BIT_ID_TYPE pci_fix_asyn_xfer_always;
1521         char redo_scam;
1522         ushort res2;
1523         uchar dos_int13_table[ASC_MAX_TID + 1];
1524         ASC_DCNT max_dma_count;
1525         ASC_SCSI_BIT_ID_TYPE no_scam;
1526         ASC_SCSI_BIT_ID_TYPE pci_fix_asyn_xfer;
1527         uchar max_sdtr_index;
1528         uchar host_init_sdtr_index;
1529         struct asc_board *drv_ptr;
1530         ASC_DCNT uc_break;
1531 } ASC_DVC_VAR;
1532
1533 typedef struct asc_dvc_inq_info {
1534         uchar type[ASC_MAX_TID + 1][ASC_MAX_LUN + 1];
1535 } ASC_DVC_INQ_INFO;
1536
1537 typedef struct asc_cap_info {
1538         ASC_DCNT lba;
1539         ASC_DCNT blk_size;
1540 } ASC_CAP_INFO;
1541
1542 typedef struct asc_cap_info_array {
1543         ASC_CAP_INFO cap_info[ASC_MAX_TID + 1][ASC_MAX_LUN + 1];
1544 } ASC_CAP_INFO_ARRAY;
1545
1546 #define ASC_MCNTL_NO_SEL_TIMEOUT  (ushort)0x0001
1547 #define ASC_MCNTL_NULL_TARGET     (ushort)0x0002
1548 #define ASC_CNTL_INITIATOR         (ushort)0x0001
1549 #define ASC_CNTL_BIOS_GT_1GB       (ushort)0x0002
1550 #define ASC_CNTL_BIOS_GT_2_DISK    (ushort)0x0004
1551 #define ASC_CNTL_BIOS_REMOVABLE    (ushort)0x0008
1552 #define ASC_CNTL_NO_SCAM           (ushort)0x0010
1553 #define ASC_CNTL_INT_MULTI_Q       (ushort)0x0080
1554 #define ASC_CNTL_NO_LUN_SUPPORT    (ushort)0x0040
1555 #define ASC_CNTL_NO_VERIFY_COPY    (ushort)0x0100
1556 #define ASC_CNTL_RESET_SCSI        (ushort)0x0200
1557 #define ASC_CNTL_INIT_INQUIRY      (ushort)0x0400
1558 #define ASC_CNTL_INIT_VERBOSE      (ushort)0x0800
1559 #define ASC_CNTL_SCSI_PARITY       (ushort)0x1000
1560 #define ASC_CNTL_BURST_MODE        (ushort)0x2000
1561 #define ASC_CNTL_SDTR_ENABLE_ULTRA (ushort)0x4000
1562 #define ASC_EEP_DVC_CFG_BEG_VL    2
1563 #define ASC_EEP_MAX_DVC_ADDR_VL   15
1564 #define ASC_EEP_DVC_CFG_BEG      32
1565 #define ASC_EEP_MAX_DVC_ADDR     45
1566 #define ASC_EEP_DEFINED_WORDS    10
1567 #define ASC_EEP_MAX_ADDR         63
1568 #define ASC_EEP_RES_WORDS         0
1569 #define ASC_EEP_MAX_RETRY        20
1570 #define ASC_MAX_INIT_BUSY_RETRY   8
1571 #define ASC_EEP_ISA_PNP_WSIZE    16
1572
1573 /*
1574  * These macros keep the chip SCSI id and ISA DMA speed
1575  * bitfields in board order. C bitfields aren't portable
1576  * between big and little-endian platforms so they are
1577  * not used.
1578  */
1579
1580 #define ASC_EEP_GET_CHIP_ID(cfg)    ((cfg)->id_speed & 0x0f)
1581 #define ASC_EEP_GET_DMA_SPD(cfg)    (((cfg)->id_speed & 0xf0) >> 4)
1582 #define ASC_EEP_SET_CHIP_ID(cfg, sid) \
1583    ((cfg)->id_speed = ((cfg)->id_speed & 0xf0) | ((sid) & ASC_MAX_TID))
1584 #define ASC_EEP_SET_DMA_SPD(cfg, spd) \
1585    ((cfg)->id_speed = ((cfg)->id_speed & 0x0f) | ((spd) & 0x0f) << 4)
1586
1587 typedef struct asceep_config {
1588         ushort cfg_lsw;
1589         ushort cfg_msw;
1590         uchar init_sdtr;
1591         uchar disc_enable;
1592         uchar use_cmd_qng;
1593         uchar start_motor;
1594         uchar max_total_qng;
1595         uchar max_tag_qng;
1596         uchar bios_scan;
1597         uchar power_up_wait;
1598         uchar no_scam;
1599         uchar id_speed;         /* low order 4 bits is chip scsi id */
1600         /* high order 4 bits is isa dma speed */
1601         uchar dos_int13_table[ASC_MAX_TID + 1];
1602         uchar adapter_info[6];
1603         ushort cntl;
1604         ushort chksum;
1605 } ASCEEP_CONFIG;
1606
1607 #define ASC_PCI_CFG_LSW_SCSI_PARITY  0x0800
1608 #define ASC_PCI_CFG_LSW_BURST_MODE   0x0080
1609 #define ASC_PCI_CFG_LSW_INTR_ABLE    0x0020
1610
1611 #define ASC_EEP_CMD_READ          0x80
1612 #define ASC_EEP_CMD_WRITE         0x40
1613 #define ASC_EEP_CMD_WRITE_ABLE    0x30
1614 #define ASC_EEP_CMD_WRITE_DISABLE 0x00
1615 #define ASC_OVERRUN_BSIZE  0x00000048UL
1616 #define ASC_CTRL_BREAK_ONCE        0x0001
1617 #define ASC_CTRL_BREAK_STAY_IDLE   0x0002
1618 #define ASCV_MSGOUT_BEG         0x0000
1619 #define ASCV_MSGOUT_SDTR_PERIOD (ASCV_MSGOUT_BEG+3)
1620 #define ASCV_MSGOUT_SDTR_OFFSET (ASCV_MSGOUT_BEG+4)
1621 #define ASCV_BREAK_SAVED_CODE   (ushort)0x0006
1622 #define ASCV_MSGIN_BEG          (ASCV_MSGOUT_BEG+8)
1623 #define ASCV_MSGIN_SDTR_PERIOD  (ASCV_MSGIN_BEG+3)
1624 #define ASCV_MSGIN_SDTR_OFFSET  (ASCV_MSGIN_BEG+4)
1625 #define ASCV_SDTR_DATA_BEG      (ASCV_MSGIN_BEG+8)
1626 #define ASCV_SDTR_DONE_BEG      (ASCV_SDTR_DATA_BEG+8)
1627 #define ASCV_MAX_DVC_QNG_BEG    (ushort)0x0020
1628 #define ASCV_BREAK_ADDR           (ushort)0x0028
1629 #define ASCV_BREAK_NOTIFY_COUNT   (ushort)0x002A
1630 #define ASCV_BREAK_CONTROL        (ushort)0x002C
1631 #define ASCV_BREAK_HIT_COUNT      (ushort)0x002E
1632
1633 #define ASCV_ASCDVC_ERR_CODE_W  (ushort)0x0030
1634 #define ASCV_MCODE_CHKSUM_W   (ushort)0x0032
1635 #define ASCV_MCODE_SIZE_W     (ushort)0x0034
1636 #define ASCV_STOP_CODE_B      (ushort)0x0036
1637 #define ASCV_DVC_ERR_CODE_B   (ushort)0x0037
1638 #define ASCV_OVERRUN_PADDR_D  (ushort)0x0038
1639 #define ASCV_OVERRUN_BSIZE_D  (ushort)0x003C
1640 #define ASCV_HALTCODE_W       (ushort)0x0040
1641 #define ASCV_CHKSUM_W         (ushort)0x0042
1642 #define ASCV_MC_DATE_W        (ushort)0x0044
1643 #define ASCV_MC_VER_W         (ushort)0x0046
1644 #define ASCV_NEXTRDY_B        (ushort)0x0048
1645 #define ASCV_DONENEXT_B       (ushort)0x0049
1646 #define ASCV_USE_TAGGED_QNG_B (ushort)0x004A
1647 #define ASCV_SCSIBUSY_B       (ushort)0x004B
1648 #define ASCV_Q_DONE_IN_PROGRESS_B  (ushort)0x004C
1649 #define ASCV_CURCDB_B         (ushort)0x004D
1650 #define ASCV_RCLUN_B          (ushort)0x004E
1651 #define ASCV_BUSY_QHEAD_B     (ushort)0x004F
1652 #define ASCV_DISC1_QHEAD_B    (ushort)0x0050
1653 #define ASCV_DISC_ENABLE_B    (ushort)0x0052
1654 #define ASCV_CAN_TAGGED_QNG_B (ushort)0x0053
1655 #define ASCV_HOSTSCSI_ID_B    (ushort)0x0055
1656 #define ASCV_MCODE_CNTL_B     (ushort)0x0056
1657 #define ASCV_NULL_TARGET_B    (ushort)0x0057
1658 #define ASCV_FREE_Q_HEAD_W    (ushort)0x0058
1659 #define ASCV_DONE_Q_TAIL_W    (ushort)0x005A
1660 #define ASCV_FREE_Q_HEAD_B    (ushort)(ASCV_FREE_Q_HEAD_W+1)
1661 #define ASCV_DONE_Q_TAIL_B    (ushort)(ASCV_DONE_Q_TAIL_W+1)
1662 #define ASCV_HOST_FLAG_B      (ushort)0x005D
1663 #define ASCV_TOTAL_READY_Q_B  (ushort)0x0064
1664 #define ASCV_VER_SERIAL_B     (ushort)0x0065
1665 #define ASCV_HALTCODE_SAVED_W (ushort)0x0066
1666 #define ASCV_WTM_FLAG_B       (ushort)0x0068
1667 #define ASCV_RISC_FLAG_B      (ushort)0x006A
1668 #define ASCV_REQ_SG_LIST_QP   (ushort)0x006B
1669 #define ASC_HOST_FLAG_IN_ISR        0x01
1670 #define ASC_HOST_FLAG_ACK_INT       0x02
1671 #define ASC_RISC_FLAG_GEN_INT      0x01
1672 #define ASC_RISC_FLAG_REQ_SG_LIST  0x02
1673 #define IOP_CTRL         (0x0F)
1674 #define IOP_STATUS       (0x0E)
1675 #define IOP_INT_ACK      IOP_STATUS
1676 #define IOP_REG_IFC      (0x0D)
1677 #define IOP_SYN_OFFSET    (0x0B)
1678 #define IOP_EXTRA_CONTROL (0x0D)
1679 #define IOP_REG_PC        (0x0C)
1680 #define IOP_RAM_ADDR      (0x0A)
1681 #define IOP_RAM_DATA      (0x08)
1682 #define IOP_EEP_DATA      (0x06)
1683 #define IOP_EEP_CMD       (0x07)
1684 #define IOP_VERSION       (0x03)
1685 #define IOP_CONFIG_HIGH   (0x04)
1686 #define IOP_CONFIG_LOW    (0x02)
1687 #define IOP_SIG_BYTE      (0x01)
1688 #define IOP_SIG_WORD      (0x00)
1689 #define IOP_REG_DC1      (0x0E)
1690 #define IOP_REG_DC0      (0x0C)
1691 #define IOP_REG_SB       (0x0B)
1692 #define IOP_REG_DA1      (0x0A)
1693 #define IOP_REG_DA0      (0x08)
1694 #define IOP_REG_SC       (0x09)
1695 #define IOP_DMA_SPEED    (0x07)
1696 #define IOP_REG_FLAG     (0x07)
1697 #define IOP_FIFO_H       (0x06)
1698 #define IOP_FIFO_L       (0x04)
1699 #define IOP_REG_ID       (0x05)
1700 #define IOP_REG_QP       (0x03)
1701 #define IOP_REG_IH       (0x02)
1702 #define IOP_REG_IX       (0x01)
1703 #define IOP_REG_AX       (0x00)
1704 #define IFC_REG_LOCK      (0x00)
1705 #define IFC_REG_UNLOCK    (0x09)
1706 #define IFC_WR_EN_FILTER  (0x10)
1707 #define IFC_RD_NO_EEPROM  (0x10)
1708 #define IFC_SLEW_RATE     (0x20)
1709 #define IFC_ACT_NEG       (0x40)
1710 #define IFC_INP_FILTER    (0x80)
1711 #define IFC_INIT_DEFAULT  (IFC_ACT_NEG | IFC_REG_UNLOCK)
1712 #define SC_SEL   (uchar)(0x80)
1713 #define SC_BSY   (uchar)(0x40)
1714 #define SC_ACK   (uchar)(0x20)
1715 #define SC_REQ   (uchar)(0x10)
1716 #define SC_ATN   (uchar)(0x08)
1717 #define SC_IO    (uchar)(0x04)
1718 #define SC_CD    (uchar)(0x02)
1719 #define SC_MSG   (uchar)(0x01)
1720 #define SEC_SCSI_CTL         (uchar)(0x80)
1721 #define SEC_ACTIVE_NEGATE    (uchar)(0x40)
1722 #define SEC_SLEW_RATE        (uchar)(0x20)
1723 #define SEC_ENABLE_FILTER    (uchar)(0x10)
1724 #define ASC_HALT_EXTMSG_IN     (ushort)0x8000
1725 #define ASC_HALT_CHK_CONDITION (ushort)0x8100
1726 #define ASC_HALT_SS_QUEUE_FULL (ushort)0x8200
1727 #define ASC_HALT_DISABLE_ASYN_USE_SYN_FIX  (ushort)0x8300
1728 #define ASC_HALT_ENABLE_ASYN_USE_SYN_FIX   (ushort)0x8400
1729 #define ASC_HALT_SDTR_REJECTED (ushort)0x4000
1730 #define ASC_HALT_HOST_COPY_SG_LIST_TO_RISC ( ushort )0x2000
1731 #define ASC_MAX_QNO        0xF8
1732 #define ASC_DATA_SEC_BEG   (ushort)0x0080
1733 #define ASC_DATA_SEC_END   (ushort)0x0080
1734 #define ASC_CODE_SEC_BEG   (ushort)0x0080
1735 #define ASC_CODE_SEC_END   (ushort)0x0080
1736 #define ASC_QADR_BEG       (0x4000)
1737 #define ASC_QADR_USED      (ushort)(ASC_MAX_QNO * 64)
1738 #define ASC_QADR_END       (ushort)0x7FFF
1739 #define ASC_QLAST_ADR      (ushort)0x7FC0
1740 #define ASC_QBLK_SIZE      0x40
1741 #define ASC_BIOS_DATA_QBEG 0xF8
1742 #define ASC_MIN_ACTIVE_QNO 0x01
1743 #define ASC_QLINK_END      0xFF
1744 #define ASC_EEPROM_WORDS   0x10
1745 #define ASC_MAX_MGS_LEN    0x10
1746 #define ASC_BIOS_ADDR_DEF  0xDC00
1747 #define ASC_BIOS_SIZE      0x3800
1748 #define ASC_BIOS_RAM_OFF   0x3800
1749 #define ASC_BIOS_RAM_SIZE  0x800
1750 #define ASC_BIOS_MIN_ADDR  0xC000
1751 #define ASC_BIOS_MAX_ADDR  0xEC00
1752 #define ASC_BIOS_BANK_SIZE 0x0400
1753 #define ASC_MCODE_START_ADDR  0x0080
1754 #define ASC_CFG0_HOST_INT_ON    0x0020
1755 #define ASC_CFG0_BIOS_ON        0x0040
1756 #define ASC_CFG0_VERA_BURST_ON  0x0080
1757 #define ASC_CFG0_SCSI_PARITY_ON 0x0800
1758 #define ASC_CFG1_SCSI_TARGET_ON 0x0080
1759 #define ASC_CFG1_LRAM_8BITS_ON  0x0800
1760 #define ASC_CFG_MSW_CLR_MASK    0x3080
1761 #define CSW_TEST1             (ASC_CS_TYPE)0x8000
1762 #define CSW_AUTO_CONFIG       (ASC_CS_TYPE)0x4000
1763 #define CSW_RESERVED1         (ASC_CS_TYPE)0x2000
1764 #define CSW_IRQ_WRITTEN       (ASC_CS_TYPE)0x1000
1765 #define CSW_33MHZ_SELECTED    (ASC_CS_TYPE)0x0800
1766 #define CSW_TEST2             (ASC_CS_TYPE)0x0400
1767 #define CSW_TEST3             (ASC_CS_TYPE)0x0200
1768 #define CSW_RESERVED2         (ASC_CS_TYPE)0x0100
1769 #define CSW_DMA_DONE          (ASC_CS_TYPE)0x0080
1770 #define CSW_FIFO_RDY          (ASC_CS_TYPE)0x0040
1771 #define CSW_EEP_READ_DONE     (ASC_CS_TYPE)0x0020
1772 #define CSW_HALTED            (ASC_CS_TYPE)0x0010
1773 #define CSW_SCSI_RESET_ACTIVE (ASC_CS_TYPE)0x0008
1774 #define CSW_PARITY_ERR        (ASC_CS_TYPE)0x0004
1775 #define CSW_SCSI_RESET_LATCH  (ASC_CS_TYPE)0x0002
1776 #define CSW_INT_PENDING       (ASC_CS_TYPE)0x0001
1777 #define CIW_CLR_SCSI_RESET_INT (ASC_CS_TYPE)0x1000
1778 #define CIW_INT_ACK      (ASC_CS_TYPE)0x0100
1779 #define CIW_TEST1        (ASC_CS_TYPE)0x0200
1780 #define CIW_TEST2        (ASC_CS_TYPE)0x0400
1781 #define CIW_SEL_33MHZ    (ASC_CS_TYPE)0x0800
1782 #define CIW_IRQ_ACT      (ASC_CS_TYPE)0x1000
1783 #define CC_CHIP_RESET   (uchar)0x80
1784 #define CC_SCSI_RESET   (uchar)0x40
1785 #define CC_HALT         (uchar)0x20
1786 #define CC_SINGLE_STEP  (uchar)0x10
1787 #define CC_DMA_ABLE     (uchar)0x08
1788 #define CC_TEST         (uchar)0x04
1789 #define CC_BANK_ONE     (uchar)0x02
1790 #define CC_DIAG         (uchar)0x01
1791 #define ASC_1000_ID0W      0x04C1
1792 #define ASC_1000_ID0W_FIX  0x00C1
1793 #define ASC_1000_ID1B      0x25
1794 #define ASC_EISA_BIG_IOP_GAP   (0x1C30-0x0C50)
1795 #define ASC_EISA_SMALL_IOP_GAP (0x0020)
1796 #define ASC_EISA_MIN_IOP_ADDR  (0x0C30)
1797 #define ASC_EISA_MAX_IOP_ADDR  (0xFC50)
1798 #define ASC_EISA_REV_IOP_MASK  (0x0C83)
1799 #define ASC_EISA_PID_IOP_MASK  (0x0C80)
1800 #define ASC_EISA_CFG_IOP_MASK  (0x0C86)
1801 #define ASC_GET_EISA_SLOT(iop)  (PortAddr)((iop) & 0xF000)
1802 #define ASC_EISA_ID_740    0x01745004UL
1803 #define ASC_EISA_ID_750    0x01755004UL
1804 #define INS_HALTINT        (ushort)0x6281
1805 #define INS_HALT           (ushort)0x6280
1806 #define INS_SINT           (ushort)0x6200
1807 #define INS_RFLAG_WTM      (ushort)0x7380
1808 #define ASC_MC_SAVE_CODE_WSIZE  0x500
1809 #define ASC_MC_SAVE_DATA_WSIZE  0x40
1810
1811 typedef struct asc_mc_saved {
1812         ushort data[ASC_MC_SAVE_DATA_WSIZE];
1813         ushort code[ASC_MC_SAVE_CODE_WSIZE];
1814 } ASC_MC_SAVED;
1815
1816 #define AscGetQDoneInProgress(port)         AscReadLramByte((port), ASCV_Q_DONE_IN_PROGRESS_B)
1817 #define AscPutQDoneInProgress(port, val)    AscWriteLramByte((port), ASCV_Q_DONE_IN_PROGRESS_B, val)
1818 #define AscGetVarFreeQHead(port)            AscReadLramWord((port), ASCV_FREE_Q_HEAD_W)
1819 #define AscGetVarDoneQTail(port)            AscReadLramWord((port), ASCV_DONE_Q_TAIL_W)
1820 #define AscPutVarFreeQHead(port, val)       AscWriteLramWord((port), ASCV_FREE_Q_HEAD_W, val)
1821 #define AscPutVarDoneQTail(port, val)       AscWriteLramWord((port), ASCV_DONE_Q_TAIL_W, val)
1822 #define AscGetRiscVarFreeQHead(port)        AscReadLramByte((port), ASCV_NEXTRDY_B)
1823 #define AscGetRiscVarDoneQTail(port)        AscReadLramByte((port), ASCV_DONENEXT_B)
1824 #define AscPutRiscVarFreeQHead(port, val)   AscWriteLramByte((port), ASCV_NEXTRDY_B, val)
1825 #define AscPutRiscVarDoneQTail(port, val)   AscWriteLramByte((port), ASCV_DONENEXT_B, val)
1826 #define AscPutMCodeSDTRDoneAtID(port, id, data)  AscWriteLramByte((port), (ushort)((ushort)ASCV_SDTR_DONE_BEG+(ushort)id), (data));
1827 #define AscGetMCodeSDTRDoneAtID(port, id)        AscReadLramByte((port), (ushort)((ushort)ASCV_SDTR_DONE_BEG+(ushort)id));
1828 #define AscPutMCodeInitSDTRAtID(port, id, data)  AscWriteLramByte((port), (ushort)((ushort)ASCV_SDTR_DATA_BEG+(ushort)id), data);
1829 #define AscGetMCodeInitSDTRAtID(port, id)        AscReadLramByte((port), (ushort)((ushort)ASCV_SDTR_DATA_BEG+(ushort)id));
1830 #define AscSynIndexToPeriod(index)        (uchar)(asc_dvc->sdtr_period_tbl[ (index) ])
1831 #define AscGetChipSignatureByte(port)     (uchar)inp((port)+IOP_SIG_BYTE)
1832 #define AscGetChipSignatureWord(port)     (ushort)inpw((port)+IOP_SIG_WORD)
1833 #define AscGetChipVerNo(port)             (uchar)inp((port)+IOP_VERSION)
1834 #define AscGetChipCfgLsw(port)            (ushort)inpw((port)+IOP_CONFIG_LOW)
1835 #define AscGetChipCfgMsw(port)            (ushort)inpw((port)+IOP_CONFIG_HIGH)
1836 #define AscSetChipCfgLsw(port, data)      outpw((port)+IOP_CONFIG_LOW, data)
1837 #define AscSetChipCfgMsw(port, data)      outpw((port)+IOP_CONFIG_HIGH, data)
1838 #define AscGetChipEEPCmd(port)            (uchar)inp((port)+IOP_EEP_CMD)
1839 #define AscSetChipEEPCmd(port, data)      outp((port)+IOP_EEP_CMD, data)
1840 #define AscGetChipEEPData(port)           (ushort)inpw((port)+IOP_EEP_DATA)
1841 #define AscSetChipEEPData(port, data)     outpw((port)+IOP_EEP_DATA, data)
1842 #define AscGetChipLramAddr(port)          (ushort)inpw((PortAddr)((port)+IOP_RAM_ADDR))
1843 #define AscSetChipLramAddr(port, addr)    outpw((PortAddr)((port)+IOP_RAM_ADDR), addr)
1844 #define AscGetChipLramData(port)          (ushort)inpw((port)+IOP_RAM_DATA)
1845 #define AscSetChipLramData(port, data)    outpw((port)+IOP_RAM_DATA, data)
1846 #define AscGetChipIFC(port)               (uchar)inp((port)+IOP_REG_IFC)
1847 #define AscSetChipIFC(port, data)          outp((port)+IOP_REG_IFC, data)
1848 #define AscGetChipStatus(port)            (ASC_CS_TYPE)inpw((port)+IOP_STATUS)
1849 #define AscSetChipStatus(port, cs_val)    outpw((port)+IOP_STATUS, cs_val)
1850 #define AscGetChipControl(port)           (uchar)inp((port)+IOP_CTRL)
1851 #define AscSetChipControl(port, cc_val)   outp((port)+IOP_CTRL, cc_val)
1852 #define AscGetChipSyn(port)               (uchar)inp((port)+IOP_SYN_OFFSET)
1853 #define AscSetChipSyn(port, data)         outp((port)+IOP_SYN_OFFSET, data)
1854 #define AscSetPCAddr(port, data)          outpw((port)+IOP_REG_PC, data)
1855 #define AscGetPCAddr(port)                (ushort)inpw((port)+IOP_REG_PC)
1856 #define AscIsIntPending(port)             (AscGetChipStatus(port) & (CSW_INT_PENDING | CSW_SCSI_RESET_LATCH))
1857 #define AscGetChipScsiID(port)            ((AscGetChipCfgLsw(port) >> 8) & ASC_MAX_TID)
1858 #define AscGetExtraControl(port)          (uchar)inp((port)+IOP_EXTRA_CONTROL)
1859 #define AscSetExtraControl(port, data)    outp((port)+IOP_EXTRA_CONTROL, data)
1860 #define AscReadChipAX(port)               (ushort)inpw((port)+IOP_REG_AX)
1861 #define AscWriteChipAX(port, data)        outpw((port)+IOP_REG_AX, data)
1862 #define AscReadChipIX(port)               (uchar)inp((port)+IOP_REG_IX)
1863 #define AscWriteChipIX(port, data)        outp((port)+IOP_REG_IX, data)
1864 #define AscReadChipIH(port)               (ushort)inpw((port)+IOP_REG_IH)
1865 #define AscWriteChipIH(port, data)        outpw((port)+IOP_REG_IH, data)
1866 #define AscReadChipQP(port)               (uchar)inp((port)+IOP_REG_QP)
1867 #define AscWriteChipQP(port, data)        outp((port)+IOP_REG_QP, data)
1868 #define AscReadChipFIFO_L(port)           (ushort)inpw((port)+IOP_REG_FIFO_L)
1869 #define AscWriteChipFIFO_L(port, data)    outpw((port)+IOP_REG_FIFO_L, data)
1870 #define AscReadChipFIFO_H(port)           (ushort)inpw((port)+IOP_REG_FIFO_H)
1871 #define AscWriteChipFIFO_H(port, data)    outpw((port)+IOP_REG_FIFO_H, data)
1872 #define AscReadChipDmaSpeed(port)         (uchar)inp((port)+IOP_DMA_SPEED)
1873 #define AscWriteChipDmaSpeed(port, data)  outp((port)+IOP_DMA_SPEED, data)
1874 #define AscReadChipDA0(port)              (ushort)inpw((port)+IOP_REG_DA0)
1875 #define AscWriteChipDA0(port)             outpw((port)+IOP_REG_DA0, data)
1876 #define AscReadChipDA1(port)              (ushort)inpw((port)+IOP_REG_DA1)
1877 #define AscWriteChipDA1(port)             outpw((port)+IOP_REG_DA1, data)
1878 #define AscReadChipDC0(port)              (ushort)inpw((port)+IOP_REG_DC0)
1879 #define AscWriteChipDC0(port)             outpw((port)+IOP_REG_DC0, data)
1880 #define AscReadChipDC1(port)              (ushort)inpw((port)+IOP_REG_DC1)
1881 #define AscWriteChipDC1(port)             outpw((port)+IOP_REG_DC1, data)
1882 #define AscReadChipDvcID(port)            (uchar)inp((port)+IOP_REG_ID)
1883 #define AscWriteChipDvcID(port, data)     outp((port)+IOP_REG_ID, data)
1884
1885 static int AscWriteEEPCmdReg(PortAddr iop_base, uchar cmd_reg);
1886 static int AscWriteEEPDataReg(PortAddr iop_base, ushort data_reg);
1887 static void AscWaitEEPRead(void);
1888 static void AscWaitEEPWrite(void);
1889 static ushort AscReadEEPWord(PortAddr, uchar);
1890 static ushort AscWriteEEPWord(PortAddr, uchar, ushort);
1891 static ushort AscGetEEPConfig(PortAddr, ASCEEP_CONFIG *, ushort);
1892 static int AscSetEEPConfigOnce(PortAddr, ASCEEP_CONFIG *, ushort);
1893 static int AscSetEEPConfig(PortAddr, ASCEEP_CONFIG *, ushort);
1894 static int AscStartChip(PortAddr);
1895 static int AscStopChip(PortAddr);
1896 static void AscSetChipIH(PortAddr, ushort);
1897 static int AscIsChipHalted(PortAddr);
1898 static void AscAckInterrupt(PortAddr);
1899 static void AscDisableInterrupt(PortAddr);
1900 static void AscEnableInterrupt(PortAddr);
1901 static void AscSetBank(PortAddr, uchar);
1902 static int AscResetChipAndScsiBus(ASC_DVC_VAR *);
1903 #ifdef CONFIG_ISA
1904 static ushort AscGetIsaDmaChannel(PortAddr);
1905 static ushort AscSetIsaDmaChannel(PortAddr, ushort);
1906 static uchar AscSetIsaDmaSpeed(PortAddr, uchar);
1907 static uchar AscGetIsaDmaSpeed(PortAddr);
1908 #endif /* CONFIG_ISA */
1909 static uchar AscReadLramByte(PortAddr, ushort);
1910 static ushort AscReadLramWord(PortAddr, ushort);
1911 #if CC_VERY_LONG_SG_LIST
1912 static ASC_DCNT AscReadLramDWord(PortAddr, ushort);
1913 #endif /* CC_VERY_LONG_SG_LIST */
1914 static void AscWriteLramWord(PortAddr, ushort, ushort);
1915 static void AscWriteLramByte(PortAddr, ushort, uchar);
1916 static ASC_DCNT AscMemSumLramWord(PortAddr, ushort, int);
1917 static void AscMemWordSetLram(PortAddr, ushort, ushort, int);
1918 static void AscMemWordCopyPtrToLram(PortAddr, ushort, uchar *, int);
1919 static void AscMemDWordCopyPtrToLram(PortAddr, ushort, uchar *, int);
1920 static void AscMemWordCopyPtrFromLram(PortAddr, ushort, uchar *, int);
1921 static ushort AscInitAscDvcVar(ASC_DVC_VAR *);
1922 static ushort AscInitFromEEP(ASC_DVC_VAR *);
1923 static ushort AscInitFromAscDvcVar(ASC_DVC_VAR *);
1924 static ushort AscInitMicroCodeVar(ASC_DVC_VAR *);
1925 static int AscTestExternalLram(ASC_DVC_VAR *);
1926 static uchar AscMsgOutSDTR(ASC_DVC_VAR *, uchar, uchar);
1927 static uchar AscCalSDTRData(ASC_DVC_VAR *, uchar, uchar);
1928 static void AscSetChipSDTR(PortAddr, uchar, uchar);
1929 static uchar AscGetSynPeriodIndex(ASC_DVC_VAR *, uchar);
1930 static uchar AscAllocFreeQueue(PortAddr, uchar);
1931 static uchar AscAllocMultipleFreeQueue(PortAddr, uchar, uchar);
1932 static int AscHostReqRiscHalt(PortAddr);
1933 static int AscStopQueueExe(PortAddr);
1934 static int AscSendScsiQueue(ASC_DVC_VAR *,
1935                             ASC_SCSI_Q *scsiq, uchar n_q_required);
1936 static int AscPutReadyQueue(ASC_DVC_VAR *, ASC_SCSI_Q *, uchar);
1937 static int AscPutReadySgListQueue(ASC_DVC_VAR *, ASC_SCSI_Q *, uchar);
1938 static int AscSetChipSynRegAtID(PortAddr, uchar, uchar);
1939 static int AscSetRunChipSynRegAtID(PortAddr, uchar, uchar);
1940 static ushort AscInitLram(ASC_DVC_VAR *);
1941 static ushort AscInitQLinkVar(ASC_DVC_VAR *);
1942 static int AscSetLibErrorCode(ASC_DVC_VAR *, ushort);
1943 static int AscIsrChipHalted(ASC_DVC_VAR *);
1944 static uchar _AscCopyLramScsiDoneQ(PortAddr, ushort,
1945                                    ASC_QDONE_INFO *, ASC_DCNT);
1946 static int AscIsrQDone(ASC_DVC_VAR *);
1947 static int AscCompareString(uchar *, uchar *, int);
1948 #ifdef CONFIG_ISA
1949 static ushort AscGetEisaChipCfg(PortAddr);
1950 static ASC_DCNT AscGetEisaProductID(PortAddr);
1951 static PortAddr AscSearchIOPortAddrEISA(PortAddr);
1952 static PortAddr AscSearchIOPortAddr11(PortAddr);
1953 static PortAddr AscSearchIOPortAddr(PortAddr, ushort);
1954 static void AscSetISAPNPWaitForKey(void);
1955 #endif /* CONFIG_ISA */
1956 static uchar AscGetChipScsiCtrl(PortAddr);
1957 static uchar AscSetChipScsiID(PortAddr, uchar);
1958 static uchar AscGetChipVersion(PortAddr, ushort);
1959 static ushort AscGetChipBusType(PortAddr);
1960 static ASC_DCNT AscLoadMicroCode(PortAddr, ushort, uchar *, ushort);
1961 static int AscFindSignature(PortAddr);
1962 static void AscToggleIRQAct(PortAddr);
1963 static uchar AscGetChipIRQ(PortAddr, ushort);
1964 static uchar AscSetChipIRQ(PortAddr, uchar, ushort);
1965 static ushort AscGetChipBiosAddress(PortAddr, ushort);
1966 static inline ulong DvcEnterCritical(void);
1967 static inline void DvcLeaveCritical(ulong);
1968 #ifdef CONFIG_PCI
1969 static uchar DvcReadPCIConfigByte(ASC_DVC_VAR *, ushort);
1970 static void DvcWritePCIConfigByte(ASC_DVC_VAR *, ushort, uchar);
1971 #endif /* CONFIG_PCI */
1972 static ushort AscGetChipBiosAddress(PortAddr, ushort);
1973 static void DvcSleepMilliSecond(ASC_DCNT);
1974 static void DvcDelayNanoSecond(ASC_DVC_VAR *, ASC_DCNT);
1975 static void DvcPutScsiQ(PortAddr, ushort, uchar *, int);
1976 static void DvcGetQinfo(PortAddr, ushort, uchar *, int);
1977 static ushort AscInitGetConfig(ASC_DVC_VAR *);
1978 static ushort AscInitSetConfig(ASC_DVC_VAR *);
1979 static ushort AscInitAsc1000Driver(ASC_DVC_VAR *);
1980 static void AscAsyncFix(ASC_DVC_VAR *, uchar, ASC_SCSI_INQUIRY *);
1981 static int AscTagQueuingSafe(ASC_SCSI_INQUIRY *);
1982 static void AscInquiryHandling(ASC_DVC_VAR *, uchar, ASC_SCSI_INQUIRY *);
1983 static int AscExeScsiQueue(ASC_DVC_VAR *, ASC_SCSI_Q *);
1984 static int AscISR(ASC_DVC_VAR *);
1985 static uint AscGetNumOfFreeQueue(ASC_DVC_VAR *, uchar, uchar);
1986 static int AscSgListToQueue(int);
1987 #ifdef CONFIG_ISA
1988 static void AscEnableIsaDma(uchar);
1989 #endif /* CONFIG_ISA */
1990 static ASC_DCNT AscGetMaxDmaCount(ushort);
1991 static const char *advansys_info(struct Scsi_Host *shost);
1992
1993 /*
1994  * --- Adv Library Constants and Macros
1995  */
1996
1997 #define ADV_LIB_VERSION_MAJOR  5
1998 #define ADV_LIB_VERSION_MINOR  14
1999
2000 /*
2001  * Define Adv Library required special types.
2002  */
2003
2004 /*
2005  * Portable Data Types
2006  *
2007  * Any instance where a 32-bit long or pointer type is assumed
2008  * for precision or HW defined structures, the following define
2009  * types must be used. In Linux the char, short, and int types
2010  * are all consistent at 8, 16, and 32 bits respectively. Pointers
2011  * and long types are 64 bits on Alpha and UltraSPARC.
2012  */
2013 #define ADV_PADDR __u32         /* Physical address data type. */
2014 #define ADV_VADDR __u32         /* Virtual address data type. */
2015 #define ADV_DCNT  __u32         /* Unsigned Data count type. */
2016 #define ADV_SDCNT __s32         /* Signed Data count type. */
2017
2018 /*
2019  * These macros are used to convert a virtual address to a
2020  * 32-bit value. This currently can be used on Linux Alpha
2021  * which uses 64-bit virtual address but a 32-bit bus address.
2022  * This is likely to break in the future, but doing this now
2023  * will give us time to change the HW and FW to handle 64-bit
2024  * addresses.
2025  */
2026 #define ADV_VADDR_TO_U32   virt_to_bus
2027 #define ADV_U32_TO_VADDR   bus_to_virt
2028
2029 #define AdvPortAddr  void __iomem *     /* Virtual memory address size */
2030
2031 /*
2032  * Define Adv Library required memory access macros.
2033  */
2034 #define ADV_MEM_READB(addr) readb(addr)
2035 #define ADV_MEM_READW(addr) readw(addr)
2036 #define ADV_MEM_WRITEB(addr, byte) writeb(byte, addr)
2037 #define ADV_MEM_WRITEW(addr, word) writew(word, addr)
2038 #define ADV_MEM_WRITEDW(addr, dword) writel(dword, addr)
2039
2040 #define ADV_CARRIER_COUNT (ASC_DEF_MAX_HOST_QNG + 15)
2041
2042 /*
2043  * For wide  boards a CDB length maximum of 16 bytes
2044  * is supported.
2045  */
2046 #define ADV_MAX_CDB_LEN     16
2047
2048 /*
2049  * Define total number of simultaneous maximum element scatter-gather
2050  * request blocks per wide adapter. ASC_DEF_MAX_HOST_QNG (253) is the
2051  * maximum number of outstanding commands per wide host adapter. Each
2052  * command uses one or more ADV_SG_BLOCK each with 15 scatter-gather
2053  * elements. Allow each command to have at least one ADV_SG_BLOCK structure.
2054  * This allows about 15 commands to have the maximum 17 ADV_SG_BLOCK
2055  * structures or 255 scatter-gather elements.
2056  *
2057  */
2058 #define ADV_TOT_SG_BLOCK        ASC_DEF_MAX_HOST_QNG
2059
2060 /*
2061  * Define Adv Library required maximum number of scatter-gather
2062  * elements per request.
2063  */
2064 #define ADV_MAX_SG_LIST         255
2065
2066 /* Number of SG blocks needed. */
2067 #define ADV_NUM_SG_BLOCK \
2068     ((ADV_MAX_SG_LIST + (NO_OF_SG_PER_BLOCK - 1))/NO_OF_SG_PER_BLOCK)
2069
2070 /* Total contiguous memory needed for SG blocks. */
2071 #define ADV_SG_TOTAL_MEM_SIZE \
2072     (sizeof(ADV_SG_BLOCK) *  ADV_NUM_SG_BLOCK)
2073
2074 #define ADV_PAGE_SIZE PAGE_SIZE
2075
2076 #define ADV_NUM_PAGE_CROSSING \
2077     ((ADV_SG_TOTAL_MEM_SIZE + (ADV_PAGE_SIZE - 1))/ADV_PAGE_SIZE)
2078
2079 #define ADV_EEP_DVC_CFG_BEGIN           (0x00)
2080 #define ADV_EEP_DVC_CFG_END             (0x15)
2081 #define ADV_EEP_DVC_CTL_BEGIN           (0x16)  /* location of OEM name */
2082 #define ADV_EEP_MAX_WORD_ADDR           (0x1E)
2083
2084 #define ADV_EEP_DELAY_MS                100
2085
2086 #define ADV_EEPROM_BIG_ENDIAN          0x8000   /* EEPROM Bit 15 */
2087 #define ADV_EEPROM_BIOS_ENABLE         0x4000   /* EEPROM Bit 14 */
2088 /*
2089  * For the ASC3550 Bit 13 is Termination Polarity control bit.
2090  * For later ICs Bit 13 controls whether the CIS (Card Information
2091  * Service Section) is loaded from EEPROM.
2092  */
2093 #define ADV_EEPROM_TERM_POL            0x2000   /* EEPROM Bit 13 */
2094 #define ADV_EEPROM_CIS_LD              0x2000   /* EEPROM Bit 13 */
2095 /*
2096  * ASC38C1600 Bit 11
2097  *
2098  * If EEPROM Bit 11 is 0 for Function 0, then Function 0 will specify
2099  * INT A in the PCI Configuration Space Int Pin field. If it is 1, then
2100  * Function 0 will specify INT B.
2101  *
2102  * If EEPROM Bit 11 is 0 for Function 1, then Function 1 will specify
2103  * INT B in the PCI Configuration Space Int Pin field. If it is 1, then
2104  * Function 1 will specify INT A.
2105  */
2106 #define ADV_EEPROM_INTAB               0x0800   /* EEPROM Bit 11 */
2107
2108 typedef struct adveep_3550_config {
2109         /* Word Offset, Description */
2110
2111         ushort cfg_lsw;         /* 00 power up initialization */
2112         /*  bit 13 set - Term Polarity Control */
2113         /*  bit 14 set - BIOS Enable */
2114         /*  bit 15 set - Big Endian Mode */
2115         ushort cfg_msw;         /* 01 unused      */
2116         ushort disc_enable;     /* 02 disconnect enable */
2117         ushort wdtr_able;       /* 03 Wide DTR able */
2118         ushort sdtr_able;       /* 04 Synchronous DTR able */
2119         ushort start_motor;     /* 05 send start up motor */
2120         ushort tagqng_able;     /* 06 tag queuing able */
2121         ushort bios_scan;       /* 07 BIOS device control */
2122         ushort scam_tolerant;   /* 08 no scam */
2123
2124         uchar adapter_scsi_id;  /* 09 Host Adapter ID */
2125         uchar bios_boot_delay;  /*    power up wait */
2126
2127         uchar scsi_reset_delay; /* 10 reset delay */
2128         uchar bios_id_lun;      /*    first boot device scsi id & lun */
2129         /*    high nibble is lun */
2130         /*    low nibble is scsi id */
2131
2132         uchar termination;      /* 11 0 - automatic */
2133         /*    1 - low off / high off */
2134         /*    2 - low off / high on */
2135         /*    3 - low on  / high on */
2136         /*    There is no low on  / high off */
2137
2138         uchar reserved1;        /*    reserved byte (not used) */
2139
2140         ushort bios_ctrl;       /* 12 BIOS control bits */
2141         /*  bit 0  BIOS don't act as initiator. */
2142         /*  bit 1  BIOS > 1 GB support */
2143         /*  bit 2  BIOS > 2 Disk Support */
2144         /*  bit 3  BIOS don't support removables */
2145         /*  bit 4  BIOS support bootable CD */
2146         /*  bit 5  BIOS scan enabled */
2147         /*  bit 6  BIOS support multiple LUNs */
2148         /*  bit 7  BIOS display of message */
2149         /*  bit 8  SCAM disabled */
2150         /*  bit 9  Reset SCSI bus during init. */
2151         /*  bit 10 */
2152         /*  bit 11 No verbose initialization. */
2153         /*  bit 12 SCSI parity enabled */
2154         /*  bit 13 */
2155         /*  bit 14 */
2156         /*  bit 15 */
2157         ushort ultra_able;      /* 13 ULTRA speed able */
2158         ushort reserved2;       /* 14 reserved */
2159         uchar max_host_qng;     /* 15 maximum host queuing */
2160         uchar max_dvc_qng;      /*    maximum per device queuing */
2161         ushort dvc_cntl;        /* 16 control bit for driver */
2162         ushort bug_fix;         /* 17 control bit for bug fix */
2163         ushort serial_number_word1;     /* 18 Board serial number word 1 */
2164         ushort serial_number_word2;     /* 19 Board serial number word 2 */
2165         ushort serial_number_word3;     /* 20 Board serial number word 3 */
2166         ushort check_sum;       /* 21 EEP check sum */
2167         uchar oem_name[16];     /* 22 OEM name */
2168         ushort dvc_err_code;    /* 30 last device driver error code */
2169         ushort adv_err_code;    /* 31 last uc and Adv Lib error code */
2170         ushort adv_err_addr;    /* 32 last uc error address */
2171         ushort saved_dvc_err_code;      /* 33 saved last dev. driver error code   */
2172         ushort saved_adv_err_code;      /* 34 saved last uc and Adv Lib error code */
2173         ushort saved_adv_err_addr;      /* 35 saved last uc error address         */
2174         ushort num_of_err;      /* 36 number of error */
2175 } ADVEEP_3550_CONFIG;
2176
2177 typedef struct adveep_38C0800_config {
2178         /* Word Offset, Description */
2179
2180         ushort cfg_lsw;         /* 00 power up initialization */
2181         /*  bit 13 set - Load CIS */
2182         /*  bit 14 set - BIOS Enable */
2183         /*  bit 15 set - Big Endian Mode */
2184         ushort cfg_msw;         /* 01 unused      */
2185         ushort disc_enable;     /* 02 disconnect enable */
2186         ushort wdtr_able;       /* 03 Wide DTR able */
2187         ushort sdtr_speed1;     /* 04 SDTR Speed TID 0-3 */
2188         ushort start_motor;     /* 05 send start up motor */
2189         ushort tagqng_able;     /* 06 tag queuing able */
2190         ushort bios_scan;       /* 07 BIOS device control */
2191         ushort scam_tolerant;   /* 08 no scam */
2192
2193         uchar adapter_scsi_id;  /* 09 Host Adapter ID */
2194         uchar bios_boot_delay;  /*    power up wait */
2195
2196         uchar scsi_reset_delay; /* 10 reset delay */
2197         uchar bios_id_lun;      /*    first boot device scsi id & lun */
2198         /*    high nibble is lun */
2199         /*    low nibble is scsi id */
2200
2201         uchar termination_se;   /* 11 0 - automatic */
2202         /*    1 - low off / high off */
2203         /*    2 - low off / high on */
2204         /*    3 - low on  / high on */
2205         /*    There is no low on  / high off */
2206
2207         uchar termination_lvd;  /* 11 0 - automatic */
2208         /*    1 - low off / high off */
2209         /*    2 - low off / high on */
2210         /*    3 - low on  / high on */
2211         /*    There is no low on  / high off */
2212
2213         ushort bios_ctrl;       /* 12 BIOS control bits */
2214         /*  bit 0  BIOS don't act as initiator. */
2215         /*  bit 1  BIOS > 1 GB support */
2216         /*  bit 2  BIOS > 2 Disk Support */
2217         /*  bit 3  BIOS don't support removables */
2218         /*  bit 4  BIOS support bootable CD */
2219         /*  bit 5  BIOS scan enabled */
2220         /*  bit 6  BIOS support multiple LUNs */
2221         /*  bit 7  BIOS display of message */
2222         /*  bit 8  SCAM disabled */
2223         /*  bit 9  Reset SCSI bus during init. */
2224         /*  bit 10 */
2225         /*  bit 11 No verbose initialization. */
2226         /*  bit 12 SCSI parity enabled */
2227         /*  bit 13 */
2228         /*  bit 14 */
2229         /*  bit 15 */
2230         ushort sdtr_speed2;     /* 13 SDTR speed TID 4-7 */
2231         ushort sdtr_speed3;     /* 14 SDTR speed TID 8-11 */
2232         uchar max_host_qng;     /* 15 maximum host queueing */
2233         uchar max_dvc_qng;      /*    maximum per device queuing */
2234         ushort dvc_cntl;        /* 16 control bit for driver */
2235         ushort sdtr_speed4;     /* 17 SDTR speed 4 TID 12-15 */
2236         ushort serial_number_word1;     /* 18 Board serial number word 1 */
2237         ushort serial_number_word2;     /* 19 Board serial number word 2 */
2238         ushort serial_number_word3;     /* 20 Board serial number word 3 */
2239         ushort check_sum;       /* 21 EEP check sum */
2240         uchar oem_name[16];     /* 22 OEM name */
2241         ushort dvc_err_code;    /* 30 last device driver error code */
2242         ushort adv_err_code;    /* 31 last uc and Adv Lib error code */
2243         ushort adv_err_addr;    /* 32 last uc error address */
2244         ushort saved_dvc_err_code;      /* 33 saved last dev. driver error code   */
2245         ushort saved_adv_err_code;      /* 34 saved last uc and Adv Lib error code */
2246         ushort saved_adv_err_addr;      /* 35 saved last uc error address         */
2247         ushort reserved36;      /* 36 reserved */
2248         ushort reserved37;      /* 37 reserved */
2249         ushort reserved38;      /* 38 reserved */
2250         ushort reserved39;      /* 39 reserved */
2251         ushort reserved40;      /* 40 reserved */
2252         ushort reserved41;      /* 41 reserved */
2253         ushort reserved42;      /* 42 reserved */
2254         ushort reserved43;      /* 43 reserved */
2255         ushort reserved44;      /* 44 reserved */
2256         ushort reserved45;      /* 45 reserved */
2257         ushort reserved46;      /* 46 reserved */
2258         ushort reserved47;      /* 47 reserved */
2259         ushort reserved48;      /* 48 reserved */
2260         ushort reserved49;      /* 49 reserved */
2261         ushort reserved50;      /* 50 reserved */
2262         ushort reserved51;      /* 51 reserved */
2263         ushort reserved52;      /* 52 reserved */
2264         ushort reserved53;      /* 53 reserved */
2265         ushort reserved54;      /* 54 reserved */
2266         ushort reserved55;      /* 55 reserved */
2267         ushort cisptr_lsw;      /* 56 CIS PTR LSW */
2268         ushort cisprt_msw;      /* 57 CIS PTR MSW */
2269         ushort subsysvid;       /* 58 SubSystem Vendor ID */
2270         ushort subsysid;        /* 59 SubSystem ID */
2271         ushort reserved60;      /* 60 reserved */
2272         ushort reserved61;      /* 61 reserved */
2273         ushort reserved62;      /* 62 reserved */
2274         ushort reserved63;      /* 63 reserved */
2275 } ADVEEP_38C0800_CONFIG;
2276
2277 typedef struct adveep_38C1600_config {
2278         /* Word Offset, Description */
2279
2280         ushort cfg_lsw;         /* 00 power up initialization */
2281         /*  bit 11 set - Func. 0 INTB, Func. 1 INTA */
2282         /*       clear - Func. 0 INTA, Func. 1 INTB */
2283         /*  bit 13 set - Load CIS */
2284         /*  bit 14 set - BIOS Enable */
2285         /*  bit 15 set - Big Endian Mode */
2286         ushort cfg_msw;         /* 01 unused */
2287         ushort disc_enable;     /* 02 disconnect enable */
2288         ushort wdtr_able;       /* 03 Wide DTR able */
2289         ushort sdtr_speed1;     /* 04 SDTR Speed TID 0-3 */
2290         ushort start_motor;     /* 05 send start up motor */
2291         ushort tagqng_able;     /* 06 tag queuing able */
2292         ushort bios_scan;       /* 07 BIOS device control */
2293         ushort scam_tolerant;   /* 08 no scam */
2294
2295         uchar adapter_scsi_id;  /* 09 Host Adapter ID */
2296         uchar bios_boot_delay;  /*    power up wait */
2297
2298         uchar scsi_reset_delay; /* 10 reset delay */
2299         uchar bios_id_lun;      /*    first boot device scsi id & lun */
2300         /*    high nibble is lun */
2301         /*    low nibble is scsi id */
2302
2303         uchar termination_se;   /* 11 0 - automatic */
2304         /*    1 - low off / high off */
2305         /*    2 - low off / high on */
2306         /*    3 - low on  / high on */
2307         /*    There is no low on  / high off */
2308
2309         uchar termination_lvd;  /* 11 0 - automatic */
2310         /*    1 - low off / high off */
2311         /*    2 - low off / high on */
2312         /*    3 - low on  / high on */
2313         /*    There is no low on  / high off */
2314
2315         ushort bios_ctrl;       /* 12 BIOS control bits */
2316         /*  bit 0  BIOS don't act as initiator. */
2317         /*  bit 1  BIOS > 1 GB support */
2318         /*  bit 2  BIOS > 2 Disk Support */
2319         /*  bit 3  BIOS don't support removables */
2320         /*  bit 4  BIOS support bootable CD */
2321         /*  bit 5  BIOS scan enabled */
2322         /*  bit 6  BIOS support multiple LUNs */
2323         /*  bit 7  BIOS display of message */
2324         /*  bit 8  SCAM disabled */
2325         /*  bit 9  Reset SCSI bus during init. */
2326         /*  bit 10 Basic Integrity Checking disabled */
2327         /*  bit 11 No verbose initialization. */
2328         /*  bit 12 SCSI parity enabled */
2329         /*  bit 13 AIPP (Asyn. Info. Ph. Prot.) dis. */
2330         /*  bit 14 */
2331         /*  bit 15 */
2332         ushort sdtr_speed2;     /* 13 SDTR speed TID 4-7 */
2333         ushort sdtr_speed3;     /* 14 SDTR speed TID 8-11 */
2334         uchar max_host_qng;     /* 15 maximum host queueing */
2335         uchar max_dvc_qng;      /*    maximum per device queuing */
2336         ushort dvc_cntl;        /* 16 control bit for driver */
2337         ushort sdtr_speed4;     /* 17 SDTR speed 4 TID 12-15 */
2338         ushort serial_number_word1;     /* 18 Board serial number word 1 */
2339         ushort serial_number_word2;     /* 19 Board serial number word 2 */
2340         ushort serial_number_word3;     /* 20 Board serial number word 3 */
2341         ushort check_sum;       /* 21 EEP check sum */
2342         uchar oem_name[16];     /* 22 OEM name */
2343         ushort dvc_err_code;    /* 30 last device driver error code */
2344         ushort adv_err_code;    /* 31 last uc and Adv Lib error code */
2345         ushort adv_err_addr;    /* 32 last uc error address */
2346         ushort saved_dvc_err_code;      /* 33 saved last dev. driver error code   */
2347         ushort saved_adv_err_code;      /* 34 saved last uc and Adv Lib error code */
2348         ushort saved_adv_err_addr;      /* 35 saved last uc error address         */
2349         ushort reserved36;      /* 36 reserved */
2350         ushort reserved37;      /* 37 reserved */
2351         ushort reserved38;      /* 38 reserved */
2352         ushort reserved39;      /* 39 reserved */
2353         ushort reserved40;      /* 40 reserved */
2354         ushort reserved41;      /* 41 reserved */
2355         ushort reserved42;      /* 42 reserved */
2356         ushort reserved43;      /* 43 reserved */
2357         ushort reserved44;      /* 44 reserved */
2358         ushort reserved45;      /* 45 reserved */
2359         ushort reserved46;      /* 46 reserved */
2360         ushort reserved47;      /* 47 reserved */
2361         ushort reserved48;      /* 48 reserved */
2362         ushort reserved49;      /* 49 reserved */
2363         ushort reserved50;      /* 50 reserved */
2364         ushort reserved51;      /* 51 reserved */
2365         ushort reserved52;      /* 52 reserved */
2366         ushort reserved53;      /* 53 reserved */
2367         ushort reserved54;      /* 54 reserved */
2368         ushort reserved55;      /* 55 reserved */
2369         ushort cisptr_lsw;      /* 56 CIS PTR LSW */
2370         ushort cisprt_msw;      /* 57 CIS PTR MSW */
2371         ushort subsysvid;       /* 58 SubSystem Vendor ID */
2372         ushort subsysid;        /* 59 SubSystem ID */
2373         ushort reserved60;      /* 60 reserved */
2374         ushort reserved61;      /* 61 reserved */
2375         ushort reserved62;      /* 62 reserved */
2376         ushort reserved63;      /* 63 reserved */
2377 } ADVEEP_38C1600_CONFIG;
2378
2379 /*
2380  * EEPROM Commands
2381  */
2382 #define ASC_EEP_CMD_DONE             0x0200
2383 #define ASC_EEP_CMD_DONE_ERR         0x0001
2384
2385 /* cfg_word */
2386 #define EEP_CFG_WORD_BIG_ENDIAN      0x8000
2387
2388 /* bios_ctrl */
2389 #define BIOS_CTRL_BIOS               0x0001
2390 #define BIOS_CTRL_EXTENDED_XLAT      0x0002
2391 #define BIOS_CTRL_GT_2_DISK          0x0004
2392 #define BIOS_CTRL_BIOS_REMOVABLE     0x0008
2393 #define BIOS_CTRL_BOOTABLE_CD        0x0010
2394 #define BIOS_CTRL_MULTIPLE_LUN       0x0040
2395 #define BIOS_CTRL_DISPLAY_MSG        0x0080
2396 #define BIOS_CTRL_NO_SCAM            0x0100
2397 #define BIOS_CTRL_RESET_SCSI_BUS     0x0200
2398 #define BIOS_CTRL_INIT_VERBOSE       0x0800
2399 #define BIOS_CTRL_SCSI_PARITY        0x1000
2400 #define BIOS_CTRL_AIPP_DIS           0x2000
2401
2402 #define ADV_3550_MEMSIZE   0x2000       /* 8 KB Internal Memory */
2403 #define ADV_3550_IOLEN     0x40 /* I/O Port Range in bytes */
2404
2405 #define ADV_38C0800_MEMSIZE  0x4000     /* 16 KB Internal Memory */
2406 #define ADV_38C0800_IOLEN    0x100      /* I/O Port Range in bytes */
2407
2408 /*
2409  * XXX - Since ASC38C1600 Rev.3 has a local RAM failure issue, there is
2410  * a special 16K Adv Library and Microcode version. After the issue is
2411  * resolved, should restore 32K support.
2412  *
2413  * #define ADV_38C1600_MEMSIZE  0x8000L   * 32 KB Internal Memory *
2414  */
2415 #define ADV_38C1600_MEMSIZE  0x4000     /* 16 KB Internal Memory */
2416 #define ADV_38C1600_IOLEN    0x100      /* I/O Port Range 256 bytes */
2417 #define ADV_38C1600_MEMLEN   0x1000     /* Memory Range 4KB bytes */
2418
2419 /*
2420  * Byte I/O register address from base of 'iop_base'.
2421  */
2422 #define IOPB_INTR_STATUS_REG    0x00
2423 #define IOPB_CHIP_ID_1          0x01
2424 #define IOPB_INTR_ENABLES       0x02
2425 #define IOPB_CHIP_TYPE_REV      0x03
2426 #define IOPB_RES_ADDR_4         0x04
2427 #define IOPB_RES_ADDR_5         0x05
2428 #define IOPB_RAM_DATA           0x06
2429 #define IOPB_RES_ADDR_7         0x07
2430 #define IOPB_FLAG_REG           0x08
2431 #define IOPB_RES_ADDR_9         0x09
2432 #define IOPB_RISC_CSR           0x0A
2433 #define IOPB_RES_ADDR_B         0x0B
2434 #define IOPB_RES_ADDR_C         0x0C
2435 #define IOPB_RES_ADDR_D         0x0D
2436 #define IOPB_SOFT_OVER_WR       0x0E
2437 #define IOPB_RES_ADDR_F         0x0F
2438 #define IOPB_MEM_CFG            0x10
2439 #define IOPB_RES_ADDR_11        0x11
2440 #define IOPB_GPIO_DATA          0x12
2441 #define IOPB_RES_ADDR_13        0x13
2442 #define IOPB_FLASH_PAGE         0x14
2443 #define IOPB_RES_ADDR_15        0x15
2444 #define IOPB_GPIO_CNTL          0x16
2445 #define IOPB_RES_ADDR_17        0x17
2446 #define IOPB_FLASH_DATA         0x18
2447 #define IOPB_RES_ADDR_19        0x19
2448 #define IOPB_RES_ADDR_1A        0x1A
2449 #define IOPB_RES_ADDR_1B        0x1B
2450 #define IOPB_RES_ADDR_1C        0x1C
2451 #define IOPB_RES_ADDR_1D        0x1D
2452 #define IOPB_RES_ADDR_1E        0x1E
2453 #define IOPB_RES_ADDR_1F        0x1F
2454 #define IOPB_DMA_CFG0           0x20
2455 #define IOPB_DMA_CFG1           0x21
2456 #define IOPB_TICKLE             0x22
2457 #define IOPB_DMA_REG_WR         0x23
2458 #define IOPB_SDMA_STATUS        0x24
2459 #define IOPB_SCSI_BYTE_CNT      0x25
2460 #define IOPB_HOST_BYTE_CNT      0x26
2461 #define IOPB_BYTE_LEFT_TO_XFER  0x27
2462 #define IOPB_BYTE_TO_XFER_0     0x28
2463 #define IOPB_BYTE_TO_XFER_1     0x29
2464 #define IOPB_BYTE_TO_XFER_2     0x2A
2465 #define IOPB_BYTE_TO_XFER_3     0x2B
2466 #define IOPB_ACC_GRP            0x2C
2467 #define IOPB_RES_ADDR_2D        0x2D
2468 #define IOPB_DEV_ID             0x2E
2469 #define IOPB_RES_ADDR_2F        0x2F
2470 #define IOPB_SCSI_DATA          0x30
2471 #define IOPB_RES_ADDR_31        0x31
2472 #define IOPB_RES_ADDR_32        0x32
2473 #define IOPB_SCSI_DATA_HSHK     0x33
2474 #define IOPB_SCSI_CTRL          0x34
2475 #define IOPB_RES_ADDR_35        0x35
2476 #define IOPB_RES_ADDR_36        0x36
2477 #define IOPB_RES_ADDR_37        0x37
2478 #define IOPB_RAM_BIST           0x38
2479 #define IOPB_PLL_TEST           0x39
2480 #define IOPB_PCI_INT_CFG        0x3A
2481 #define IOPB_RES_ADDR_3B        0x3B
2482 #define IOPB_RFIFO_CNT          0x3C
2483 #define IOPB_RES_ADDR_3D        0x3D
2484 #define IOPB_RES_ADDR_3E        0x3E
2485 #define IOPB_RES_ADDR_3F        0x3F
2486
2487 /*
2488  * Word I/O register address from base of 'iop_base'.
2489  */
2490 #define IOPW_CHIP_ID_0          0x00    /* CID0  */
2491 #define IOPW_CTRL_REG           0x02    /* CC    */
2492 #define IOPW_RAM_ADDR           0x04    /* LA    */
2493 #define IOPW_RAM_DATA           0x06    /* LD    */
2494 #define IOPW_RES_ADDR_08        0x08
2495 #define IOPW_RISC_CSR           0x0A    /* CSR   */
2496 #define IOPW_SCSI_CFG0          0x0C    /* CFG0  */
2497 #define IOPW_SCSI_CFG1          0x0E    /* CFG1  */
2498 #define IOPW_RES_ADDR_10        0x10
2499 #define IOPW_SEL_MASK           0x12    /* SM    */
2500 #define IOPW_RES_ADDR_14        0x14
2501 #define IOPW_FLASH_ADDR         0x16    /* FA    */
2502 #define IOPW_RES_ADDR_18        0x18
2503 #define IOPW_EE_CMD             0x1A    /* EC    */
2504 #define IOPW_EE_DATA            0x1C    /* ED    */
2505 #define IOPW_SFIFO_CNT          0x1E    /* SFC   */
2506 #define IOPW_RES_ADDR_20        0x20
2507 #define IOPW_Q_BASE             0x22    /* QB    */
2508 #define IOPW_QP                 0x24    /* QP    */
2509 #define IOPW_IX                 0x26    /* IX    */
2510 #define IOPW_SP                 0x28    /* SP    */
2511 #define IOPW_PC                 0x2A    /* PC    */
2512 #define IOPW_RES_ADDR_2C        0x2C
2513 #define IOPW_RES_ADDR_2E        0x2E
2514 #define IOPW_SCSI_DATA          0x30    /* SD    */
2515 #define IOPW_SCSI_DATA_HSHK     0x32    /* SDH   */
2516 #define IOPW_SCSI_CTRL          0x34    /* SC    */
2517 #define IOPW_HSHK_CFG           0x36    /* HCFG  */
2518 #define IOPW_SXFR_STATUS        0x36    /* SXS   */
2519 #define IOPW_SXFR_CNTL          0x38    /* SXL   */
2520 #define IOPW_SXFR_CNTH          0x3A    /* SXH   */
2521 #define IOPW_RES_ADDR_3C        0x3C
2522 #define IOPW_RFIFO_DATA         0x3E    /* RFD   */
2523
2524 /*
2525  * Doubleword I/O register address from base of 'iop_base'.
2526  */
2527 #define IOPDW_RES_ADDR_0         0x00
2528 #define IOPDW_RAM_DATA           0x04
2529 #define IOPDW_RES_ADDR_8         0x08
2530 #define IOPDW_RES_ADDR_C         0x0C
2531 #define IOPDW_RES_ADDR_10        0x10
2532 #define IOPDW_COMMA              0x14
2533 #define IOPDW_COMMB              0x18
2534 #define IOPDW_RES_ADDR_1C        0x1C
2535 #define IOPDW_SDMA_ADDR0         0x20
2536 #define IOPDW_SDMA_ADDR1         0x24
2537 #define IOPDW_SDMA_COUNT         0x28
2538 #define IOPDW_SDMA_ERROR         0x2C
2539 #define IOPDW_RDMA_ADDR0         0x30
2540 #define IOPDW_RDMA_ADDR1         0x34
2541 #define IOPDW_RDMA_COUNT         0x38
2542 #define IOPDW_RDMA_ERROR         0x3C
2543
2544 #define ADV_CHIP_ID_BYTE         0x25
2545 #define ADV_CHIP_ID_WORD         0x04C1
2546
2547 #define ADV_SC_SCSI_BUS_RESET    0x2000
2548
2549 #define ADV_INTR_ENABLE_HOST_INTR                   0x01
2550 #define ADV_INTR_ENABLE_SEL_INTR                    0x02
2551 #define ADV_INTR_ENABLE_DPR_INTR                    0x04
2552 #define ADV_INTR_ENABLE_RTA_INTR                    0x08
2553 #define ADV_INTR_ENABLE_RMA_INTR                    0x10
2554 #define ADV_INTR_ENABLE_RST_INTR                    0x20
2555 #define ADV_INTR_ENABLE_DPE_INTR                    0x40
2556 #define ADV_INTR_ENABLE_GLOBAL_INTR                 0x80
2557
2558 #define ADV_INTR_STATUS_INTRA            0x01
2559 #define ADV_INTR_STATUS_INTRB            0x02
2560 #define ADV_INTR_STATUS_INTRC            0x04
2561
2562 #define ADV_RISC_CSR_STOP           (0x0000)
2563 #define ADV_RISC_TEST_COND          (0x2000)
2564 #define ADV_RISC_CSR_RUN            (0x4000)
2565 #define ADV_RISC_CSR_SINGLE_STEP    (0x8000)
2566
2567 #define ADV_CTRL_REG_HOST_INTR      0x0100
2568 #define ADV_CTRL_REG_SEL_INTR       0x0200
2569 #define ADV_CTRL_REG_DPR_INTR       0x0400
2570 #define ADV_CTRL_REG_RTA_INTR       0x0800
2571 #define ADV_CTRL_REG_RMA_INTR       0x1000
2572 #define ADV_CTRL_REG_RES_BIT14      0x2000
2573 #define ADV_CTRL_REG_DPE_INTR       0x4000
2574 #define ADV_CTRL_REG_POWER_DONE     0x8000
2575 #define ADV_CTRL_REG_ANY_INTR       0xFF00
2576
2577 #define ADV_CTRL_REG_CMD_RESET             0x00C6
2578 #define ADV_CTRL_REG_CMD_WR_IO_REG         0x00C5
2579 #define ADV_CTRL_REG_CMD_RD_IO_REG         0x00C4
2580 #define ADV_CTRL_REG_CMD_WR_PCI_CFG_SPACE  0x00C3
2581 #define ADV_CTRL_REG_CMD_RD_PCI_CFG_SPACE  0x00C2
2582
2583 #define ADV_TICKLE_NOP                      0x00
2584 #define ADV_TICKLE_A                        0x01
2585 #define ADV_TICKLE_B                        0x02
2586 #define ADV_TICKLE_C                        0x03
2587
2588 #define ADV_SCSI_CTRL_RSTOUT        0x2000
2589
2590 #define AdvIsIntPending(port) \
2591     (AdvReadWordRegister(port, IOPW_CTRL_REG) & ADV_CTRL_REG_HOST_INTR)
2592
2593 /*
2594  * SCSI_CFG0 Register bit definitions
2595  */
2596 #define TIMER_MODEAB    0xC000  /* Watchdog, Second, and Select. Timer Ctrl. */
2597 #define PARITY_EN       0x2000  /* Enable SCSI Parity Error detection */
2598 #define EVEN_PARITY     0x1000  /* Select Even Parity */
2599 #define WD_LONG         0x0800  /* Watchdog Interval, 1: 57 min, 0: 13 sec */
2600 #define QUEUE_128       0x0400  /* Queue Size, 1: 128 byte, 0: 64 byte */
2601 #define PRIM_MODE       0x0100  /* Primitive SCSI mode */
2602 #define SCAM_EN         0x0080  /* Enable SCAM selection */
2603 #define SEL_TMO_LONG    0x0040  /* Sel/Resel Timeout, 1: 400 ms, 0: 1.6 ms */
2604 #define CFRM_ID         0x0020  /* SCAM id sel. confirm., 1: fast, 0: 6.4 ms */
2605 #define OUR_ID_EN       0x0010  /* Enable OUR_ID bits */
2606 #define OUR_ID          0x000F  /* SCSI ID */
2607
2608 /*
2609  * SCSI_CFG1 Register bit definitions
2610  */
2611 #define BIG_ENDIAN      0x8000  /* Enable Big Endian Mode MIO:15, EEP:15 */
2612 #define TERM_POL        0x2000  /* Terminator Polarity Ctrl. MIO:13, EEP:13 */
2613 #define SLEW_RATE       0x1000  /* SCSI output buffer slew rate */
2614 #define FILTER_SEL      0x0C00  /* Filter Period Selection */
2615 #define  FLTR_DISABLE    0x0000 /* Input Filtering Disabled */
2616 #define  FLTR_11_TO_20NS 0x0800 /* Input Filtering 11ns to 20ns */
2617 #define  FLTR_21_TO_39NS 0x0C00 /* Input Filtering 21ns to 39ns */
2618 #define ACTIVE_DBL      0x0200  /* Disable Active Negation */
2619 #define DIFF_MODE       0x0100  /* SCSI differential Mode (Read-Only) */
2620 #define DIFF_SENSE      0x0080  /* 1: No SE cables, 0: SE cable (Read-Only) */
2621 #define TERM_CTL_SEL    0x0040  /* Enable TERM_CTL_H and TERM_CTL_L */
2622 #define TERM_CTL        0x0030  /* External SCSI Termination Bits */
2623 #define  TERM_CTL_H      0x0020 /* Enable External SCSI Upper Termination */
2624 #define  TERM_CTL_L      0x0010 /* Enable External SCSI Lower Termination */
2625 #define CABLE_DETECT    0x000F  /* External SCSI Cable Connection Status */
2626
2627 /*
2628  * Addendum for ASC-38C0800 Chip
2629  *
2630  * The ASC-38C1600 Chip uses the same definitions except that the
2631  * bus mode override bits [12:10] have been moved to byte register
2632  * offset 0xE (IOPB_SOFT_OVER_WR) bits [12:10]. The [12:10] bits in
2633  * SCSI_CFG1 are read-only and always available. Bit 14 (DIS_TERM_DRV)
2634  * is not needed. The [12:10] bits in IOPB_SOFT_OVER_WR are write-only.
2635  * Also each ASC-38C1600 function or channel uses only cable bits [5:4]
2636  * and [1:0]. Bits [14], [7:6], [3:2] are unused.
2637  */
2638 #define DIS_TERM_DRV    0x4000  /* 1: Read c_det[3:0], 0: cannot read */
2639 #define HVD_LVD_SE      0x1C00  /* Device Detect Bits */
2640 #define  HVD             0x1000 /* HVD Device Detect */
2641 #define  LVD             0x0800 /* LVD Device Detect */
2642 #define  SE              0x0400 /* SE Device Detect */
2643 #define TERM_LVD        0x00C0  /* LVD Termination Bits */
2644 #define  TERM_LVD_HI     0x0080 /* Enable LVD Upper Termination */
2645 #define  TERM_LVD_LO     0x0040 /* Enable LVD Lower Termination */
2646 #define TERM_SE         0x0030  /* SE Termination Bits */
2647 #define  TERM_SE_HI      0x0020 /* Enable SE Upper Termination */
2648 #define  TERM_SE_LO      0x0010 /* Enable SE Lower Termination */
2649 #define C_DET_LVD       0x000C  /* LVD Cable Detect Bits */
2650 #define  C_DET3          0x0008 /* Cable Detect for LVD External Wide */
2651 #define  C_DET2          0x0004 /* Cable Detect for LVD Internal Wide */
2652 #define C_DET_SE        0x0003  /* SE Cable Detect Bits */
2653 #define  C_DET1          0x0002 /* Cable Detect for SE Internal Wide */
2654 #define  C_DET0          0x0001 /* Cable Detect for SE Internal Narrow */
2655
2656 #define CABLE_ILLEGAL_A 0x7
2657     /* x 0 0 0  | on  on | Illegal (all 3 connectors are used) */
2658
2659 #define CABLE_ILLEGAL_B 0xB
2660     /* 0 x 0 0  | on  on | Illegal (all 3 connectors are used) */
2661
2662 /*
2663  * MEM_CFG Register bit definitions
2664  */
2665 #define BIOS_EN         0x40    /* BIOS Enable MIO:14,EEP:14 */
2666 #define FAST_EE_CLK     0x20    /* Diagnostic Bit */
2667 #define RAM_SZ          0x1C    /* Specify size of RAM to RISC */
2668 #define  RAM_SZ_2KB      0x00   /* 2 KB */
2669 #define  RAM_SZ_4KB      0x04   /* 4 KB */
2670 #define  RAM_SZ_8KB      0x08   /* 8 KB */
2671 #define  RAM_SZ_16KB     0x0C   /* 16 KB */
2672 #define  RAM_SZ_32KB     0x10   /* 32 KB */
2673 #define  RAM_SZ_64KB     0x14   /* 64 KB */
2674
2675 /*
2676  * DMA_CFG0 Register bit definitions
2677  *
2678  * This register is only accessible to the host.
2679  */
2680 #define BC_THRESH_ENB   0x80    /* PCI DMA Start Conditions */
2681 #define FIFO_THRESH     0x70    /* PCI DMA FIFO Threshold */
2682 #define  FIFO_THRESH_16B  0x00  /* 16 bytes */
2683 #define  FIFO_THRESH_32B  0x20  /* 32 bytes */
2684 #define  FIFO_THRESH_48B  0x30  /* 48 bytes */
2685 #define  FIFO_THRESH_64B  0x40  /* 64 bytes */
2686 #define  FIFO_THRESH_80B  0x50  /* 80 bytes (default) */
2687 #define  FIFO_THRESH_96B  0x60  /* 96 bytes */
2688 #define  FIFO_THRESH_112B 0x70  /* 112 bytes */
2689 #define START_CTL       0x0C    /* DMA start conditions */
2690 #define  START_CTL_TH    0x00   /* Wait threshold level (default) */
2691 #define  START_CTL_ID    0x04   /* Wait SDMA/SBUS idle */
2692 #define  START_CTL_THID  0x08   /* Wait threshold and SDMA/SBUS idle */
2693 #define  START_CTL_EMFU  0x0C   /* Wait SDMA FIFO empty/full */
2694 #define READ_CMD        0x03    /* Memory Read Method */
2695 #define  READ_CMD_MR     0x00   /* Memory Read */
2696 #define  READ_CMD_MRL    0x02   /* Memory Read Long */
2697 #define  READ_CMD_MRM    0x03   /* Memory Read Multiple (default) */
2698
2699 /*
2700  * ASC-38C0800 RAM BIST Register bit definitions
2701  */
2702 #define RAM_TEST_MODE         0x80
2703 #define PRE_TEST_MODE         0x40
2704 #define NORMAL_MODE           0x00
2705 #define RAM_TEST_DONE         0x10
2706 #define RAM_TEST_STATUS       0x0F
2707 #define  RAM_TEST_HOST_ERROR   0x08
2708 #define  RAM_TEST_INTRAM_ERROR 0x04
2709 #define  RAM_TEST_RISC_ERROR   0x02
2710 #define  RAM_TEST_SCSI_ERROR   0x01
2711 #define  RAM_TEST_SUCCESS      0x00
2712 #define PRE_TEST_VALUE        0x05
2713 #define NORMAL_VALUE          0x00
2714
2715 /*
2716  * ASC38C1600 Definitions
2717  *
2718  * IOPB_PCI_INT_CFG Bit Field Definitions
2719  */
2720
2721 #define INTAB_LD        0x80    /* Value loaded from EEPROM Bit 11. */
2722
2723 /*
2724  * Bit 1 can be set to change the interrupt for the Function to operate in
2725  * Totem Pole mode. By default Bit 1 is 0 and the interrupt operates in
2726  * Open Drain mode. Both functions of the ASC38C1600 must be set to the same
2727  * mode, otherwise the operating mode is undefined.
2728  */
2729 #define TOTEMPOLE       0x02
2730
2731 /*
2732  * Bit 0 can be used to change the Int Pin for the Function. The value is
2733  * 0 by default for both Functions with Function 0 using INT A and Function
2734  * B using INT B. For Function 0 if set, INT B is used. For Function 1 if set,
2735  * INT A is used.
2736  *
2737  * EEPROM Word 0 Bit 11 for each Function may change the initial Int Pin
2738  * value specified in the PCI Configuration Space.
2739  */
2740 #define INTAB           0x01
2741
2742 /* a_advlib.h */
2743
2744 /*
2745  * Adv Library Status Definitions
2746  */
2747 #define ADV_TRUE        1
2748 #define ADV_FALSE       0
2749 #define ADV_NOERROR     1
2750 #define ADV_SUCCESS     1
2751 #define ADV_BUSY        0
2752 #define ADV_ERROR       (-1)
2753
2754 /*
2755  * ADV_DVC_VAR 'warn_code' values
2756  */
2757 #define ASC_WARN_BUSRESET_ERROR         0x0001  /* SCSI Bus Reset error */
2758 #define ASC_WARN_EEPROM_CHKSUM          0x0002  /* EEP check sum error */
2759 #define ASC_WARN_EEPROM_TERMINATION     0x0004  /* EEP termination bad field */
2760 #define ASC_WARN_SET_PCI_CONFIG_SPACE   0x0080  /* PCI config space set error */
2761 #define ASC_WARN_ERROR                  0xFFFF  /* ADV_ERROR return */
2762
2763 #define ADV_MAX_TID                     15      /* max. target identifier */
2764 #define ADV_MAX_LUN                     7       /* max. logical unit number */
2765
2766 /*
2767  * Error code values are set in ADV_DVC_VAR 'err_code'.
2768  */
2769 #define ASC_IERR_WRITE_EEPROM       0x0001      /* write EEPROM error */
2770 #define ASC_IERR_MCODE_CHKSUM       0x0002      /* micro code check sum error */
2771 #define ASC_IERR_NO_CARRIER         0x0004      /* No more carrier memory. */
2772 #define ASC_IERR_START_STOP_CHIP    0x0008      /* start/stop chip failed */
2773 #define ASC_IERR_CHIP_VERSION       0x0040      /* wrong chip version */
2774 #define ASC_IERR_SET_SCSI_ID        0x0080      /* set SCSI ID failed */
2775 #define ASC_IERR_HVD_DEVICE         0x0100      /* HVD attached to LVD connector. */
2776 #define ASC_IERR_BAD_SIGNATURE      0x0200      /* signature not found */
2777 #define ASC_IERR_ILLEGAL_CONNECTION 0x0400      /* Illegal cable connection */
2778 #define ASC_IERR_SINGLE_END_DEVICE  0x0800      /* Single-end used w/differential */
2779 #define ASC_IERR_REVERSED_CABLE     0x1000      /* Narrow flat cable reversed */
2780 #define ASC_IERR_BIST_PRE_TEST      0x2000      /* BIST pre-test error */
2781 #define ASC_IERR_BIST_RAM_TEST      0x4000      /* BIST RAM test error */
2782 #define ASC_IERR_BAD_CHIPTYPE       0x8000      /* Invalid 'chip_type' setting. */
2783
2784 /*
2785  * Fixed locations of microcode operating variables.
2786  */
2787 #define ASC_MC_CODE_BEGIN_ADDR          0x0028  /* microcode start address */
2788 #define ASC_MC_CODE_END_ADDR            0x002A  /* microcode end address */
2789 #define ASC_MC_CODE_CHK_SUM             0x002C  /* microcode code checksum */
2790 #define ASC_MC_VERSION_DATE             0x0038  /* microcode version */
2791 #define ASC_MC_VERSION_NUM              0x003A  /* microcode number */
2792 #define ASC_MC_BIOSMEM                  0x0040  /* BIOS RISC Memory Start */
2793 #define ASC_MC_BIOSLEN                  0x0050  /* BIOS RISC Memory Length */
2794 #define ASC_MC_BIOS_SIGNATURE           0x0058  /* BIOS Signature 0x55AA */
2795 #define ASC_MC_BIOS_VERSION             0x005A  /* BIOS Version (2 bytes) */
2796 #define ASC_MC_SDTR_SPEED1              0x0090  /* SDTR Speed for TID 0-3 */
2797 #define ASC_MC_SDTR_SPEED2              0x0092  /* SDTR Speed for TID 4-7 */
2798 #define ASC_MC_SDTR_SPEED3              0x0094  /* SDTR Speed for TID 8-11 */
2799 #define ASC_MC_SDTR_SPEED4              0x0096  /* SDTR Speed for TID 12-15 */
2800 #define ASC_MC_CHIP_TYPE                0x009A
2801 #define ASC_MC_INTRB_CODE               0x009B
2802 #define ASC_MC_WDTR_ABLE                0x009C
2803 #define ASC_MC_SDTR_ABLE                0x009E
2804 #define ASC_MC_TAGQNG_ABLE              0x00A0
2805 #define ASC_MC_DISC_ENABLE              0x00A2
2806 #define ASC_MC_IDLE_CMD_STATUS          0x00A4
2807 #define ASC_MC_IDLE_CMD                 0x00A6
2808 #define ASC_MC_IDLE_CMD_PARAMETER       0x00A8
2809 #define ASC_MC_DEFAULT_SCSI_CFG0        0x00AC
2810 #define ASC_MC_DEFAULT_SCSI_CFG1        0x00AE
2811 #define ASC_MC_DEFAULT_MEM_CFG          0x00B0
2812 #define ASC_MC_DEFAULT_SEL_MASK         0x00B2
2813 #define ASC_MC_SDTR_DONE                0x00B6
2814 #define ASC_MC_NUMBER_OF_QUEUED_CMD     0x00C0
2815 #define ASC_MC_NUMBER_OF_MAX_CMD        0x00D0
2816 #define ASC_MC_DEVICE_HSHK_CFG_TABLE    0x0100
2817 #define ASC_MC_CONTROL_FLAG             0x0122  /* Microcode control flag. */
2818 #define ASC_MC_WDTR_DONE                0x0124
2819 #define ASC_MC_CAM_MODE_MASK            0x015E  /* CAM mode TID bitmask. */
2820 #define ASC_MC_ICQ                      0x0160
2821 #define ASC_MC_IRQ                      0x0164
2822 #define ASC_MC_PPR_ABLE                 0x017A
2823
2824 /*
2825  * BIOS LRAM variable absolute offsets.
2826  */
2827 #define BIOS_CODESEG    0x54
2828 #define BIOS_CODELEN    0x56
2829 #define BIOS_SIGNATURE  0x58
2830 #define BIOS_VERSION    0x5A
2831
2832 /*
2833  * Microcode Control Flags
2834  *
2835  * Flags set by the Adv Library in RISC variable 'control_flag' (0x122)
2836  * and handled by the microcode.
2837  */
2838 #define CONTROL_FLAG_IGNORE_PERR        0x0001  /* Ignore DMA Parity Errors */
2839 #define CONTROL_FLAG_ENABLE_AIPP        0x0002  /* Enabled AIPP checking. */
2840
2841 /*
2842  * ASC_MC_DEVICE_HSHK_CFG_TABLE microcode table or HSHK_CFG register format
2843  */
2844 #define HSHK_CFG_WIDE_XFR       0x8000
2845 #define HSHK_CFG_RATE           0x0F00
2846 #define HSHK_CFG_OFFSET         0x001F
2847
2848 #define ASC_DEF_MAX_HOST_QNG    0xFD    /* Max. number of host commands (253) */
2849 #define ASC_DEF_MIN_HOST_QNG    0x10    /* Min. number of host commands (16) */
2850 #define ASC_DEF_MAX_DVC_QNG     0x3F    /* Max. number commands per device (63) */
2851 #define ASC_DEF_MIN_DVC_QNG     0x04    /* Min. number commands per device (4) */
2852
2853 #define ASC_QC_DATA_CHECK  0x01 /* Require ASC_QC_DATA_OUT set or clear. */
2854 #define ASC_QC_DATA_OUT    0x02 /* Data out DMA transfer. */
2855 #define ASC_QC_START_MOTOR 0x04 /* Send auto-start motor before request. */
2856 #define ASC_QC_NO_OVERRUN  0x08 /* Don't report overrun. */
2857 #define ASC_QC_FREEZE_TIDQ 0x10 /* Freeze TID queue after request. XXX TBD */
2858
2859 #define ASC_QSC_NO_DISC     0x01        /* Don't allow disconnect for request. */
2860 #define ASC_QSC_NO_TAGMSG   0x02        /* Don't allow tag queuing for request. */
2861 #define ASC_QSC_NO_SYNC     0x04        /* Don't use Synch. transfer on request. */
2862 #define ASC_QSC_NO_WIDE     0x08        /* Don't use Wide transfer on request. */
2863 #define ASC_QSC_REDO_DTR    0x10        /* Renegotiate WDTR/SDTR before request. */
2864 /*
2865  * Note: If a Tag Message is to be sent and neither ASC_QSC_HEAD_TAG or
2866  * ASC_QSC_ORDERED_TAG is set, then a Simple Tag Message (0x20) is used.
2867  */
2868 #define ASC_QSC_HEAD_TAG    0x40        /* Use Head Tag Message (0x21). */
2869 #define ASC_QSC_ORDERED_TAG 0x80        /* Use Ordered Tag Message (0x22). */
2870
2871 /*
2872  * All fields here are accessed by the board microcode and need to be
2873  * little-endian.
2874  */
2875 typedef struct adv_carr_t {
2876         ADV_VADDR carr_va;      /* Carrier Virtual Address */
2877         ADV_PADDR carr_pa;      /* Carrier Physical Address */
2878         ADV_VADDR areq_vpa;     /* ASC_SCSI_REQ_Q Virtual or Physical Address */
2879         /*
2880          * next_vpa [31:4]            Carrier Virtual or Physical Next Pointer
2881          *
2882          * next_vpa [3:1]             Reserved Bits
2883          * next_vpa [0]               Done Flag set in Response Queue.
2884          */
2885         ADV_VADDR next_vpa;
2886 } ADV_CARR_T;
2887
2888 /*
2889  * Mask used to eliminate low 4 bits of carrier 'next_vpa' field.
2890  */
2891 #define ASC_NEXT_VPA_MASK       0xFFFFFFF0
2892
2893 #define ASC_RQ_DONE             0x00000001
2894 #define ASC_RQ_GOOD             0x00000002
2895 #define ASC_CQ_STOPPER          0x00000000
2896
2897 #define ASC_GET_CARRP(carrp) ((carrp) & ASC_NEXT_VPA_MASK)
2898
2899 #define ADV_CARRIER_NUM_PAGE_CROSSING \
2900     (((ADV_CARRIER_COUNT * sizeof(ADV_CARR_T)) + \
2901         (ADV_PAGE_SIZE - 1))/ADV_PAGE_SIZE)
2902
2903 #define ADV_CARRIER_BUFSIZE \
2904     ((ADV_CARRIER_COUNT + ADV_CARRIER_NUM_PAGE_CROSSING) * sizeof(ADV_CARR_T))
2905
2906 /*
2907  * ASC_SCSI_REQ_Q 'a_flag' definitions
2908  *
2909  * The Adv Library should limit use to the lower nibble (4 bits) of
2910  * a_flag. Drivers are free to use the upper nibble (4 bits) of a_flag.
2911  */
2912 #define ADV_POLL_REQUEST                0x01    /* poll for request completion */
2913 #define ADV_SCSIQ_DONE                  0x02    /* request done */
2914 #define ADV_DONT_RETRY                  0x08    /* don't do retry */
2915
2916 #define ADV_CHIP_ASC3550          0x01  /* Ultra-Wide IC */
2917 #define ADV_CHIP_ASC38C0800       0x02  /* Ultra2-Wide/LVD IC */
2918 #define ADV_CHIP_ASC38C1600       0x03  /* Ultra3-Wide/LVD2 IC */
2919
2920 /*
2921  * Adapter temporary configuration structure
2922  *
2923  * This structure can be discarded after initialization. Don't add
2924  * fields here needed after initialization.
2925  *
2926  * Field naming convention:
2927  *
2928  *  *_enable indicates the field enables or disables a feature. The
2929  *  value of the field is never reset.
2930  */
2931 typedef struct adv_dvc_cfg {
2932         ushort disc_enable;     /* enable disconnection */
2933         uchar chip_version;     /* chip version */
2934         uchar termination;      /* Term. Ctrl. bits 6-5 of SCSI_CFG1 register */
2935         ushort lib_version;     /* Adv Library version number */
2936         ushort control_flag;    /* Microcode Control Flag */
2937         ushort mcode_date;      /* Microcode date */
2938         ushort mcode_version;   /* Microcode version */
2939         ushort pci_slot_info;   /* high byte device/function number */
2940         /* bits 7-3 device num., bits 2-0 function num. */
2941         /* low byte bus num. */
2942         ushort serial1;         /* EEPROM serial number word 1 */
2943         ushort serial2;         /* EEPROM serial number word 2 */
2944         ushort serial3;         /* EEPROM serial number word 3 */
2945         struct device *dev;     /* pointer to the pci dev structure for this board */
2946 } ADV_DVC_CFG;
2947
2948 struct adv_dvc_var;
2949 struct adv_scsi_req_q;
2950
2951 typedef void (*ADV_ISR_CALLBACK)
2952  (struct adv_dvc_var *, struct adv_scsi_req_q *);
2953
2954 typedef void (*ADV_ASYNC_CALLBACK)
2955  (struct adv_dvc_var *, uchar);
2956
2957 /*
2958  * Adapter operation variable structure.
2959  *
2960  * One structure is required per host adapter.
2961  *
2962  * Field naming convention:
2963  *
2964  *  *_able indicates both whether a feature should be enabled or disabled
2965  *  and whether a device isi capable of the feature. At initialization
2966  *  this field may be set, but later if a device is found to be incapable
2967  *  of the feature, the field is cleared.
2968  */
2969 typedef struct adv_dvc_var {
2970         AdvPortAddr iop_base;   /* I/O port address */
2971         ushort err_code;        /* fatal error code */
2972         ushort bios_ctrl;       /* BIOS control word, EEPROM word 12 */
2973         ADV_ISR_CALLBACK isr_callback;
2974         ADV_ASYNC_CALLBACK async_callback;
2975         ushort wdtr_able;       /* try WDTR for a device */
2976         ushort sdtr_able;       /* try SDTR for a device */
2977         ushort ultra_able;      /* try SDTR Ultra speed for a device */
2978         ushort sdtr_speed1;     /* EEPROM SDTR Speed for TID 0-3   */
2979         ushort sdtr_speed2;     /* EEPROM SDTR Speed for TID 4-7   */
2980         ushort sdtr_speed3;     /* EEPROM SDTR Speed for TID 8-11  */
2981         ushort sdtr_speed4;     /* EEPROM SDTR Speed for TID 12-15 */
2982         ushort tagqng_able;     /* try tagged queuing with a device */
2983         ushort ppr_able;        /* PPR message capable per TID bitmask. */
2984         uchar max_dvc_qng;      /* maximum number of tagged commands per device */
2985         ushort start_motor;     /* start motor command allowed */
2986         uchar scsi_reset_wait;  /* delay in seconds after scsi bus reset */
2987         uchar chip_no;          /* should be assigned by caller */
2988         uchar max_host_qng;     /* maximum number of Q'ed command allowed */
2989         uchar irq_no;           /* IRQ number */
2990         ushort no_scam;         /* scam_tolerant of EEPROM */
2991         struct asc_board *drv_ptr;      /* driver pointer to private structure */
2992         uchar chip_scsi_id;     /* chip SCSI target ID */
2993         uchar chip_type;
2994         uchar bist_err_code;
2995         ADV_CARR_T *carrier_buf;
2996         ADV_CARR_T *carr_freelist;      /* Carrier free list. */
2997         ADV_CARR_T *icq_sp;     /* Initiator command queue stopper pointer. */
2998         ADV_CARR_T *irq_sp;     /* Initiator response queue stopper pointer. */
2999         ushort carr_pending_cnt;        /* Count of pending carriers. */
3000         /*
3001          * Note: The following fields will not be used after initialization. The
3002          * driver may discard the buffer after initialization is done.
3003          */
3004         ADV_DVC_CFG *cfg;       /* temporary configuration structure  */
3005 } ADV_DVC_VAR;
3006
3007 #define NO_OF_SG_PER_BLOCK              15
3008
3009 typedef struct asc_sg_block {
3010         uchar reserved1;
3011         uchar reserved2;
3012         uchar reserved3;
3013         uchar sg_cnt;           /* Valid entries in block. */
3014         ADV_PADDR sg_ptr;       /* Pointer to next sg block. */
3015         struct {
3016                 ADV_PADDR sg_addr;      /* SG element address. */
3017                 ADV_DCNT sg_count;      /* SG element count. */
3018         } sg_list[NO_OF_SG_PER_BLOCK];
3019 } ADV_SG_BLOCK;
3020
3021 /*
3022  * ADV_SCSI_REQ_Q - microcode request structure
3023  *
3024  * All fields in this structure up to byte 60 are used by the microcode.
3025  * The microcode makes assumptions about the size and ordering of fields
3026  * in this structure. Do not change the structure definition here without
3027  * coordinating the change with the microcode.
3028  *
3029  * All fields accessed by microcode must be maintained in little_endian
3030  * order.
3031  */
3032 typedef struct adv_scsi_req_q {
3033         uchar cntl;             /* Ucode flags and state (ASC_MC_QC_*). */
3034         uchar target_cmd;
3035         uchar target_id;        /* Device target identifier. */
3036         uchar target_lun;       /* Device target logical unit number. */
3037         ADV_PADDR data_addr;    /* Data buffer physical address. */
3038         ADV_DCNT data_cnt;      /* Data count. Ucode sets to residual. */
3039         ADV_PADDR sense_addr;
3040         ADV_PADDR carr_pa;
3041         uchar mflag;
3042         uchar sense_len;
3043         uchar cdb_len;          /* SCSI CDB length. Must <= 16 bytes. */
3044         uchar scsi_cntl;
3045         uchar done_status;      /* Completion status. */
3046         uchar scsi_status;      /* SCSI status byte. */
3047         uchar host_status;      /* Ucode host status. */
3048         uchar sg_working_ix;
3049         uchar cdb[12];          /* SCSI CDB bytes 0-11. */
3050         ADV_PADDR sg_real_addr; /* SG list physical address. */
3051         ADV_PADDR scsiq_rptr;
3052         uchar cdb16[4];         /* SCSI CDB bytes 12-15. */
3053         ADV_VADDR scsiq_ptr;
3054         ADV_VADDR carr_va;
3055         /*
3056          * End of microcode structure - 60 bytes. The rest of the structure
3057          * is used by the Adv Library and ignored by the microcode.
3058          */
3059         ADV_VADDR srb_ptr;
3060         ADV_SG_BLOCK *sg_list_ptr;      /* SG list virtual address. */
3061         char *vdata_addr;       /* Data buffer virtual address. */
3062         uchar a_flag;
3063         uchar pad[2];           /* Pad out to a word boundary. */
3064 } ADV_SCSI_REQ_Q;
3065
3066 /*
3067  * Microcode idle loop commands
3068  */
3069 #define IDLE_CMD_COMPLETED           0
3070 #define IDLE_CMD_STOP_CHIP           0x0001
3071 #define IDLE_CMD_STOP_CHIP_SEND_INT  0x0002
3072 #define IDLE_CMD_SEND_INT            0x0004
3073 #define IDLE_CMD_ABORT               0x0008
3074 #define IDLE_CMD_DEVICE_RESET        0x0010
3075 #define IDLE_CMD_SCSI_RESET_START    0x0020     /* Assert SCSI Bus Reset */
3076 #define IDLE_CMD_SCSI_RESET_END      0x0040     /* Deassert SCSI Bus Reset */
3077 #define IDLE_CMD_SCSIREQ             0x0080
3078
3079 #define IDLE_CMD_STATUS_SUCCESS      0x0001
3080 #define IDLE_CMD_STATUS_FAILURE      0x0002
3081
3082 /*
3083  * AdvSendIdleCmd() flag definitions.
3084  */
3085 #define ADV_NOWAIT     0x01
3086
3087 /*
3088  * Wait loop time out values.
3089  */
3090 #define SCSI_WAIT_10_SEC             10UL       /* 10 seconds */
3091 #define SCSI_WAIT_100_MSEC           100UL      /* 100 milliseconds */
3092 #define SCSI_US_PER_MSEC             1000       /* microseconds per millisecond */
3093 #define SCSI_MS_PER_SEC              1000UL     /* milliseconds per second */
3094 #define SCSI_MAX_RETRY               10 /* retry count */
3095
3096 #define ADV_ASYNC_RDMA_FAILURE          0x01    /* Fatal RDMA failure. */
3097 #define ADV_ASYNC_SCSI_BUS_RESET_DET    0x02    /* Detected SCSI Bus Reset. */
3098 #define ADV_ASYNC_CARRIER_READY_FAILURE 0x03    /* Carrier Ready failure. */
3099 #define ADV_RDMA_IN_CARR_AND_Q_INVALID  0x04    /* RDMAed-in data invalid. */
3100
3101 #define ADV_HOST_SCSI_BUS_RESET      0x80       /* Host Initiated SCSI Bus Reset. */
3102
3103 /*
3104  * Device drivers must define the following functions.
3105  */
3106 static inline ulong DvcEnterCritical(void);
3107 static inline void DvcLeaveCritical(ulong);
3108 static void DvcSleepMilliSecond(ADV_DCNT);
3109 static uchar DvcAdvReadPCIConfigByte(ADV_DVC_VAR *, ushort);
3110 static void DvcAdvWritePCIConfigByte(ADV_DVC_VAR *, ushort, uchar);
3111 static ADV_PADDR DvcGetPhyAddr(ADV_DVC_VAR *, ADV_SCSI_REQ_Q *,
3112                                uchar *, ASC_SDCNT *, int);
3113 static void DvcDelayMicroSecond(ADV_DVC_VAR *, ushort);
3114
3115 /*
3116  * Adv Library functions available to drivers.
3117  */
3118 static int AdvExeScsiQueue(ADV_DVC_VAR *, ADV_SCSI_REQ_Q *);
3119 static int AdvISR(ADV_DVC_VAR *);
3120 static int AdvInitGetConfig(ADV_DVC_VAR *);
3121 static int AdvInitAsc3550Driver(ADV_DVC_VAR *);
3122 static int AdvInitAsc38C0800Driver(ADV_DVC_VAR *);
3123 static int AdvInitAsc38C1600Driver(ADV_DVC_VAR *);
3124 static int AdvResetChipAndSB(ADV_DVC_VAR *);
3125 static int AdvResetSB(ADV_DVC_VAR *asc_dvc);
3126
3127 /*
3128  * Internal Adv Library functions.
3129  */
3130 static int AdvSendIdleCmd(ADV_DVC_VAR *, ushort, ADV_DCNT);
3131 static void AdvInquiryHandling(ADV_DVC_VAR *, ADV_SCSI_REQ_Q *);
3132 static int AdvInitFrom3550EEP(ADV_DVC_VAR *);
3133 static int AdvInitFrom38C0800EEP(ADV_DVC_VAR *);
3134 static int AdvInitFrom38C1600EEP(ADV_DVC_VAR *);
3135 static ushort AdvGet3550EEPConfig(AdvPortAddr, ADVEEP_3550_CONFIG *);
3136 static void AdvSet3550EEPConfig(AdvPortAddr, ADVEEP_3550_CONFIG *);
3137 static ushort AdvGet38C0800EEPConfig(AdvPortAddr, ADVEEP_38C0800_CONFIG *);
3138 static void AdvSet38C0800EEPConfig(AdvPortAddr, ADVEEP_38C0800_CONFIG *);
3139 static ushort AdvGet38C1600EEPConfig(AdvPortAddr, ADVEEP_38C1600_CONFIG *);
3140 static void AdvSet38C1600EEPConfig(AdvPortAddr, ADVEEP_38C1600_CONFIG *);
3141 static void AdvWaitEEPCmd(AdvPortAddr);
3142 static ushort AdvReadEEPWord(AdvPortAddr, int);
3143
3144 /*
3145  * PCI Bus Definitions
3146  */
3147 #define AscPCICmdRegBits_BusMastering     0x0007
3148 #define AscPCICmdRegBits_ParErrRespCtrl   0x0040
3149
3150 /* Read byte from a register. */
3151 #define AdvReadByteRegister(iop_base, reg_off) \
3152      (ADV_MEM_READB((iop_base) + (reg_off)))
3153
3154 /* Write byte to a register. */
3155 #define AdvWriteByteRegister(iop_base, reg_off, byte) \
3156      (ADV_MEM_WRITEB((iop_base) + (reg_off), (byte)))
3157
3158 /* Read word (2 bytes) from a register. */
3159 #define AdvReadWordRegister(iop_base, reg_off) \
3160      (ADV_MEM_READW((iop_base) + (reg_off)))
3161
3162 /* Write word (2 bytes) to a register. */
3163 #define AdvWriteWordRegister(iop_base, reg_off, word) \
3164      (ADV_MEM_WRITEW((iop_base) + (reg_off), (word)))
3165
3166 /* Write dword (4 bytes) to a register. */
3167 #define AdvWriteDWordRegister(iop_base, reg_off, dword) \
3168      (ADV_MEM_WRITEDW((iop_base) + (reg_off), (dword)))
3169
3170 /* Read byte from LRAM. */
3171 #define AdvReadByteLram(iop_base, addr, byte) \
3172 do { \
3173     ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)); \
3174     (byte) = ADV_MEM_READB((iop_base) + IOPB_RAM_DATA); \
3175 } while (0)
3176
3177 /* Write byte to LRAM. */
3178 #define AdvWriteByteLram(iop_base, addr, byte) \
3179     (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
3180      ADV_MEM_WRITEB((iop_base) + IOPB_RAM_DATA, (byte)))
3181
3182 /* Read word (2 bytes) from LRAM. */
3183 #define AdvReadWordLram(iop_base, addr, word) \
3184 do { \
3185     ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)); \
3186     (word) = (ADV_MEM_READW((iop_base) + IOPW_RAM_DATA)); \
3187 } while (0)
3188
3189 /* Write word (2 bytes) to LRAM. */
3190 #define AdvWriteWordLram(iop_base, addr, word) \
3191     (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
3192      ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, (word)))
3193
3194 /* Write little-endian double word (4 bytes) to LRAM */
3195 /* Because of unspecified C language ordering don't use auto-increment. */
3196 #define AdvWriteDWordLramNoSwap(iop_base, addr, dword) \
3197     ((ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
3198       ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, \
3199                      cpu_to_le16((ushort) ((dword) & 0xFFFF)))), \
3200      (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr) + 2), \
3201       ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, \
3202                      cpu_to_le16((ushort) ((dword >> 16) & 0xFFFF)))))
3203
3204 /* Read word (2 bytes) from LRAM assuming that the address is already set. */
3205 #define AdvReadWordAutoIncLram(iop_base) \
3206      (ADV_MEM_READW((iop_base) + IOPW_RAM_DATA))
3207
3208 /* Write word (2 bytes) to LRAM assuming that the address is already set. */
3209 #define AdvWriteWordAutoIncLram(iop_base, word) \
3210      (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, (word)))
3211
3212 /*
3213  * Define macro to check for Condor signature.
3214  *
3215  * Evaluate to ADV_TRUE if a Condor chip is found the specified port
3216  * address 'iop_base'. Otherwise evalue to ADV_FALSE.
3217  */
3218 #define AdvFindSignature(iop_base) \
3219     (((AdvReadByteRegister((iop_base), IOPB_CHIP_ID_1) == \
3220     ADV_CHIP_ID_BYTE) && \
3221      (AdvReadWordRegister((iop_base), IOPW_CHIP_ID_0) == \
3222     ADV_CHIP_ID_WORD)) ?  ADV_TRUE : ADV_FALSE)
3223
3224 /*
3225  * Define macro to Return the version number of the chip at 'iop_base'.
3226  *
3227  * The second parameter 'bus_type' is currently unused.
3228  */
3229 #define AdvGetChipVersion(iop_base, bus_type) \
3230     AdvReadByteRegister((iop_base), IOPB_CHIP_TYPE_REV)
3231
3232 /*
3233  * Abort an SRB in the chip's RISC Memory. The 'srb_ptr' argument must
3234  * match the ASC_SCSI_REQ_Q 'srb_ptr' field.
3235  *
3236  * If the request has not yet been sent to the device it will simply be
3237  * aborted from RISC memory. If the request is disconnected it will be
3238  * aborted on reselection by sending an Abort Message to the target ID.
3239  *
3240  * Return value:
3241  *      ADV_TRUE(1) - Queue was successfully aborted.
3242  *      ADV_FALSE(0) - Queue was not found on the active queue list.
3243  */
3244 #define AdvAbortQueue(asc_dvc, scsiq) \
3245         AdvSendIdleCmd((asc_dvc), (ushort) IDLE_CMD_ABORT, \
3246                        (ADV_DCNT) (scsiq))
3247
3248 /*
3249  * Send a Bus Device Reset Message to the specified target ID.
3250  *
3251  * All outstanding commands will be purged if sending the
3252  * Bus Device Reset Message is successful.
3253  *
3254  * Return Value:
3255  *      ADV_TRUE(1) - All requests on the target are purged.
3256  *      ADV_FALSE(0) - Couldn't issue Bus Device Reset Message; Requests
3257  *                     are not purged.
3258  */
3259 #define AdvResetDevice(asc_dvc, target_id) \
3260         AdvSendIdleCmd((asc_dvc), (ushort) IDLE_CMD_DEVICE_RESET, \
3261                     (ADV_DCNT) (target_id))
3262
3263 /*
3264  * SCSI Wide Type definition.
3265  */
3266 #define ADV_SCSI_BIT_ID_TYPE   ushort
3267
3268 /*
3269  * AdvInitScsiTarget() 'cntl_flag' options.
3270  */
3271 #define ADV_SCAN_LUN           0x01
3272 #define ADV_CAPINFO_NOLUN      0x02
3273
3274 /*
3275  * Convert target id to target id bit mask.
3276  */
3277 #define ADV_TID_TO_TIDMASK(tid)   (0x01 << ((tid) & ADV_MAX_TID))
3278
3279 /*
3280  * ASC_SCSI_REQ_Q 'done_status' and 'host_status' return values.
3281  */
3282
3283 #define QD_NO_STATUS         0x00       /* Request not completed yet. */
3284 #define QD_NO_ERROR          0x01
3285 #define QD_ABORTED_BY_HOST   0x02
3286 #define QD_WITH_ERROR        0x04
3287
3288 #define QHSTA_NO_ERROR              0x00
3289 #define QHSTA_M_SEL_TIMEOUT         0x11
3290 #define QHSTA_M_DATA_OVER_RUN       0x12
3291 #define QHSTA_M_UNEXPECTED_BUS_FREE 0x13
3292 #define QHSTA_M_QUEUE_ABORTED       0x15
3293 #define QHSTA_M_SXFR_SDMA_ERR       0x16        /* SXFR_STATUS SCSI DMA Error */
3294 #define QHSTA_M_SXFR_SXFR_PERR      0x17        /* SXFR_STATUS SCSI Bus Parity Error */
3295 #define QHSTA_M_RDMA_PERR           0x18        /* RISC PCI DMA parity error */
3296 #define QHSTA_M_SXFR_OFF_UFLW       0x19        /* SXFR_STATUS Offset Underflow */
3297 #define QHSTA_M_SXFR_OFF_OFLW       0x20        /* SXFR_STATUS Offset Overflow */
3298 #define QHSTA_M_SXFR_WD_TMO         0x21        /* SXFR_STATUS Watchdog Timeout */
3299 #define QHSTA_M_SXFR_DESELECTED     0x22        /* SXFR_STATUS Deselected */
3300 /* Note: QHSTA_M_SXFR_XFR_OFLW is identical to QHSTA_M_DATA_OVER_RUN. */
3301 #define QHSTA_M_SXFR_XFR_OFLW       0x12        /* SXFR_STATUS Transfer Overflow */
3302 #define QHSTA_M_SXFR_XFR_PH_ERR     0x24        /* SXFR_STATUS Transfer Phase Error */
3303 #define QHSTA_M_SXFR_UNKNOWN_ERROR  0x25        /* SXFR_STATUS Unknown Error */
3304 #define QHSTA_M_SCSI_BUS_RESET      0x30        /* Request aborted from SBR */
3305 #define QHSTA_M_SCSI_BUS_RESET_UNSOL 0x31       /* Request aborted from unsol. SBR */
3306 #define QHSTA_M_BUS_DEVICE_RESET    0x32        /* Request aborted from BDR */
3307 #define QHSTA_M_DIRECTION_ERR       0x35        /* Data Phase mismatch */
3308 #define QHSTA_M_DIRECTION_ERR_HUNG  0x36        /* Data Phase mismatch and bus hang */
3309 #define QHSTA_M_WTM_TIMEOUT         0x41
3310 #define QHSTA_M_BAD_CMPL_STATUS_IN  0x42
3311 #define QHSTA_M_NO_AUTO_REQ_SENSE   0x43
3312 #define QHSTA_M_AUTO_REQ_SENSE_FAIL 0x44
3313 #define QHSTA_M_INVALID_DEVICE      0x45        /* Bad target ID */
3314 #define QHSTA_M_FROZEN_TIDQ         0x46        /* TID Queue frozen. */
3315 #define QHSTA_M_SGBACKUP_ERROR      0x47        /* Scatter-Gather backup error */
3316
3317 /*
3318  * Default EEPROM Configuration structure defined in a_init.c.
3319  */
3320 static ADVEEP_3550_CONFIG Default_3550_EEPROM_Config;
3321 static ADVEEP_38C0800_CONFIG Default_38C0800_EEPROM_Config;
3322 static ADVEEP_38C1600_CONFIG Default_38C1600_EEPROM_Config;
3323
3324 /*
3325  * DvcGetPhyAddr() flag arguments
3326  */
3327 #define ADV_IS_SCSIQ_FLAG       0x01    /* 'addr' is ASC_SCSI_REQ_Q pointer */
3328 #define ADV_ASCGETSGLIST_VADDR  0x02    /* 'addr' is AscGetSGList() virtual addr */
3329 #define ADV_IS_SENSE_FLAG       0x04    /* 'addr' is sense virtual pointer */
3330 #define ADV_IS_DATA_FLAG        0x08    /* 'addr' is data virtual pointer */
3331 #define ADV_IS_SGLIST_FLAG      0x10    /* 'addr' is sglist virtual pointer */
3332 #define ADV_IS_CARRIER_FLAG     0x20    /* 'addr' is ADV_CARR_T pointer */
3333
3334 /* Return the address that is aligned at the next doubleword >= to 'addr'. */
3335 #define ADV_8BALIGN(addr)      (((ulong) (addr) + 0x7) & ~0x7)
3336 #define ADV_16BALIGN(addr)     (((ulong) (addr) + 0xF) & ~0xF)
3337 #define ADV_32BALIGN(addr)     (((ulong) (addr) + 0x1F) & ~0x1F)
3338
3339 /*
3340  * Total contiguous memory needed for driver SG blocks.
3341  *
3342  * ADV_MAX_SG_LIST must be defined by a driver. It is the maximum
3343  * number of scatter-gather elements the driver supports in a
3344  * single request.
3345  */
3346
3347 #define ADV_SG_LIST_MAX_BYTE_SIZE \
3348          (sizeof(ADV_SG_BLOCK) * \
3349           ((ADV_MAX_SG_LIST + (NO_OF_SG_PER_BLOCK - 1))/NO_OF_SG_PER_BLOCK))
3350
3351 /*
3352  * Inquiry data structure and bitfield macros
3353  *
3354  * Using bitfields to access the subchar data isn't portable across
3355  * endianness, so instead mask and shift. Only quantities of more
3356  * than 1 bit are shifted, since the others are just tested for true
3357  * or false.
3358  */
3359
3360 #define ADV_INQ_DVC_TYPE(inq)       ((inq)->periph & 0x1f)
3361 #define ADV_INQ_QUALIFIER(inq)      (((inq)->periph & 0xe0) >> 5)
3362 #define ADV_INQ_DVC_TYPE_MOD(inq)   ((inq)->devtype & 0x7f)
3363 #define ADV_INQ_REMOVABLE(inq)      ((inq)->devtype & 0x80)
3364 #define ADV_INQ_ANSI_VER(inq)       ((inq)->ver & 0x07)
3365 #define ADV_INQ_ECMA_VER(inq)       (((inq)->ver & 0x38) >> 3)
3366 #define ADV_INQ_ISO_VER(inq)        (((inq)->ver & 0xc0) >> 6)
3367 #define ADV_INQ_RESPONSE_FMT(inq)   ((inq)->byte3 & 0x0f)
3368 #define ADV_INQ_TERM_IO(inq)        ((inq)->byte3 & 0x40)
3369 #define ADV_INQ_ASYNC_NOTIF(inq)    ((inq)->byte3 & 0x80)
3370 #define ADV_INQ_SOFT_RESET(inq)     ((inq)->flags & 0x01)
3371 #define ADV_INQ_CMD_QUEUE(inq)      ((inq)->flags & 0x02)
3372 #define ADV_INQ_LINK_CMD(inq)       ((inq)->flags & 0x08)
3373 #define ADV_INQ_SYNC(inq)           ((inq)->flags & 0x10)
3374 #define ADV_INQ_WIDE16(inq)         ((inq)->flags & 0x20)
3375 #define ADV_INQ_WIDE32(inq)         ((inq)->flags & 0x40)
3376 #define ADV_INQ_REL_ADDR(inq)       ((inq)->flags & 0x80)
3377 #define ADV_INQ_INFO_UNIT(inq)      ((inq)->info & 0x01)
3378 #define ADV_INQ_QUICK_ARB(inq)      ((inq)->info & 0x02)
3379 #define ADV_INQ_CLOCKING(inq)       (((inq)->info & 0x0c) >> 2)
3380
3381 typedef struct {
3382         uchar periph;           /* peripheral device type [0:4] */
3383         /* peripheral qualifier [5:7] */
3384         uchar devtype;          /* device type modifier (for SCSI I) [0:6] */
3385         /* RMB - removable medium bit [7] */
3386         uchar ver;              /* ANSI approved version [0:2] */
3387         /* ECMA version [3:5] */
3388         /* ISO version [6:7] */
3389         uchar byte3;            /* response data format [0:3] */
3390         /* 0 SCSI 1 */
3391         /* 1 CCS */
3392         /* 2 SCSI-2 */
3393         /* 3-F reserved */
3394         /* reserved [4:5] */
3395         /* terminate I/O process bit (see 5.6.22) [6] */
3396         /* asynch. event notification (processor) [7] */
3397         uchar add_len;          /* additional length */
3398         uchar res1;             /* reserved */
3399         uchar res2;             /* reserved */
3400         uchar flags;            /* soft reset implemented [0] */
3401         /* command queuing [1] */
3402         /* reserved [2] */
3403         /* linked command for this logical unit [3] */
3404         /* synchronous data transfer [4] */
3405         /* wide bus 16 bit data transfer [5] */
3406         /* wide bus 32 bit data transfer [6] */
3407         /* relative addressing mode [7] */
3408         uchar vendor_id[8];     /* vendor identification */
3409         uchar product_id[16];   /* product identification */
3410         uchar product_rev_level[4];     /* product revision level */
3411         uchar vendor_specific[20];      /* vendor specific */
3412         uchar info;             /* information unit supported [0] */
3413         /* quick arbitrate supported [1] */
3414         /* clocking field [2:3] */
3415         /* reserved [4:7] */
3416         uchar res3;             /* reserved */
3417 } ADV_SCSI_INQUIRY;             /* 58 bytes */
3418
3419 /*
3420  * --- Driver Constants and Macros
3421  */
3422
3423 #define ASC_NUM_BOARD_SUPPORTED 16
3424 #define ASC_NUM_IOPORT_PROBE    4
3425 #define ASC_NUM_BUS             4
3426
3427 /* Reference Scsi_Host hostdata */
3428 #define ASC_BOARDP(host) ((asc_board_t *) &((host)->hostdata))
3429
3430 /* asc_board_t flags */
3431 #define ASC_HOST_IN_RESET       0x01
3432 #define ASC_IS_WIDE_BOARD       0x04    /* AdvanSys Wide Board */
3433 #define ASC_SELECT_QUEUE_DEPTHS 0x08
3434
3435 #define ASC_NARROW_BOARD(boardp) (((boardp)->flags & ASC_IS_WIDE_BOARD) == 0)
3436 #define ASC_WIDE_BOARD(boardp)   ((boardp)->flags & ASC_IS_WIDE_BOARD)
3437
3438 #define NO_ISA_DMA              0xff    /* No ISA DMA Channel Used */
3439
3440 #define ASC_INFO_SIZE           128     /* advansys_info() line size */
3441
3442 #ifdef CONFIG_PROC_FS
3443 /* /proc/scsi/advansys/[0...] related definitions */
3444 #define ASC_PRTBUF_SIZE         2048
3445 #define ASC_PRTLINE_SIZE        160
3446
3447 #define ASC_PRT_NEXT() \
3448     if (cp) { \
3449         totlen += len; \
3450         leftlen -= len; \
3451         if (leftlen == 0) { \
3452             return totlen; \
3453         } \
3454         cp += len; \
3455     }
3456 #endif /* CONFIG_PROC_FS */
3457
3458 /* Asc Library return codes */
3459 #define ASC_TRUE        1
3460 #define ASC_FALSE       0
3461 #define ASC_NOERROR     1
3462 #define ASC_BUSY        0
3463 #define ASC_ERROR       (-1)
3464
3465 /* struct scsi_cmnd function return codes */
3466 #define STATUS_BYTE(byte)   (byte)
3467 #define MSG_BYTE(byte)      ((byte) << 8)
3468 #define HOST_BYTE(byte)     ((byte) << 16)
3469 #define DRIVER_BYTE(byte)   ((byte) << 24)
3470
3471 /*
3472  * The following definitions and macros are OS independent interfaces to
3473  * the queue functions:
3474  *  REQ - SCSI request structure
3475  *  REQP - pointer to SCSI request structure
3476  *  REQPTID(reqp) - reqp's target id
3477  *  REQPNEXT(reqp) - reqp's next pointer
3478  *  REQPNEXTP(reqp) - pointer to reqp's next pointer
3479  *  REQPTIME(reqp) - reqp's time stamp value
3480  *  REQTIMESTAMP() - system time stamp value
3481  */
3482 typedef struct scsi_cmnd REQ, *REQP;
3483 #define REQPNEXT(reqp)       ((REQP) ((reqp)->host_scribble))
3484 #define REQPNEXTP(reqp)      ((REQP *) &((reqp)->host_scribble))
3485 #define REQPTID(reqp)        ((reqp)->device->id)
3486 #define REQPTIME(reqp)       ((reqp)->SCp.this_residual)
3487 #define REQTIMESTAMP()       (jiffies)
3488
3489 #define REQTIMESTAT(function, ascq, reqp, tid) \
3490 { \
3491     /*
3492      * If the request time stamp is less than the system time stamp, then \
3493      * maybe the system time stamp wrapped. Set the request time to zero.\
3494      */ \
3495     if (REQPTIME(reqp) <= REQTIMESTAMP()) { \
3496         REQPTIME(reqp) = REQTIMESTAMP() - REQPTIME(reqp); \
3497     } else { \
3498         /* Indicate an error occurred with the assertion. */ \
3499         ASC_ASSERT(REQPTIME(reqp) <= REQTIMESTAMP()); \
3500         REQPTIME(reqp) = 0; \
3501     } \
3502     /* Handle first minimum time case without external initialization. */ \
3503     if (((ascq)->q_tot_cnt[tid] == 1) ||  \
3504         (REQPTIME(reqp) < (ascq)->q_min_tim[tid])) { \
3505             (ascq)->q_min_tim[tid] = REQPTIME(reqp); \
3506             ASC_DBG3(1, "%s: new q_min_tim[%d] %u\n", \
3507                 (function), (tid), (ascq)->q_min_tim[tid]); \
3508         } \
3509     if (REQPTIME(reqp) > (ascq)->q_max_tim[tid]) { \
3510         (ascq)->q_max_tim[tid] = REQPTIME(reqp); \
3511         ASC_DBG3(1, "%s: new q_max_tim[%d] %u\n", \
3512             (function), tid, (ascq)->q_max_tim[tid]); \
3513     } \
3514     (ascq)->q_tot_tim[tid] += REQPTIME(reqp); \
3515     /* Reset the time stamp field. */ \
3516     REQPTIME(reqp) = 0; \
3517 }
3518
3519 /* asc_enqueue() flags */
3520 #define ASC_FRONT       1
3521 #define ASC_BACK        2
3522
3523 /* asc_dequeue_list() argument */
3524 #define ASC_TID_ALL        (-1)
3525
3526 /* Return non-zero, if the queue is empty. */
3527 #define ASC_QUEUE_EMPTY(ascq)    ((ascq)->q_tidmask == 0)
3528
3529 #define PCI_MAX_SLOT            0x1F
3530 #define PCI_MAX_BUS             0xFF
3531 #define PCI_IOADDRESS_MASK      0xFFFE
3532 #define ASC_PCI_DEVICE_ID_CNT   6       /* PCI Device ID count. */
3533
3534 #ifndef ADVANSYS_STATS
3535 #define ASC_STATS(shost, counter)
3536 #define ASC_STATS_ADD(shost, counter, count)
3537 #else /* ADVANSYS_STATS */
3538 #define ASC_STATS(shost, counter) \
3539     (ASC_BOARDP(shost)->asc_stats.counter++)
3540
3541 #define ASC_STATS_ADD(shost, counter, count) \
3542     (ASC_BOARDP(shost)->asc_stats.counter += (count))
3543 #endif /* ADVANSYS_STATS */
3544
3545 #define ASC_CEILING(val, unit) (((val) + ((unit) - 1))/(unit))
3546
3547 /* If the result wraps when calculating tenths, return 0. */
3548 #define ASC_TENTHS(num, den) \
3549     (((10 * ((num)/(den))) > (((num) * 10)/(den))) ? \
3550     0 : ((((num) * 10)/(den)) - (10 * ((num)/(den)))))
3551
3552 /*
3553  * Display a message to the console.
3554  */
3555 #define ASC_PRINT(s) \
3556     { \
3557         printk("advansys: "); \
3558         printk(s); \
3559     }
3560
3561 #define ASC_PRINT1(s, a1) \
3562     { \
3563         printk("advansys: "); \
3564         printk((s), (a1)); \
3565     }
3566
3567 #define ASC_PRINT2(s, a1, a2) \
3568     { \
3569         printk("advansys: "); \
3570         printk((s), (a1), (a2)); \
3571     }
3572
3573 #define ASC_PRINT3(s, a1, a2, a3) \
3574     { \
3575         printk("advansys: "); \
3576         printk((s), (a1), (a2), (a3)); \
3577     }
3578
3579 #define ASC_PRINT4(s, a1, a2, a3, a4) \
3580     { \
3581         printk("advansys: "); \
3582         printk((s), (a1), (a2), (a3), (a4)); \
3583     }
3584
3585 #ifndef ADVANSYS_DEBUG
3586
3587 #define ASC_DBG(lvl, s)
3588 #define ASC_DBG1(lvl, s, a1)
3589 #define ASC_DBG2(lvl, s, a1, a2)
3590 #define ASC_DBG3(lvl, s, a1, a2, a3)
3591 #define ASC_DBG4(lvl, s, a1, a2, a3, a4)
3592 #define ASC_DBG_PRT_SCSI_HOST(lvl, s)
3593 #define ASC_DBG_PRT_SCSI_CMND(lvl, s)
3594 #define ASC_DBG_PRT_ASC_SCSI_Q(lvl, scsiqp)
3595 #define ASC_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp)
3596 #define ASC_DBG_PRT_ASC_QDONE_INFO(lvl, qdone)
3597 #define ADV_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp)
3598 #define ASC_DBG_PRT_HEX(lvl, name, start, length)
3599 #define ASC_DBG_PRT_CDB(lvl, cdb, len)
3600 #define ASC_DBG_PRT_SENSE(lvl, sense, len)
3601 #define ASC_DBG_PRT_INQUIRY(lvl, inq, len)
3602
3603 #else /* ADVANSYS_DEBUG */
3604
3605 /*
3606  * Debugging Message Levels:
3607  * 0: Errors Only
3608  * 1: High-Level Tracing
3609  * 2-N: Verbose Tracing
3610  */
3611
3612 #define ASC_DBG(lvl, s) \
3613     { \
3614         if (asc_dbglvl >= (lvl)) { \
3615             printk(s); \
3616         } \
3617     }
3618
3619 #define ASC_DBG1(lvl, s, a1) \
3620     { \
3621         if (asc_dbglvl >= (lvl)) { \
3622             printk((s), (a1)); \
3623         } \
3624     }
3625
3626 #define ASC_DBG2(lvl, s, a1, a2) \
3627     { \
3628         if (asc_dbglvl >= (lvl)) { \
3629             printk((s), (a1), (a2)); \
3630         } \
3631     }
3632
3633 #define ASC_DBG3(lvl, s, a1, a2, a3) \
3634     { \
3635         if (asc_dbglvl >= (lvl)) { \
3636             printk((s), (a1), (a2), (a3)); \
3637         } \
3638     }
3639
3640 #define ASC_DBG4(lvl, s, a1, a2, a3, a4) \
3641     { \
3642         if (asc_dbglvl >= (lvl)) { \
3643             printk((s), (a1), (a2), (a3), (a4)); \
3644         } \
3645     }
3646
3647 #define ASC_DBG_PRT_SCSI_HOST(lvl, s) \
3648     { \
3649         if (asc_dbglvl >= (lvl)) { \
3650             asc_prt_scsi_host(s); \
3651         } \
3652     }
3653
3654 #define ASC_DBG_PRT_SCSI_CMND(lvl, s) \
3655     { \
3656         if (asc_dbglvl >= (lvl)) { \
3657             asc_prt_scsi_cmnd(s); \
3658         } \
3659     }
3660
3661 #define ASC_DBG_PRT_ASC_SCSI_Q(lvl, scsiqp) \
3662     { \
3663         if (asc_dbglvl >= (lvl)) { \
3664             asc_prt_asc_scsi_q(scsiqp); \
3665         } \
3666     }
3667
3668 #define ASC_DBG_PRT_ASC_QDONE_INFO(lvl, qdone) \
3669     { \
3670         if (asc_dbglvl >= (lvl)) { \
3671             asc_prt_asc_qdone_info(qdone); \
3672         } \
3673     }
3674
3675 #define ASC_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp) \
3676     { \
3677         if (asc_dbglvl >= (lvl)) { \
3678             asc_prt_adv_scsi_req_q(scsiqp); \
3679         } \
3680     }
3681
3682 #define ASC_DBG_PRT_HEX(lvl, name, start, length) \
3683     { \
3684         if (asc_dbglvl >= (lvl)) { \
3685             asc_prt_hex((name), (start), (length)); \
3686         } \
3687     }
3688
3689 #define ASC_DBG_PRT_CDB(lvl, cdb, len) \
3690         ASC_DBG_PRT_HEX((lvl), "CDB", (uchar *) (cdb), (len));
3691
3692 #define ASC_DBG_PRT_SENSE(lvl, sense, len) \
3693         ASC_DBG_PRT_HEX((lvl), "SENSE", (uchar *) (sense), (len));
3694
3695 #define ASC_DBG_PRT_INQUIRY(lvl, inq, len) \
3696         ASC_DBG_PRT_HEX((lvl), "INQUIRY", (uchar *) (inq), (len));
3697 #endif /* ADVANSYS_DEBUG */
3698
3699 #ifndef ADVANSYS_ASSERT
3700 #define ASC_ASSERT(a)
3701 #else /* ADVANSYS_ASSERT */
3702
3703 #define ASC_ASSERT(a) \
3704     { \
3705         if (!(a)) { \
3706             printk("ASC_ASSERT() Failure: file %s, line %d\n", \
3707                 __FILE__, __LINE__); \
3708         } \
3709     }
3710
3711 #endif /* ADVANSYS_ASSERT */
3712
3713 /*
3714  * --- Driver Structures
3715  */
3716
3717 #ifdef ADVANSYS_STATS
3718
3719 /* Per board statistics structure */
3720 struct asc_stats {
3721         /* Driver Entrypoint Statistics */
3722         ADV_DCNT queuecommand;  /* # calls to advansys_queuecommand() */
3723         ADV_DCNT reset;         /* # calls to advansys_eh_bus_reset() */
3724         ADV_DCNT biosparam;     /* # calls to advansys_biosparam() */
3725         ADV_DCNT interrupt;     /* # advansys_interrupt() calls */
3726         ADV_DCNT callback;      /* # calls to asc/adv_isr_callback() */
3727         ADV_DCNT done;          /* # calls to request's scsi_done function */
3728         ADV_DCNT build_error;   /* # asc/adv_build_req() ASC_ERROR returns. */
3729         ADV_DCNT adv_build_noreq;       /* # adv_build_req() adv_req_t alloc. fail. */
3730         ADV_DCNT adv_build_nosg;        /* # adv_build_req() adv_sgblk_t alloc. fail. */
3731         /* AscExeScsiQueue()/AdvExeScsiQueue() Statistics */
3732         ADV_DCNT exe_noerror;   /* # ASC_NOERROR returns. */
3733         ADV_DCNT exe_busy;      /* # ASC_BUSY returns. */
3734         ADV_DCNT exe_error;     /* # ASC_ERROR returns. */
3735         ADV_DCNT exe_unknown;   /* # unknown returns. */
3736         /* Data Transfer Statistics */
3737         ADV_DCNT cont_cnt;      /* # non-scatter-gather I/O requests received */
3738         ADV_DCNT cont_xfer;     /* # contiguous transfer 512-bytes */
3739         ADV_DCNT sg_cnt;        /* # scatter-gather I/O requests received */
3740         ADV_DCNT sg_elem;       /* # scatter-gather elements */
3741         ADV_DCNT sg_xfer;       /* # scatter-gather transfer 512-bytes */
3742 };
3743 #endif /* ADVANSYS_STATS */
3744
3745 /*
3746  * Request queuing structure
3747  */
3748 typedef struct asc_queue {
3749         ADV_SCSI_BIT_ID_TYPE q_tidmask; /* queue mask */
3750         REQP q_first[ADV_MAX_TID + 1];  /* first queued request */
3751         REQP q_last[ADV_MAX_TID + 1];   /* last queued request */
3752 #ifdef ADVANSYS_STATS
3753         short q_cur_cnt[ADV_MAX_TID + 1];       /* current queue count */
3754         short q_max_cnt[ADV_MAX_TID + 1];       /* maximum queue count */
3755         ADV_DCNT q_tot_cnt[ADV_MAX_TID + 1];    /* total enqueue count */
3756         ADV_DCNT q_tot_tim[ADV_MAX_TID + 1];    /* total time queued */
3757         ushort q_max_tim[ADV_MAX_TID + 1];      /* maximum time queued */
3758         ushort q_min_tim[ADV_MAX_TID + 1];      /* minimum time queued */
3759 #endif                          /* ADVANSYS_STATS */
3760 } asc_queue_t;
3761
3762 /*
3763  * Adv Library Request Structures
3764  *
3765  * The following two structures are used to process Wide Board requests.
3766  *
3767  * The ADV_SCSI_REQ_Q structure in adv_req_t is passed to the Adv Library
3768  * and microcode with the ADV_SCSI_REQ_Q field 'srb_ptr' pointing to the
3769  * adv_req_t. The adv_req_t structure 'cmndp' field in turn points to the
3770  * Mid-Level SCSI request structure.
3771  *
3772  * Zero or more ADV_SG_BLOCK are used with each ADV_SCSI_REQ_Q. Each
3773  * ADV_SG_BLOCK structure holds 15 scatter-gather elements. Under Linux
3774  * up to 255 scatter-gather elements may be used per request or
3775  * ADV_SCSI_REQ_Q.
3776  *
3777  * Both structures must be 32 byte aligned.
3778  */
3779 typedef struct adv_sgblk {
3780         ADV_SG_BLOCK sg_block;  /* Sgblock structure. */
3781         uchar align[32];        /* Sgblock structure padding. */
3782         struct adv_sgblk *next_sgblkp;  /* Next scatter-gather structure. */
3783 } adv_sgblk_t;
3784
3785 typedef struct adv_req {
3786         ADV_SCSI_REQ_Q scsi_req_q;      /* Adv Library request structure. */
3787         uchar align[32];        /* Request structure padding. */
3788         struct scsi_cmnd *cmndp;        /* Mid-Level SCSI command pointer. */
3789         adv_sgblk_t *sgblkp;    /* Adv Library scatter-gather pointer. */
3790         struct adv_req *next_reqp;      /* Next Request Structure. */
3791 } adv_req_t;
3792
3793 /*
3794  * Structure allocated for each board.
3795  *
3796  * This structure is allocated by scsi_register() at the end
3797  * of the 'Scsi_Host' structure starting at the 'hostdata'
3798  * field. It is guaranteed to be allocated from DMA-able memory.
3799  */
3800 typedef struct asc_board {
3801         int id;                 /* Board Id */
3802         uint flags;             /* Board flags */
3803         union {
3804                 ASC_DVC_VAR asc_dvc_var;        /* Narrow board */
3805                 ADV_DVC_VAR adv_dvc_var;        /* Wide board */
3806         } dvc_var;
3807         union {
3808                 ASC_DVC_CFG asc_dvc_cfg;        /* Narrow board */
3809                 ADV_DVC_CFG adv_dvc_cfg;        /* Wide board */
3810         } dvc_cfg;
3811         ushort asc_n_io_port;   /* Number I/O ports. */
3812         asc_queue_t active;     /* Active command queue */
3813         asc_queue_t waiting;    /* Waiting command queue */
3814         asc_queue_t done;       /* Done command queue */
3815         ADV_SCSI_BIT_ID_TYPE init_tidmask;      /* Target init./valid mask */
3816         struct scsi_device *device[ADV_MAX_TID + 1];    /* Mid-Level Scsi Device */
3817         ushort reqcnt[ADV_MAX_TID + 1]; /* Starvation request count */
3818         ADV_SCSI_BIT_ID_TYPE queue_full;        /* Queue full mask */
3819         ushort queue_full_cnt[ADV_MAX_TID + 1]; /* Queue full count */
3820         union {
3821                 ASCEEP_CONFIG asc_eep;  /* Narrow EEPROM config. */
3822                 ADVEEP_3550_CONFIG adv_3550_eep;        /* 3550 EEPROM config. */
3823                 ADVEEP_38C0800_CONFIG adv_38C0800_eep;  /* 38C0800 EEPROM config. */
3824                 ADVEEP_38C1600_CONFIG adv_38C1600_eep;  /* 38C1600 EEPROM config. */
3825         } eep_config;
3826         ulong last_reset;       /* Saved last reset time */
3827         spinlock_t lock;        /* Board spinlock */
3828 #ifdef CONFIG_PROC_FS
3829         /* /proc/scsi/advansys/[0...] */
3830         char *prtbuf;           /* /proc print buffer */
3831 #endif                          /* CONFIG_PROC_FS */
3832 #ifdef ADVANSYS_STATS
3833         struct asc_stats asc_stats;     /* Board statistics */
3834 #endif                          /* ADVANSYS_STATS */
3835         /*
3836          * The following fields are used only for Narrow Boards.
3837          */
3838         /* The following three structures must be in DMA-able memory. */
3839         ASC_SCSI_REQ_Q scsireqq;
3840         ASC_CAP_INFO cap_info;
3841         ASC_SCSI_INQUIRY inquiry;
3842         uchar sdtr_data[ASC_MAX_TID + 1];       /* SDTR information */
3843         /*
3844          * The following fields are used only for Wide Boards.
3845          */
3846         void __iomem *ioremap_addr;     /* I/O Memory remap address. */
3847         ushort ioport;          /* I/O Port address. */
3848         ADV_CARR_T *orig_carrp; /* ADV_CARR_T memory block. */
3849         adv_req_t *orig_reqp;   /* adv_req_t memory block. */
3850         adv_req_t *adv_reqp;    /* Request structures. */
3851         adv_sgblk_t *adv_sgblkp;        /* Scatter-gather structures. */
3852         ushort bios_signature;  /* BIOS Signature. */
3853         ushort bios_version;    /* BIOS Version. */
3854         ushort bios_codeseg;    /* BIOS Code Segment. */
3855         ushort bios_codelen;    /* BIOS Code Segment Length. */
3856 } asc_board_t;
3857
3858 /*
3859  * PCI configuration structures
3860  */
3861 typedef struct _PCI_DATA_ {
3862         uchar type;
3863         uchar bus;
3864         uchar slot;
3865         uchar func;
3866         uchar offset;
3867 } PCI_DATA;
3868
3869 typedef struct _PCI_DEVICE_ {
3870         ushort vendorID;
3871         ushort deviceID;
3872         ushort slotNumber;
3873         ushort slotFound;
3874         uchar busNumber;
3875         uchar maxBusNumber;
3876         uchar devFunc;
3877         ushort startSlot;
3878         ushort endSlot;
3879         uchar bridge;
3880         uchar type;
3881 } PCI_DEVICE;
3882
3883 typedef struct _PCI_CONFIG_SPACE_ {
3884         ushort vendorID;
3885         ushort deviceID;
3886         ushort command;
3887         ushort status;
3888         uchar revision;
3889         uchar classCode[3];
3890         uchar cacheSize;
3891         uchar latencyTimer;
3892         uchar headerType;
3893         uchar bist;
3894         ADV_PADDR baseAddress[6];
3895         ushort reserved[4];
3896         ADV_PADDR optionRomAddr;
3897         ushort reserved2[4];
3898         uchar irqLine;
3899         uchar irqPin;
3900         uchar minGnt;
3901         uchar maxLatency;
3902 } PCI_CONFIG_SPACE;
3903
3904 /*
3905  * --- Driver Data
3906  */
3907
3908 /* Note: All driver global data should be initialized. */
3909
3910 /* Number of boards detected in system. */
3911 static int asc_board_count = 0;
3912 static struct Scsi_Host *asc_host[ASC_NUM_BOARD_SUPPORTED] = { NULL };
3913
3914 /* Overrun buffer used by all narrow boards. */
3915 static uchar overrun_buf[ASC_OVERRUN_BSIZE] = { 0 };
3916
3917 /*
3918  * Global structures required to issue a command.
3919  */
3920 static ASC_SCSI_Q asc_scsi_q = { {0} };
3921 static ASC_SG_HEAD asc_sg_head = { 0 };
3922
3923 /* List of supported bus types. */
3924 static ushort asc_bus[ASC_NUM_BUS] __initdata = {
3925         ASC_IS_ISA,
3926         ASC_IS_VL,
3927         ASC_IS_EISA,
3928         ASC_IS_PCI,
3929 };
3930
3931 static int asc_iopflag = ASC_FALSE;
3932 static int asc_ioport[ASC_NUM_IOPORT_PROBE] = { 0, 0, 0, 0 };
3933
3934 #ifdef ADVANSYS_DEBUG
3935 static char *asc_bus_name[ASC_NUM_BUS] = {
3936         "ASC_IS_ISA",
3937         "ASC_IS_VL",
3938         "ASC_IS_EISA",
3939         "ASC_IS_PCI",
3940 };
3941
3942 static int asc_dbglvl = 3;
3943 #endif /* ADVANSYS_DEBUG */
3944
3945 /* Declaration for Asc Library internal data referenced by driver. */
3946 static PortAddr _asc_def_iop_base[];
3947
3948 /*
3949  * --- Driver Function Prototypes
3950  *
3951  * advansys.h contains function prototypes for functions global to Linux.
3952  */
3953
3954 static irqreturn_t advansys_interrupt(int, void *);
3955 static int advansys_slave_configure(struct scsi_device *);
3956 static void asc_scsi_done_list(struct scsi_cmnd *);
3957 static int asc_execute_scsi_cmnd(struct scsi_cmnd *);
3958 static int asc_build_req(asc_board_t *, struct scsi_cmnd *);
3959 static int adv_build_req(asc_board_t *, struct scsi_cmnd *, ADV_SCSI_REQ_Q **);
3960 static int adv_get_sglist(asc_board_t *, adv_req_t *, struct scsi_cmnd *, int);
3961 static void asc_isr_callback(ASC_DVC_VAR *, ASC_QDONE_INFO *);
3962 static void adv_isr_callback(ADV_DVC_VAR *, ADV_SCSI_REQ_Q *);
3963 static void adv_async_callback(ADV_DVC_VAR *, uchar);
3964 static void asc_enqueue(asc_queue_t *, REQP, int);
3965 static REQP asc_dequeue(asc_queue_t *, int);
3966 static REQP asc_dequeue_list(asc_queue_t *, REQP *, int);
3967 static int asc_rmqueue(asc_queue_t *, REQP);
3968 static void asc_execute_queue(asc_queue_t *);
3969 #ifdef CONFIG_PROC_FS
3970 static int asc_proc_copy(off_t, off_t, char *, int, char *, int);
3971 static int asc_prt_board_devices(struct Scsi_Host *, char *, int);
3972 static int asc_prt_adv_bios(struct Scsi_Host *, char *, int);
3973 static int asc_get_eeprom_string(ushort *serialnum, uchar *cp);
3974 static int asc_prt_asc_board_eeprom(struct Scsi_Host *, char *, int);
3975 static int asc_prt_adv_board_eeprom(struct Scsi_Host *, char *, int);
3976 static int asc_prt_driver_conf(struct Scsi_Host *, char *, int);
3977 static int asc_prt_asc_board_info(struct Scsi_Host *, char *, int);
3978 static int asc_prt_adv_board_info(struct Scsi_Host *, char *, int);
3979 static int asc_prt_line(char *, int, char *fmt, ...);
3980 #endif /* CONFIG_PROC_FS */
3981
3982 /* Declaration for Asc Library internal functions referenced by driver. */
3983 static int AscFindSignature(PortAddr);
3984 static ushort AscGetEEPConfig(PortAddr, ASCEEP_CONFIG *, ushort);
3985
3986 /* Statistics function prototypes. */
3987 #ifdef ADVANSYS_STATS
3988 #ifdef CONFIG_PROC_FS
3989 static int asc_prt_board_stats(struct Scsi_Host *, char *, int);
3990 static int asc_prt_target_stats(struct Scsi_Host *, int, char *, int);
3991 #endif /* CONFIG_PROC_FS */
3992 #endif /* ADVANSYS_STATS */
3993
3994 /* Debug function prototypes. */
3995 #ifdef ADVANSYS_DEBUG
3996 static void asc_prt_scsi_host(struct Scsi_Host *);
3997 static void asc_prt_scsi_cmnd(struct scsi_cmnd *);
3998 static void asc_prt_asc_dvc_cfg(ASC_DVC_CFG *);
3999 static void asc_prt_asc_dvc_var(ASC_DVC_VAR *);
4000 static void asc_prt_asc_scsi_q(ASC_SCSI_Q *);
4001 static void asc_prt_asc_qdone_info(ASC_QDONE_INFO *);
4002 static void asc_prt_adv_dvc_cfg(ADV_DVC_CFG *);
4003 static void asc_prt_adv_dvc_var(ADV_DVC_VAR *);
4004 static void asc_prt_adv_scsi_req_q(ADV_SCSI_REQ_Q *);
4005 static void asc_prt_adv_sgblock(int, ADV_SG_BLOCK *);
4006 static void asc_prt_hex(char *f, uchar *, int);
4007 #endif /* ADVANSYS_DEBUG */
4008
4009 #ifdef CONFIG_PROC_FS
4010 /*
4011  * advansys_proc_info() - /proc/scsi/advansys/[0-(ASC_NUM_BOARD_SUPPORTED-1)]
4012  *
4013  * *buffer: I/O buffer
4014  * **start: if inout == FALSE pointer into buffer where user read should start
4015  * offset: current offset into a /proc/scsi/advansys/[0...] file
4016  * length: length of buffer
4017  * hostno: Scsi_Host host_no
4018  * inout: TRUE - user is writing; FALSE - user is reading
4019  *
4020  * Return the number of bytes read from or written to a
4021  * /proc/scsi/advansys/[0...] file.
4022  *
4023  * Note: This function uses the per board buffer 'prtbuf' which is
4024  * allocated when the board is initialized in advansys_detect(). The
4025  * buffer is ASC_PRTBUF_SIZE bytes. The function asc_proc_copy() is
4026  * used to write to the buffer. The way asc_proc_copy() is written
4027  * if 'prtbuf' is too small it will not be overwritten. Instead the
4028  * user just won't get all the available statistics.
4029  */
4030 static int
4031 advansys_proc_info(struct Scsi_Host *shost, char *buffer, char **start,
4032                    off_t offset, int length, int inout)
4033 {
4034         asc_board_t *boardp;
4035         char *cp;
4036         int cplen;
4037         int cnt;
4038         int totcnt;
4039         int leftlen;
4040         char *curbuf;
4041         off_t advoffset;
4042 #ifdef ADVANSYS_STATS
4043         int tgt_id;
4044 #endif /* ADVANSYS_STATS */
4045
4046         ASC_DBG(1, "advansys_proc_info: begin\n");
4047
4048         /*
4049          * User write not supported.
4050          */
4051         if (inout == TRUE) {
4052                 return (-ENOSYS);
4053         }
4054
4055         /*
4056          * User read of /proc/scsi/advansys/[0...] file.
4057          */
4058
4059         boardp = ASC_BOARDP(shost);
4060
4061         /* Copy read data starting at the beginning of the buffer. */
4062         *start = buffer;
4063         curbuf = buffer;
4064         advoffset = 0;
4065         totcnt = 0;
4066         leftlen = length;
4067
4068         /*
4069          * Get board configuration information.
4070          *
4071          * advansys_info() returns the board string from its own static buffer.
4072          */
4073         cp = (char *)advansys_info(shost);
4074         strcat(cp, "\n");
4075         cplen = strlen(cp);
4076         /* Copy board information. */
4077         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4078         totcnt += cnt;
4079         leftlen -= cnt;
4080         if (leftlen == 0) {
4081                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4082                 return totcnt;
4083         }
4084         advoffset += cplen;
4085         curbuf += cnt;
4086
4087         /*
4088          * Display Wide Board BIOS Information.
4089          */
4090         if (ASC_WIDE_BOARD(boardp)) {
4091                 cp = boardp->prtbuf;
4092                 cplen = asc_prt_adv_bios(shost, cp, ASC_PRTBUF_SIZE);
4093                 ASC_ASSERT(cplen < ASC_PRTBUF_SIZE);
4094                 cnt =
4095                     asc_proc_copy(advoffset, offset, curbuf, leftlen, cp,
4096                                   cplen);
4097                 totcnt += cnt;
4098                 leftlen -= cnt;
4099                 if (leftlen == 0) {
4100                         ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4101                         return totcnt;
4102                 }
4103                 advoffset += cplen;
4104                 curbuf += cnt;
4105         }
4106
4107         /*
4108          * Display driver information for each device attached to the board.
4109          */
4110         cp = boardp->prtbuf;
4111         cplen = asc_prt_board_devices(shost, cp, ASC_PRTBUF_SIZE);
4112         ASC_ASSERT(cplen < ASC_PRTBUF_SIZE);
4113         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4114         totcnt += cnt;
4115         leftlen -= cnt;
4116         if (leftlen == 0) {
4117                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4118                 return totcnt;
4119         }
4120         advoffset += cplen;
4121         curbuf += cnt;
4122
4123         /*
4124          * Display EEPROM configuration for the board.
4125          */
4126         cp = boardp->prtbuf;
4127         if (ASC_NARROW_BOARD(boardp)) {
4128                 cplen = asc_prt_asc_board_eeprom(shost, cp, ASC_PRTBUF_SIZE);
4129         } else {
4130                 cplen = asc_prt_adv_board_eeprom(shost, cp, ASC_PRTBUF_SIZE);
4131         }
4132         ASC_ASSERT(cplen < ASC_PRTBUF_SIZE);
4133         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4134         totcnt += cnt;
4135         leftlen -= cnt;
4136         if (leftlen == 0) {
4137                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4138                 return totcnt;
4139         }
4140         advoffset += cplen;
4141         curbuf += cnt;
4142
4143         /*
4144          * Display driver configuration and information for the board.
4145          */
4146         cp = boardp->prtbuf;
4147         cplen = asc_prt_driver_conf(shost, cp, ASC_PRTBUF_SIZE);
4148         ASC_ASSERT(cplen < ASC_PRTBUF_SIZE);
4149         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4150         totcnt += cnt;
4151         leftlen -= cnt;
4152         if (leftlen == 0) {
4153                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4154                 return totcnt;
4155         }
4156         advoffset += cplen;
4157         curbuf += cnt;
4158
4159 #ifdef ADVANSYS_STATS
4160         /*
4161          * Display driver statistics for the board.
4162          */
4163         cp = boardp->prtbuf;
4164         cplen = asc_prt_board_stats(shost, cp, ASC_PRTBUF_SIZE);
4165         ASC_ASSERT(cplen <= ASC_PRTBUF_SIZE);
4166         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4167         totcnt += cnt;
4168         leftlen -= cnt;
4169         if (leftlen == 0) {
4170                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4171                 return totcnt;
4172         }
4173         advoffset += cplen;
4174         curbuf += cnt;
4175
4176         /*
4177          * Display driver statistics for each target.
4178          */
4179         for (tgt_id = 0; tgt_id <= ADV_MAX_TID; tgt_id++) {
4180                 cp = boardp->prtbuf;
4181                 cplen = asc_prt_target_stats(shost, tgt_id, cp,
4182                                                         ASC_PRTBUF_SIZE);
4183                 ASC_ASSERT(cplen <= ASC_PRTBUF_SIZE);
4184                 cnt =
4185                     asc_proc_copy(advoffset, offset, curbuf, leftlen, cp,
4186                                   cplen);
4187                 totcnt += cnt;
4188                 leftlen -= cnt;
4189                 if (leftlen == 0) {
4190                         ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4191                         return totcnt;
4192                 }
4193                 advoffset += cplen;
4194                 curbuf += cnt;
4195         }
4196 #endif /* ADVANSYS_STATS */
4197
4198         /*
4199          * Display Asc Library dynamic configuration information
4200          * for the board.
4201          */
4202         cp = boardp->prtbuf;
4203         if (ASC_NARROW_BOARD(boardp)) {
4204                 cplen = asc_prt_asc_board_info(shost, cp, ASC_PRTBUF_SIZE);
4205         } else {
4206                 cplen = asc_prt_adv_board_info(shost, cp, ASC_PRTBUF_SIZE);
4207         }
4208         ASC_ASSERT(cplen < ASC_PRTBUF_SIZE);
4209         cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4210         totcnt += cnt;
4211         leftlen -= cnt;
4212         if (leftlen == 0) {
4213                 ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4214                 return totcnt;
4215         }
4216         advoffset += cplen;
4217         curbuf += cnt;
4218
4219         ASC_DBG1(1, "advansys_proc_info: totcnt %d\n", totcnt);
4220
4221         return totcnt;
4222 }
4223 #endif /* CONFIG_PROC_FS */
4224
4225 /*
4226  * advansys_info()
4227  *
4228  * Return suitable for printing on the console with the argument
4229  * adapter's configuration information.
4230  *
4231  * Note: The information line should not exceed ASC_INFO_SIZE bytes,
4232  * otherwise the static 'info' array will be overrun.
4233  */
4234 static const char *advansys_info(struct Scsi_Host *shost)
4235 {
4236         static char info[ASC_INFO_SIZE];
4237         asc_board_t *boardp;
4238         ASC_DVC_VAR *asc_dvc_varp;
4239         ADV_DVC_VAR *adv_dvc_varp;
4240         char *busname;
4241         int iolen;
4242         char *widename = NULL;
4243
4244         boardp = ASC_BOARDP(shost);
4245         if (ASC_NARROW_BOARD(boardp)) {
4246                 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
4247                 ASC_DBG(1, "advansys_info: begin\n");
4248                 if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
4249                         if ((asc_dvc_varp->bus_type & ASC_IS_ISAPNP) ==
4250                             ASC_IS_ISAPNP) {
4251                                 busname = "ISA PnP";
4252                         } else {
4253                                 busname = "ISA";
4254                         }
4255                         /* Don't reference 'shost->n_io_port'; It may be truncated. */
4256                         sprintf(info,
4257                                 "AdvanSys SCSI %s: %s: IO 0x%lX-0x%lX, IRQ 0x%X, DMA 0x%X",
4258                                 ASC_VERSION, busname,
4259                                 (ulong)shost->io_port,
4260                                 (ulong)shost->io_port + boardp->asc_n_io_port -
4261                                 1, shost->irq, shost->dma_channel);
4262                 } else {
4263                         if (asc_dvc_varp->bus_type & ASC_IS_VL) {
4264                                 busname = "VL";
4265                         } else if (asc_dvc_varp->bus_type & ASC_IS_EISA) {
4266                                 busname = "EISA";
4267                         } else if (asc_dvc_varp->bus_type & ASC_IS_PCI) {
4268                                 if ((asc_dvc_varp->bus_type & ASC_IS_PCI_ULTRA)
4269                                     == ASC_IS_PCI_ULTRA) {
4270                                         busname = "PCI Ultra";
4271                                 } else {
4272                                         busname = "PCI";
4273                                 }
4274                         } else {
4275                                 busname = "?";
4276                                 ASC_PRINT2
4277                                     ("advansys_info: board %d: unknown bus type %d\n",
4278                                      boardp->id, asc_dvc_varp->bus_type);
4279                         }
4280                         /* Don't reference 'shost->n_io_port'; It may be truncated. */
4281                         sprintf(info,
4282                                 "AdvanSys SCSI %s: %s: IO 0x%lX-0x%lX, IRQ 0x%X",
4283                                 ASC_VERSION, busname,
4284                                 (ulong)shost->io_port,
4285                                 (ulong)shost->io_port + boardp->asc_n_io_port -
4286                                 1, shost->irq);
4287                 }
4288         } else {
4289                 /*
4290                  * Wide Adapter Information
4291                  *
4292                  * Memory-mapped I/O is used instead of I/O space to access
4293                  * the adapter, but display the I/O Port range. The Memory
4294                  * I/O address is displayed through the driver /proc file.
4295                  */
4296                 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
4297                 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
4298                         iolen = ADV_3550_IOLEN;
4299                         widename = "Ultra-Wide";
4300                 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
4301                         iolen = ADV_38C0800_IOLEN;
4302                         widename = "Ultra2-Wide";
4303                 } else {
4304                         iolen = ADV_38C1600_IOLEN;
4305                         widename = "Ultra3-Wide";
4306                 }
4307                 sprintf(info,
4308                         "AdvanSys SCSI %s: PCI %s: PCIMEM 0x%lX-0x%lX, IRQ 0x%X",
4309                         ASC_VERSION, widename, (ulong)adv_dvc_varp->iop_base,
4310                         (ulong)adv_dvc_varp->iop_base + iolen - 1, shost->irq);
4311         }
4312         ASC_ASSERT(strlen(info) < ASC_INFO_SIZE);
4313         ASC_DBG(1, "advansys_info: end\n");
4314         return info;
4315 }
4316
4317 /*
4318  * advansys_queuecommand() - interrupt-driven I/O entrypoint.
4319  *
4320  * This function always returns 0. Command return status is saved
4321  * in the 'scp' result field.
4322  */
4323 static int
4324 advansys_queuecommand(struct scsi_cmnd *scp, void (*done) (struct scsi_cmnd *))
4325 {
4326         struct Scsi_Host *shost;
4327         asc_board_t *boardp;
4328         ulong flags;
4329         struct scsi_cmnd *done_scp;
4330
4331         shost = scp->device->host;
4332         boardp = ASC_BOARDP(shost);
4333         ASC_STATS(shost, queuecommand);
4334
4335         /* host_lock taken by mid-level prior to call but need to protect */
4336         /* against own ISR */
4337         spin_lock_irqsave(&boardp->lock, flags);
4338
4339         /*
4340          * Block new commands while handling a reset or abort request.
4341          */
4342         if (boardp->flags & ASC_HOST_IN_RESET) {
4343                 ASC_DBG1(1,
4344                          "advansys_queuecommand: scp 0x%lx blocked for reset request\n",
4345                          (ulong)scp);
4346                 scp->result = HOST_BYTE(DID_RESET);
4347
4348                 /*
4349                  * Add blocked requests to the board's 'done' queue. The queued
4350                  * requests will be completed at the end of the abort or reset
4351                  * handling.
4352                  */
4353                 asc_enqueue(&boardp->done, scp, ASC_BACK);
4354                 spin_unlock_irqrestore(&boardp->lock, flags);
4355                 return 0;
4356         }
4357
4358         /*
4359          * Attempt to execute any waiting commands for the board.
4360          */
4361         if (!ASC_QUEUE_EMPTY(&boardp->waiting)) {
4362                 ASC_DBG(1,
4363                         "advansys_queuecommand: before asc_execute_queue() waiting\n");
4364                 asc_execute_queue(&boardp->waiting);
4365         }
4366
4367         /*
4368          * Save the function pointer to Linux mid-level 'done' function
4369          * and attempt to execute the command.
4370          *
4371          * If ASC_NOERROR is returned the request has been added to the
4372          * board's 'active' queue and will be completed by the interrupt
4373          * handler.
4374          *
4375          * If ASC_BUSY is returned add the request to the board's per
4376          * target waiting list. This is the first time the request has
4377          * been tried. Add it to the back of the waiting list. It will be
4378          * retried later.
4379          *
4380          * If an error occurred, the request will have been placed on the
4381          * board's 'done' queue and must be completed before returning.
4382          */
4383         scp->scsi_done = done;
4384         switch (asc_execute_scsi_cmnd(scp)) {
4385         case ASC_NOERROR:
4386                 break;
4387         case ASC_BUSY:
4388                 asc_enqueue(&boardp->waiting, scp, ASC_BACK);
4389                 break;
4390         case ASC_ERROR:
4391         default:
4392                 done_scp = asc_dequeue_list(&boardp->done, NULL, ASC_TID_ALL);
4393                 /* Interrupts could be enabled here. */
4394                 asc_scsi_done_list(done_scp);
4395                 break;
4396         }
4397         spin_unlock_irqrestore(&boardp->lock, flags);
4398
4399         return 0;
4400 }
4401
4402 /*
4403  * advansys_reset()
4404  *
4405  * Reset the bus associated with the command 'scp'.
4406  *
4407  * This function runs its own thread. Interrupts must be blocked but
4408  * sleeping is allowed and no locking other than for host structures is
4409  * required. Returns SUCCESS or FAILED.
4410  */
4411 static int advansys_reset(struct scsi_cmnd *scp)
4412 {
4413         struct Scsi_Host *shost;
4414         asc_board_t *boardp;
4415         ASC_DVC_VAR *asc_dvc_varp;
4416         ADV_DVC_VAR *adv_dvc_varp;
4417         ulong flags;
4418         struct scsi_cmnd *done_scp = NULL, *last_scp = NULL;
4419         struct scsi_cmnd *tscp, *new_last_scp;
4420         int status;
4421         int ret = SUCCESS;
4422
4423         ASC_DBG1(1, "advansys_reset: 0x%lx\n", (ulong)scp);
4424
4425 #ifdef ADVANSYS_STATS
4426         if (scp->device->host != NULL) {
4427                 ASC_STATS(scp->device->host, reset);
4428         }
4429 #endif /* ADVANSYS_STATS */
4430
4431         if ((shost = scp->device->host) == NULL) {
4432                 scp->result = HOST_BYTE(DID_ERROR);
4433                 return FAILED;
4434         }
4435
4436         boardp = ASC_BOARDP(shost);
4437
4438         ASC_PRINT1("advansys_reset: board %d: SCSI bus reset started...\n",
4439                    boardp->id);
4440         /*
4441          * Check for re-entrancy.
4442          */
4443         spin_lock_irqsave(&boardp->lock, flags);
4444         if (boardp->flags & ASC_HOST_IN_RESET) {
4445                 spin_unlock_irqrestore(&boardp->lock, flags);
4446                 return FAILED;
4447         }
4448         boardp->flags |= ASC_HOST_IN_RESET;
4449         spin_unlock_irqrestore(&boardp->lock, flags);
4450
4451         if (ASC_NARROW_BOARD(boardp)) {
4452                 /*
4453                  * Narrow Board
4454                  */
4455                 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
4456
4457                 /*
4458                  * Reset the chip and SCSI bus.
4459                  */
4460                 ASC_DBG(1, "advansys_reset: before AscInitAsc1000Driver()\n");
4461                 status = AscInitAsc1000Driver(asc_dvc_varp);
4462
4463                 /* Refer to ASC_IERR_* defintions for meaning of 'err_code'. */
4464                 if (asc_dvc_varp->err_code) {
4465                         ASC_PRINT2
4466                             ("advansys_reset: board %d: SCSI bus reset error: 0x%x\n",
4467                              boardp->id, asc_dvc_varp->err_code);
4468                         ret = FAILED;
4469                 } else if (status) {
4470                         ASC_PRINT2
4471                             ("advansys_reset: board %d: SCSI bus reset warning: 0x%x\n",
4472                              boardp->id, status);
4473                 } else {
4474                         ASC_PRINT1
4475                             ("advansys_reset: board %d: SCSI bus reset successful.\n",
4476                              boardp->id);
4477                 }
4478
4479                 ASC_DBG(1, "advansys_reset: after AscInitAsc1000Driver()\n");
4480                 spin_lock_irqsave(&boardp->lock, flags);
4481
4482         } else {
4483                 /*
4484                  * Wide Board
4485                  *
4486                  * If the suggest reset bus flags are set, then reset the bus.
4487                  * Otherwise only reset the device.
4488                  */
4489                 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
4490
4491                 /*
4492                  * Reset the target's SCSI bus.
4493                  */
4494                 ASC_DBG(1, "advansys_reset: before AdvResetChipAndSB()\n");
4495                 switch (AdvResetChipAndSB(adv_dvc_varp)) {
4496                 case ASC_TRUE:
4497                         ASC_PRINT1
4498                             ("advansys_reset: board %d: SCSI bus reset successful.\n",
4499                              boardp->id);
4500                         break;
4501                 case ASC_FALSE:
4502                 default:
4503                         ASC_PRINT1
4504                             ("advansys_reset: board %d: SCSI bus reset error.\n",
4505                              boardp->id);
4506                         ret = FAILED;
4507                         break;
4508                 }
4509                 spin_lock_irqsave(&boardp->lock, flags);
4510                 (void)AdvISR(adv_dvc_varp);
4511         }
4512         /* Board lock is held. */
4513
4514         /*
4515          * Dequeue all board 'done' requests. A pointer to the last request
4516          * is returned in 'last_scp'.
4517          */
4518         done_scp = asc_dequeue_list(&boardp->done, &last_scp, ASC_TID_ALL);
4519
4520         /*
4521          * Dequeue all board 'active' requests for all devices and set
4522          * the request status to DID_RESET. A pointer to the last request
4523          * is returned in 'last_scp'.
4524          */
4525         if (done_scp == NULL) {
4526                 done_scp =
4527                     asc_dequeue_list(&boardp->active, &last_scp, ASC_TID_ALL);
4528                 for (tscp = done_scp; tscp; tscp = REQPNEXT(tscp)) {
4529                         tscp->result = HOST_BYTE(DID_RESET);
4530                 }
4531         } else {
4532                 /* Append to 'done_scp' at the end with 'last_scp'. */
4533                 ASC_ASSERT(last_scp != NULL);
4534                 last_scp->host_scribble =
4535                     (unsigned char *)asc_dequeue_list(&boardp->active,
4536                                                       &new_last_scp,
4537                                                       ASC_TID_ALL);
4538                 if (new_last_scp != NULL) {
4539                         ASC_ASSERT(REQPNEXT(last_scp) != NULL);
4540                         for (tscp = REQPNEXT(last_scp); tscp;
4541                              tscp = REQPNEXT(tscp)) {
4542                                 tscp->result = HOST_BYTE(DID_RESET);
4543                         }
4544                         last_scp = new_last_scp;
4545                 }
4546         }
4547
4548         /*
4549          * Dequeue all 'waiting' requests and set the request status
4550          * to DID_RESET.
4551          */
4552         if (done_scp == NULL) {
4553                 done_scp =
4554                     asc_dequeue_list(&boardp->waiting, &last_scp, ASC_TID_ALL);
4555                 for (tscp = done_scp; tscp; tscp = REQPNEXT(tscp)) {
4556                         tscp->result = HOST_BYTE(DID_RESET);
4557                 }
4558         } else {
4559                 /* Append to 'done_scp' at the end with 'last_scp'. */
4560                 ASC_ASSERT(last_scp != NULL);
4561                 last_scp->host_scribble =
4562                     (unsigned char *)asc_dequeue_list(&boardp->waiting,
4563                                                       &new_last_scp,
4564                                                       ASC_TID_ALL);
4565                 if (new_last_scp != NULL) {
4566                         ASC_ASSERT(REQPNEXT(last_scp) != NULL);
4567                         for (tscp = REQPNEXT(last_scp); tscp;
4568                              tscp = REQPNEXT(tscp)) {
4569                                 tscp->result = HOST_BYTE(DID_RESET);
4570                         }
4571                         last_scp = new_last_scp;
4572                 }
4573         }
4574
4575         /* Save the time of the most recently completed reset. */
4576         boardp->last_reset = jiffies;
4577
4578         /* Clear reset flag. */
4579         boardp->flags &= ~ASC_HOST_IN_RESET;
4580         spin_unlock_irqrestore(&boardp->lock, flags);
4581
4582         /*
4583          * Complete all the 'done_scp' requests.
4584          */
4585         if (done_scp != NULL) {
4586                 asc_scsi_done_list(done_scp);
4587         }
4588
4589         ASC_DBG1(1, "advansys_reset: ret %d\n", ret);
4590
4591         return ret;
4592 }
4593
4594 /*
4595  * advansys_biosparam()
4596  *
4597  * Translate disk drive geometry if the "BIOS greater than 1 GB"
4598  * support is enabled for a drive.
4599  *
4600  * ip (information pointer) is an int array with the following definition:
4601  * ip[0]: heads
4602  * ip[1]: sectors
4603  * ip[2]: cylinders
4604  */
4605 static int
4606 advansys_biosparam(struct scsi_device *sdev, struct block_device *bdev,
4607                    sector_t capacity, int ip[])
4608 {
4609         asc_board_t *boardp;
4610
4611         ASC_DBG(1, "advansys_biosparam: begin\n");
4612         ASC_STATS(sdev->host, biosparam);
4613         boardp = ASC_BOARDP(sdev->host);
4614         if (ASC_NARROW_BOARD(boardp)) {
4615                 if ((boardp->dvc_var.asc_dvc_var.dvc_cntl &
4616                      ASC_CNTL_BIOS_GT_1GB) && capacity > 0x200000) {
4617                         ip[0] = 255;
4618                         ip[1] = 63;
4619                 } else {
4620                         ip[0] = 64;
4621                         ip[1] = 32;
4622                 }
4623         } else {
4624                 if ((boardp->dvc_var.adv_dvc_var.bios_ctrl &
4625                      BIOS_CTRL_EXTENDED_XLAT) && capacity > 0x200000) {
4626                         ip[0] = 255;
4627                         ip[1] = 63;
4628                 } else {
4629                         ip[0] = 64;
4630                         ip[1] = 32;
4631                 }
4632         }
4633         ip[2] = (unsigned long)capacity / (ip[0] * ip[1]);
4634         ASC_DBG(1, "advansys_biosparam: end\n");
4635         return 0;
4636 }
4637
4638 static int __init advansys_detect(struct scsi_host_template *tpnt);
4639 static int advansys_release(struct Scsi_Host *shp);
4640
4641 static struct scsi_host_template driver_template = {
4642         .proc_name = "advansys",
4643 #ifdef CONFIG_PROC_FS
4644         .proc_info = advansys_proc_info,
4645 #endif
4646         .name = "advansys",
4647         .detect = advansys_detect,
4648         .release = advansys_release,
4649         .info = advansys_info,
4650         .queuecommand = advansys_queuecommand,
4651         .eh_bus_reset_handler = advansys_reset,
4652         .bios_param = advansys_biosparam,
4653         .slave_configure = advansys_slave_configure,
4654         /*
4655          * Because the driver may control an ISA adapter 'unchecked_isa_dma'
4656          * must be set. The flag will be cleared in advansys_detect for non-ISA
4657          * adapters. Refer to the comment in scsi_module.c for more information.
4658          */
4659         .unchecked_isa_dma = 1,
4660         /*
4661          * All adapters controlled by this driver are capable of large
4662          * scatter-gather lists. According to the mid-level SCSI documentation
4663          * this obviates any performance gain provided by setting
4664          * 'use_clustering'. But empirically while CPU utilization is increased
4665          * by enabling clustering, I/O throughput increases as well.
4666          */
4667         .use_clustering = ENABLE_CLUSTERING,
4668 };
4669
4670 #include "scsi_module.c"
4671
4672 /*
4673  * --- Miscellaneous Driver Functions
4674  */
4675
4676 /*
4677  * First-level interrupt handler.
4678  *
4679  * 'dev_id' is a pointer to the interrupting adapter's asc_board_t. Because
4680  * all boards are currently checked for interrupts on each interrupt, 'dev_id'
4681  * is not referenced. 'dev_id' could be used to identify an interrupt passed
4682  * to the AdvanSys driver which is for a device sharing an interrupt with
4683  * an AdvanSys adapter.
4684  */
4685 static irqreturn_t advansys_interrupt(int irq, void *dev_id)
4686 {
4687         ulong flags;
4688         int i;
4689         asc_board_t *boardp;
4690         struct scsi_cmnd *done_scp = NULL, *last_scp = NULL;
4691         struct scsi_cmnd *new_last_scp;
4692         struct Scsi_Host *shost;
4693
4694         ASC_DBG(1, "advansys_interrupt: begin\n");
4695
4696         /*
4697          * Check for interrupts on all boards.
4698          * AscISR() will call asc_isr_callback().
4699          */
4700         for (i = 0; i < asc_board_count; i++) {
4701                 shost = asc_host[i];
4702                 boardp = ASC_BOARDP(shost);
4703                 ASC_DBG2(2, "advansys_interrupt: i %d, boardp 0x%lx\n",
4704                          i, (ulong)boardp);
4705                 spin_lock_irqsave(&boardp->lock, flags);
4706                 if (ASC_NARROW_BOARD(boardp)) {
4707                         /*
4708                          * Narrow Board
4709                          */
4710                         if (AscIsIntPending(shost->io_port)) {
4711                                 ASC_STATS(shost, interrupt);
4712                                 ASC_DBG(1,
4713                                         "advansys_interrupt: before AscISR()\n");
4714                                 AscISR(&boardp->dvc_var.asc_dvc_var);
4715                         }
4716                 } else {
4717                         /*
4718                          * Wide Board
4719                          */
4720                         ASC_DBG(1, "advansys_interrupt: before AdvISR()\n");
4721                         if (AdvISR(&boardp->dvc_var.adv_dvc_var)) {
4722                                 ASC_STATS(shost, interrupt);
4723                         }
4724                 }
4725
4726                 /*
4727                  * Start waiting requests and create a list of completed requests.
4728                  *
4729                  * If a reset request is being performed for the board, the reset
4730                  * handler will complete pending requests after it has completed.
4731                  */
4732                 if ((boardp->flags & ASC_HOST_IN_RESET) == 0) {
4733                         ASC_DBG2(1,
4734                                  "advansys_interrupt: done_scp 0x%lx, last_scp 0x%lx\n",
4735                                  (ulong)done_scp, (ulong)last_scp);
4736
4737                         /* Start any waiting commands for the board. */
4738                         if (!ASC_QUEUE_EMPTY(&boardp->waiting)) {
4739                                 ASC_DBG(1,
4740                                         "advansys_interrupt: before asc_execute_queue()\n");
4741                                 asc_execute_queue(&boardp->waiting);
4742                         }
4743
4744                         /*
4745                          * Add to the list of requests that must be completed.
4746                          *
4747                          * 'done_scp' will always be NULL on the first iteration
4748                          * of this loop. 'last_scp' is set at the same time as
4749                          * 'done_scp'.
4750                          */
4751                         if (done_scp == NULL) {
4752                                 done_scp =
4753                                     asc_dequeue_list(&boardp->done, &last_scp,
4754                                                      ASC_TID_ALL);
4755                         } else {
4756                                 ASC_ASSERT(last_scp != NULL);
4757                                 last_scp->host_scribble =
4758                                     (unsigned char *)asc_dequeue_list(&boardp->
4759                                                                       done,
4760                                                                       &new_last_scp,
4761                                                                       ASC_TID_ALL);
4762                                 if (new_last_scp != NULL) {
4763                                         ASC_ASSERT(REQPNEXT(last_scp) != NULL);
4764                                         last_scp = new_last_scp;
4765                                 }
4766                         }
4767                 }
4768                 spin_unlock_irqrestore(&boardp->lock, flags);
4769         }
4770
4771         /*
4772          * If interrupts were enabled on entry, then they
4773          * are now enabled here.
4774          *
4775          * Complete all requests on the done list.
4776          */
4777
4778         asc_scsi_done_list(done_scp);
4779
4780         ASC_DBG(1, "advansys_interrupt: end\n");
4781         return IRQ_HANDLED;
4782 }
4783
4784 /*
4785  * Set the number of commands to queue per device for the
4786  * specified host adapter.
4787  */
4788 static int advansys_slave_configure(struct scsi_device *device)
4789 {
4790         asc_board_t *boardp;
4791
4792         boardp = ASC_BOARDP(device->host);
4793         boardp->flags |= ASC_SELECT_QUEUE_DEPTHS;
4794         /*
4795          * Save a pointer to the device and set its initial/maximum
4796          * queue depth.  Only save the pointer for a lun0 dev though.
4797          */
4798         if (device->lun == 0)
4799                 boardp->device[device->id] = device;
4800         if (device->tagged_supported) {
4801                 if (ASC_NARROW_BOARD(boardp)) {
4802                         scsi_adjust_queue_depth(device, MSG_ORDERED_TAG,
4803                                                 boardp->dvc_var.asc_dvc_var.
4804                                                 max_dvc_qng[device->id]);
4805                 } else {
4806                         scsi_adjust_queue_depth(device, MSG_ORDERED_TAG,
4807                                                 boardp->dvc_var.adv_dvc_var.
4808                                                 max_dvc_qng);
4809                 }
4810         } else {
4811                 scsi_adjust_queue_depth(device, 0, device->host->cmd_per_lun);
4812         }
4813         ASC_DBG4(1,
4814                  "advansys_slave_configure: device 0x%lx, boardp 0x%lx, id %d, depth %d\n",
4815                  (ulong)device, (ulong)boardp, device->id, device->queue_depth);
4816         return 0;
4817 }
4818
4819 /*
4820  * Complete all requests on the singly linked list pointed
4821  * to by 'scp'.
4822  *
4823  * Interrupts can be enabled on entry.
4824  */
4825 static void asc_scsi_done_list(struct scsi_cmnd *scp)
4826 {
4827         struct scsi_cmnd *tscp;
4828
4829         ASC_DBG(2, "asc_scsi_done_list: begin\n");
4830         while (scp != NULL) {
4831                 asc_board_t *boardp;
4832                 struct device *dev;
4833
4834                 ASC_DBG1(3, "asc_scsi_done_list: scp 0x%lx\n", (ulong)scp);
4835                 tscp = REQPNEXT(scp);
4836                 scp->host_scribble = NULL;
4837
4838                 boardp = ASC_BOARDP(scp->device->host);
4839
4840                 if (ASC_NARROW_BOARD(boardp))
4841                         dev = boardp->dvc_cfg.asc_dvc_cfg.dev;
4842                 else
4843                         dev = boardp->dvc_cfg.adv_dvc_cfg.dev;
4844
4845                 if (scp->use_sg)
4846                         dma_unmap_sg(dev,
4847                                      (struct scatterlist *)scp->request_buffer,
4848                                      scp->use_sg, scp->sc_data_direction);
4849                 else if (scp->request_bufflen)
4850                         dma_unmap_single(dev, scp->SCp.dma_handle,
4851                                          scp->request_bufflen,
4852                                          scp->sc_data_direction);
4853
4854                 ASC_STATS(scp->device->host, done);
4855                 ASC_ASSERT(scp->scsi_done != NULL);
4856
4857                 scp->scsi_done(scp);
4858
4859                 scp = tscp;
4860         }
4861         ASC_DBG(2, "asc_scsi_done_list: done\n");
4862         return;
4863 }
4864
4865 /*
4866  * Execute a single 'Scsi_Cmnd'.
4867  *
4868  * The function 'done' is called when the request has been completed.
4869  *
4870  * Scsi_Cmnd:
4871  *
4872  *  host - board controlling device
4873  *  device - device to send command
4874  *  target - target of device
4875  *  lun - lun of device
4876  *  cmd_len - length of SCSI CDB
4877  *  cmnd - buffer for SCSI 8, 10, or 12 byte CDB
4878  *  use_sg - if non-zero indicates scatter-gather request with use_sg elements
4879  *
4880  *  if (use_sg == 0) {
4881  *    request_buffer - buffer address for request
4882  *    request_bufflen - length of request buffer
4883  *  } else {
4884  *    request_buffer - pointer to scatterlist structure
4885  *  }
4886  *
4887  *  sense_buffer - sense command buffer
4888  *
4889  *  result (4 bytes of an int):
4890  *    Byte Meaning
4891  *    0 SCSI Status Byte Code
4892  *    1 SCSI One Byte Message Code
4893  *    2 Host Error Code
4894  *    3 Mid-Level Error Code
4895  *
4896  *  host driver fields:
4897  *    SCp - Scsi_Pointer used for command processing status
4898  *    scsi_done - used to save caller's done function
4899  *    host_scribble - used for pointer to another struct scsi_cmnd
4900  *
4901  * If this function returns ASC_NOERROR the request has been enqueued
4902  * on the board's 'active' queue and will be completed from the
4903  * interrupt handler.
4904  *
4905  * If this function returns ASC_NOERROR the request has been enqueued
4906  * on the board's 'done' queue and must be completed by the caller.
4907  *
4908  * If ASC_BUSY is returned the request will be enqueued by the
4909  * caller on the target's waiting queue and re-tried later.
4910  */
4911 static int asc_execute_scsi_cmnd(struct scsi_cmnd *scp)
4912 {
4913         asc_board_t *boardp;
4914         ASC_DVC_VAR *asc_dvc_varp;
4915         ADV_DVC_VAR *adv_dvc_varp;
4916         ADV_SCSI_REQ_Q *adv_scsiqp;
4917         struct scsi_device *device;
4918         int ret;
4919
4920         ASC_DBG2(1, "asc_execute_scsi_cmnd: scp 0x%lx, done 0x%lx\n",
4921                  (ulong)scp, (ulong)scp->scsi_done);
4922
4923         boardp = ASC_BOARDP(scp->device->host);
4924         device = boardp->device[scp->device->id];
4925
4926         if (ASC_NARROW_BOARD(boardp)) {
4927                 /*
4928                  * Build and execute Narrow Board request.
4929                  */
4930
4931                 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
4932
4933                 /*
4934                  * Build Asc Library request structure using the
4935                  * global structures 'asc_scsi_req' and 'asc_sg_head'.
4936                  *
4937                  * If an error is returned, then the request has been
4938                  * queued on the board done queue. It will be completed
4939                  * by the caller.
4940                  *
4941                  * asc_build_req() can not return ASC_BUSY.
4942                  */
4943                 if (asc_build_req(boardp, scp) == ASC_ERROR) {
4944                         ASC_STATS(scp->device->host, build_error);
4945                         return ASC_ERROR;
4946                 }
4947
4948                 /*
4949                  * Execute the command. If there is no error, add the command
4950                  * to the active queue.
4951                  */
4952                 switch (ret = AscExeScsiQueue(asc_dvc_varp, &asc_scsi_q)) {
4953                 case ASC_NOERROR:
4954                         ASC_STATS(scp->device->host, exe_noerror);
4955                         /*
4956                          * Increment monotonically increasing per device successful
4957                          * request counter. Wrapping doesn't matter.
4958                          */
4959                         boardp->reqcnt[scp->device->id]++;
4960                         asc_enqueue(&boardp->active, scp, ASC_BACK);
4961                         ASC_DBG(1,
4962                                 "asc_execute_scsi_cmnd: AscExeScsiQueue(), ASC_NOERROR\n");
4963                         break;
4964                 case ASC_BUSY:
4965                         /*
4966                          * Caller will enqueue request on the target's waiting queue
4967                          * and retry later.
4968                          */
4969                         ASC_STATS(scp->device->host, exe_busy);
4970                         break;
4971                 case ASC_ERROR:
4972                         ASC_PRINT2
4973                             ("asc_execute_scsi_cmnd: board %d: AscExeScsiQueue() ASC_ERROR, err_code 0x%x\n",
4974                              boardp->id, asc_dvc_varp->err_code);
4975                         ASC_STATS(scp->device->host, exe_error);
4976                         scp->result = HOST_BYTE(DID_ERROR);
4977                         asc_enqueue(&boardp->done, scp, ASC_BACK);
4978                         break;
4979                 default:
4980                         ASC_PRINT2
4981                             ("asc_execute_scsi_cmnd: board %d: AscExeScsiQueue() unknown, err_code 0x%x\n",
4982                              boardp->id, asc_dvc_varp->err_code);
4983                         ASC_STATS(scp->device->host, exe_unknown);
4984                         scp->result = HOST_BYTE(DID_ERROR);
4985                         asc_enqueue(&boardp->done, scp, ASC_BACK);
4986                         break;
4987                 }
4988         } else {
4989                 /*
4990                  * Build and execute Wide Board request.
4991                  */
4992                 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
4993
4994                 /*
4995                  * Build and get a pointer to an Adv Library request structure.
4996                  *
4997                  * If the request is successfully built then send it below,
4998                  * otherwise return with an error.
4999                  */
5000                 switch (adv_build_req(boardp, scp, &adv_scsiqp)) {
5001                 case ASC_NOERROR:
5002                         ASC_DBG(3,
5003                                 "asc_execute_scsi_cmnd: adv_build_req ASC_NOERROR\n");
5004                         break;
5005                 case ASC_BUSY:
5006                         ASC_DBG(1,
5007                                 "asc_execute_scsi_cmnd: adv_build_req ASC_BUSY\n");
5008                         /*
5009                          * If busy is returned the request has not been enqueued.
5010                          * It will be enqueued by the caller on the target's waiting
5011                          * queue and retried later.
5012                          *
5013                          * The asc_stats fields 'adv_build_noreq' and 'adv_build_nosg'
5014                          * count wide board busy conditions. They are updated in
5015                          * adv_build_req and adv_get_sglist, respectively.
5016                          */
5017                         return ASC_BUSY;
5018                 case ASC_ERROR:
5019                         /* 
5020                          * If an error is returned, then the request has been
5021                          * queued on the board done queue. It will be completed
5022                          * by the caller.
5023                          */
5024                 default:
5025                         ASC_DBG(1,
5026                                 "asc_execute_scsi_cmnd: adv_build_req ASC_ERROR\n");
5027                         ASC_STATS(scp->device->host, build_error);
5028                         return ASC_ERROR;
5029                 }
5030
5031                 /*
5032                  * Execute the command. If there is no error, add the command
5033                  * to the active queue.
5034                  */
5035                 switch (ret = AdvExeScsiQueue(adv_dvc_varp, adv_scsiqp)) {
5036                 case ASC_NOERROR:
5037                         ASC_STATS(scp->device->host, exe_noerror);
5038                         /*
5039                          * Increment monotonically increasing per device successful
5040                          * request counter. Wrapping doesn't matter.
5041                          */
5042                         boardp->reqcnt[scp->device->id]++;
5043                         asc_enqueue(&boardp->active, scp, ASC_BACK);
5044                         ASC_DBG(1,
5045                                 "asc_execute_scsi_cmnd: AdvExeScsiQueue(), ASC_NOERROR\n");
5046                         break;
5047                 case ASC_BUSY:
5048                         /*
5049                          * Caller will enqueue request on the target's waiting queue
5050                          * and retry later.
5051                          */
5052                         ASC_STATS(scp->device->host, exe_busy);
5053                         break;
5054                 case ASC_ERROR:
5055                         ASC_PRINT2
5056                             ("asc_execute_scsi_cmnd: board %d: AdvExeScsiQueue() ASC_ERROR, err_code 0x%x\n",
5057                              boardp->id, adv_dvc_varp->err_code);
5058                         ASC_STATS(scp->device->host, exe_error);
5059                         scp->result = HOST_BYTE(DID_ERROR);
5060                         asc_enqueue(&boardp->done, scp, ASC_BACK);
5061                         break;
5062                 default:
5063                         ASC_PRINT2
5064                             ("asc_execute_scsi_cmnd: board %d: AdvExeScsiQueue() unknown, err_code 0x%x\n",
5065                              boardp->id, adv_dvc_varp->err_code);
5066                         ASC_STATS(scp->device->host, exe_unknown);
5067                         scp->result = HOST_BYTE(DID_ERROR);
5068                         asc_enqueue(&boardp->done, scp, ASC_BACK);
5069                         break;
5070                 }
5071         }
5072
5073         ASC_DBG(1, "asc_execute_scsi_cmnd: end\n");
5074         return ret;
5075 }
5076
5077 /*
5078  * Build a request structure for the Asc Library (Narrow Board).
5079  *
5080  * The global structures 'asc_scsi_q' and 'asc_sg_head' are
5081  * used to build the request.
5082  *
5083  * If an error occurs, then queue the request on the board done
5084  * queue and return ASC_ERROR.
5085  */
5086 static int asc_build_req(asc_board_t *boardp, struct scsi_cmnd *scp)
5087 {
5088         struct device *dev = boardp->dvc_cfg.asc_dvc_cfg.dev;
5089
5090         /*
5091          * Mutually exclusive access is required to 'asc_scsi_q' and
5092          * 'asc_sg_head' until after the request is started.
5093          */
5094         memset(&asc_scsi_q, 0, sizeof(ASC_SCSI_Q));
5095
5096         /*
5097          * Point the ASC_SCSI_Q to the 'struct scsi_cmnd'.
5098          */
5099         asc_scsi_q.q2.srb_ptr = ASC_VADDR_TO_U32(scp);
5100
5101         /*
5102          * Build the ASC_SCSI_Q request.
5103          *
5104          * For narrow boards a CDB length maximum of 12 bytes
5105          * is supported.
5106          */
5107         if (scp->cmd_len > ASC_MAX_CDB_LEN) {
5108                 ASC_PRINT3
5109                     ("asc_build_req: board %d: cmd_len %d > ASC_MAX_CDB_LEN  %d\n",
5110                      boardp->id, scp->cmd_len, ASC_MAX_CDB_LEN);
5111                 scp->result = HOST_BYTE(DID_ERROR);
5112                 asc_enqueue(&boardp->done, scp, ASC_BACK);
5113                 return ASC_ERROR;
5114         }
5115         asc_scsi_q.cdbptr = &scp->cmnd[0];
5116         asc_scsi_q.q2.cdb_len = scp->cmd_len;
5117         asc_scsi_q.q1.target_id = ASC_TID_TO_TARGET_ID(scp->device->id);
5118         asc_scsi_q.q1.target_lun = scp->device->lun;
5119         asc_scsi_q.q2.target_ix =
5120             ASC_TIDLUN_TO_IX(scp->device->id, scp->device->lun);
5121         asc_scsi_q.q1.sense_addr =
5122             cpu_to_le32(virt_to_bus(&scp->sense_buffer[0]));
5123         asc_scsi_q.q1.sense_len = sizeof(scp->sense_buffer);
5124
5125         /*
5126          * If there are any outstanding requests for the current target,
5127          * then every 255th request send an ORDERED request. This heuristic
5128          * tries to retain the benefit of request sorting while preventing
5129          * request starvation. 255 is the max number of tags or pending commands
5130          * a device may have outstanding.
5131          *
5132          * The request count is incremented below for every successfully
5133          * started request.
5134          *
5135          */
5136         if ((boardp->dvc_var.asc_dvc_var.cur_dvc_qng[scp->device->id] > 0) &&
5137             (boardp->reqcnt[scp->device->id] % 255) == 0) {
5138                 asc_scsi_q.q2.tag_code = MSG_ORDERED_TAG;
5139         } else {
5140                 asc_scsi_q.q2.tag_code = MSG_SIMPLE_TAG;
5141         }
5142
5143         /*
5144          * Build ASC_SCSI_Q for a contiguous buffer or a scatter-gather
5145          * buffer command.
5146          */
5147         if (scp->use_sg == 0) {
5148                 /*
5149                  * CDB request of single contiguous buffer.
5150                  */
5151                 ASC_STATS(scp->device->host, cont_cnt);
5152                 scp->SCp.dma_handle = scp->request_bufflen ?
5153                     dma_map_single(dev, scp->request_buffer,
5154                                    scp->request_bufflen,
5155                                    scp->sc_data_direction) : 0;
5156                 asc_scsi_q.q1.data_addr = cpu_to_le32(scp->SCp.dma_handle);
5157                 asc_scsi_q.q1.data_cnt = cpu_to_le32(scp->request_bufflen);
5158                 ASC_STATS_ADD(scp->device->host, cont_xfer,
5159                               ASC_CEILING(scp->request_bufflen, 512));
5160                 asc_scsi_q.q1.sg_queue_cnt = 0;
5161                 asc_scsi_q.sg_head = NULL;
5162         } else {
5163                 /*
5164                  * CDB scatter-gather request list.
5165                  */
5166                 int sgcnt;
5167                 int use_sg;
5168                 struct scatterlist *slp;
5169
5170                 slp = (struct scatterlist *)scp->request_buffer;
5171                 use_sg =
5172                     dma_map_sg(dev, slp, scp->use_sg, scp->sc_data_direction);
5173
5174                 if (use_sg > scp->device->host->sg_tablesize) {
5175                         ASC_PRINT3
5176                             ("asc_build_req: board %d: use_sg %d > sg_tablesize %d\n",
5177                              boardp->id, use_sg,
5178                              scp->device->host->sg_tablesize);
5179                         dma_unmap_sg(dev, slp, scp->use_sg,
5180                                      scp->sc_data_direction);
5181                         scp->result = HOST_BYTE(DID_ERROR);
5182                         asc_enqueue(&boardp->done, scp, ASC_BACK);
5183                         return ASC_ERROR;
5184                 }
5185
5186                 ASC_STATS(scp->device->host, sg_cnt);
5187
5188                 /*
5189                  * Use global ASC_SG_HEAD structure and set the ASC_SCSI_Q
5190                  * structure to point to it.
5191                  */
5192                 memset(&asc_sg_head, 0, sizeof(ASC_SG_HEAD));
5193
5194                 asc_scsi_q.q1.cntl |= QC_SG_HEAD;
5195                 asc_scsi_q.sg_head = &asc_sg_head;
5196                 asc_scsi_q.q1.data_cnt = 0;
5197                 asc_scsi_q.q1.data_addr = 0;
5198                 /* This is a byte value, otherwise it would need to be swapped. */
5199                 asc_sg_head.entry_cnt = asc_scsi_q.q1.sg_queue_cnt = use_sg;
5200                 ASC_STATS_ADD(scp->device->host, sg_elem,
5201                               asc_sg_head.entry_cnt);
5202
5203                 /*
5204                  * Convert scatter-gather list into ASC_SG_HEAD list.
5205                  */
5206                 for (sgcnt = 0; sgcnt < use_sg; sgcnt++, slp++) {
5207                         asc_sg_head.sg_list[sgcnt].addr =
5208                             cpu_to_le32(sg_dma_address(slp));
5209                         asc_sg_head.sg_list[sgcnt].bytes =
5210                             cpu_to_le32(sg_dma_len(slp));
5211                         ASC_STATS_ADD(scp->device->host, sg_xfer,
5212                                       ASC_CEILING(sg_dma_len(slp), 512));
5213                 }
5214         }
5215
5216         ASC_DBG_PRT_ASC_SCSI_Q(2, &asc_scsi_q);
5217         ASC_DBG_PRT_CDB(1, scp->cmnd, scp->cmd_len);
5218
5219         return ASC_NOERROR;
5220 }
5221
5222 /*
5223  * Build a request structure for the Adv Library (Wide Board).
5224  *
5225  * If an adv_req_t can not be allocated to issue the request,
5226  * then return ASC_BUSY. If an error occurs, then return ASC_ERROR.
5227  *
5228  * Multi-byte fields in the ASC_SCSI_REQ_Q that are used by the
5229  * microcode for DMA addresses or math operations are byte swapped
5230  * to little-endian order.
5231  */
5232 static int
5233 adv_build_req(asc_board_t *boardp, struct scsi_cmnd *scp,
5234               ADV_SCSI_REQ_Q **adv_scsiqpp)
5235 {
5236         adv_req_t *reqp;
5237         ADV_SCSI_REQ_Q *scsiqp;
5238         int i;
5239         int ret;
5240         struct device *dev = boardp->dvc_cfg.adv_dvc_cfg.dev;
5241
5242         /*
5243          * Allocate an adv_req_t structure from the board to execute
5244          * the command.
5245          */
5246         if (boardp->adv_reqp == NULL) {
5247                 ASC_DBG(1, "adv_build_req: no free adv_req_t\n");
5248                 ASC_STATS(scp->device->host, adv_build_noreq);
5249                 return ASC_BUSY;
5250         } else {
5251                 reqp = boardp->adv_reqp;
5252                 boardp->adv_reqp = reqp->next_reqp;
5253                 reqp->next_reqp = NULL;
5254         }
5255
5256         /*
5257          * Get 32-byte aligned ADV_SCSI_REQ_Q and ADV_SG_BLOCK pointers.
5258          */
5259         scsiqp = (ADV_SCSI_REQ_Q *)ADV_32BALIGN(&reqp->scsi_req_q);
5260
5261         /*
5262          * Initialize the structure.
5263          */
5264         scsiqp->cntl = scsiqp->scsi_cntl = scsiqp->done_status = 0;
5265
5266         /*
5267          * Set the ADV_SCSI_REQ_Q 'srb_ptr' to point to the adv_req_t structure.
5268          */
5269         scsiqp->srb_ptr = ASC_VADDR_TO_U32(reqp);
5270
5271         /*
5272          * Set the adv_req_t 'cmndp' to point to the struct scsi_cmnd structure.
5273          */
5274         reqp->cmndp = scp;
5275
5276         /*
5277          * Build the ADV_SCSI_REQ_Q request.
5278          */
5279
5280         /*
5281          * Set CDB length and copy it to the request structure.
5282          * For wide  boards a CDB length maximum of 16 bytes
5283          * is supported.
5284          */
5285         if (scp->cmd_len > ADV_MAX_CDB_LEN) {
5286                 ASC_PRINT3
5287                     ("adv_build_req: board %d: cmd_len %d > ADV_MAX_CDB_LEN  %d\n",
5288                      boardp->id, scp->cmd_len, ADV_MAX_CDB_LEN);
5289                 scp->result = HOST_BYTE(DID_ERROR);
5290                 asc_enqueue(&boardp->done, scp, ASC_BACK);
5291                 return ASC_ERROR;
5292         }
5293         scsiqp->cdb_len = scp->cmd_len;
5294         /* Copy first 12 CDB bytes to cdb[]. */
5295         for (i = 0; i < scp->cmd_len && i < 12; i++) {
5296                 scsiqp->cdb[i] = scp->cmnd[i];
5297         }
5298         /* Copy last 4 CDB bytes, if present, to cdb16[]. */
5299         for (; i < scp->cmd_len; i++) {
5300                 scsiqp->cdb16[i - 12] = scp->cmnd[i];
5301         }
5302
5303         scsiqp->target_id = scp->device->id;
5304         scsiqp->target_lun = scp->device->lun;
5305
5306         scsiqp->sense_addr = cpu_to_le32(virt_to_bus(&scp->sense_buffer[0]));
5307         scsiqp->sense_len = sizeof(scp->sense_buffer);
5308
5309         /*
5310          * Build ADV_SCSI_REQ_Q for a contiguous buffer or a scatter-gather
5311          * buffer command.
5312          */
5313
5314         scsiqp->data_cnt = cpu_to_le32(scp->request_bufflen);
5315         scsiqp->vdata_addr = scp->request_buffer;
5316         scsiqp->data_addr = cpu_to_le32(virt_to_bus(scp->request_buffer));
5317
5318         if (scp->use_sg == 0) {
5319                 /*
5320                  * CDB request of single contiguous buffer.
5321                  */
5322                 reqp->sgblkp = NULL;
5323                 scsiqp->data_cnt = cpu_to_le32(scp->request_bufflen);
5324                 if (scp->request_bufflen) {
5325                         scsiqp->vdata_addr = scp->request_buffer;
5326                         scp->SCp.dma_handle =
5327                             dma_map_single(dev, scp->request_buffer,
5328                                            scp->request_bufflen,
5329                                            scp->sc_data_direction);
5330                 } else {
5331                         scsiqp->vdata_addr = NULL;
5332                         scp->SCp.dma_handle = 0;
5333                 }
5334                 scsiqp->data_addr = cpu_to_le32(scp->SCp.dma_handle);
5335                 scsiqp->sg_list_ptr = NULL;
5336                 scsiqp->sg_real_addr = 0;
5337                 ASC_STATS(scp->device->host, cont_cnt);
5338                 ASC_STATS_ADD(scp->device->host, cont_xfer,
5339                               ASC_CEILING(scp->request_bufflen, 512));
5340         } else {
5341                 /*
5342                  * CDB scatter-gather request list.
5343                  */
5344                 struct scatterlist *slp;
5345                 int use_sg;
5346
5347                 slp = (struct scatterlist *)scp->request_buffer;
5348                 use_sg =
5349                     dma_map_sg(dev, slp, scp->use_sg, scp->sc_data_direction);
5350
5351                 if (use_sg > ADV_MAX_SG_LIST) {
5352                         ASC_PRINT3
5353                             ("adv_build_req: board %d: use_sg %d > ADV_MAX_SG_LIST %d\n",
5354                              boardp->id, use_sg,
5355                              scp->device->host->sg_tablesize);
5356                         dma_unmap_sg(dev, slp, scp->use_sg,
5357                                      scp->sc_data_direction);
5358                         scp->result = HOST_BYTE(DID_ERROR);
5359                         asc_enqueue(&boardp->done, scp, ASC_BACK);
5360
5361                         /*
5362                          * Free the 'adv_req_t' structure by adding it back to the
5363                          * board free list.
5364                          */
5365                         reqp->next_reqp = boardp->adv_reqp;
5366                         boardp->adv_reqp = reqp;
5367
5368                         return ASC_ERROR;
5369                 }
5370
5371                 if ((ret =
5372                      adv_get_sglist(boardp, reqp, scp,
5373                                     use_sg)) != ADV_SUCCESS) {
5374                         /*
5375                          * Free the adv_req_t structure by adding it back to the
5376                          * board free list.
5377                          */
5378                         reqp->next_reqp = boardp->adv_reqp;
5379                         boardp->adv_reqp = reqp;
5380
5381                         return ret;
5382                 }
5383
5384                 ASC_STATS(scp->device->host, sg_cnt);
5385                 ASC_STATS_ADD(scp->device->host, sg_elem, use_sg);
5386         }
5387
5388         ASC_DBG_PRT_ADV_SCSI_REQ_Q(2, scsiqp);
5389         ASC_DBG_PRT_CDB(1, scp->cmnd, scp->cmd_len);
5390
5391         *adv_scsiqpp = scsiqp;
5392
5393         return ASC_NOERROR;
5394 }
5395
5396 /*
5397  * Build scatter-gather list for Adv Library (Wide Board).
5398  *
5399  * Additional ADV_SG_BLOCK structures will need to be allocated
5400  * if the total number of scatter-gather elements exceeds
5401  * NO_OF_SG_PER_BLOCK (15). The ADV_SG_BLOCK structures are
5402  * assumed to be physically contiguous.
5403  *
5404  * Return:
5405  *      ADV_SUCCESS(1) - SG List successfully created
5406  *      ADV_ERROR(-1) - SG List creation failed
5407  */
5408 static int
5409 adv_get_sglist(asc_board_t *boardp, adv_req_t *reqp, struct scsi_cmnd *scp,
5410                int use_sg)
5411 {
5412         adv_sgblk_t *sgblkp;
5413         ADV_SCSI_REQ_Q *scsiqp;
5414         struct scatterlist *slp;
5415         int sg_elem_cnt;
5416         ADV_SG_BLOCK *sg_block, *prev_sg_block;
5417         ADV_PADDR sg_block_paddr;
5418         int i;
5419
5420         scsiqp = (ADV_SCSI_REQ_Q *)ADV_32BALIGN(&reqp->scsi_req_q);
5421         slp = (struct scatterlist *)scp->request_buffer;
5422         sg_elem_cnt = use_sg;
5423         prev_sg_block = NULL;
5424         reqp->sgblkp = NULL;
5425
5426         do {
5427                 /*
5428                  * Allocate a 'adv_sgblk_t' structure from the board free
5429                  * list. One 'adv_sgblk_t' structure holds NO_OF_SG_PER_BLOCK
5430                  * (15) scatter-gather elements.
5431                  */
5432                 if ((sgblkp = boardp->adv_sgblkp) == NULL) {
5433                         ASC_DBG(1, "adv_get_sglist: no free adv_sgblk_t\n");
5434                         ASC_STATS(scp->device->host, adv_build_nosg);
5435
5436                         /*
5437                          * Allocation failed. Free 'adv_sgblk_t' structures already
5438                          * allocated for the request.
5439                          */
5440                         while ((sgblkp = reqp->sgblkp) != NULL) {
5441                                 /* Remove 'sgblkp' from the request list. */
5442                                 reqp->sgblkp = sgblkp->next_sgblkp;
5443
5444                                 /* Add 'sgblkp' to the board free list. */
5445                                 sgblkp->next_sgblkp = boardp->adv_sgblkp;
5446                                 boardp->adv_sgblkp = sgblkp;
5447                         }
5448                         return ASC_BUSY;
5449                 } else {
5450                         /* Complete 'adv_sgblk_t' board allocation. */
5451                         boardp->adv_sgblkp = sgblkp->next_sgblkp;
5452                         sgblkp->next_sgblkp = NULL;
5453
5454                         /*
5455                          * Get 8 byte aligned virtual and physical addresses for
5456                          * the allocated ADV_SG_BLOCK structure.
5457                          */
5458                         sg_block =
5459                             (ADV_SG_BLOCK *)ADV_8BALIGN(&sgblkp->sg_block);
5460                         sg_block_paddr = virt_to_bus(sg_block);
5461
5462                         /*
5463                          * Check if this is the first 'adv_sgblk_t' for the request.
5464                          */
5465                         if (reqp->sgblkp == NULL) {
5466                                 /* Request's first scatter-gather block. */
5467                                 reqp->sgblkp = sgblkp;
5468
5469                                 /*
5470                                  * Set ADV_SCSI_REQ_T ADV_SG_BLOCK virtual and physical
5471                                  * address pointers.
5472                                  */
5473                                 scsiqp->sg_list_ptr = sg_block;
5474                                 scsiqp->sg_real_addr =
5475                                     cpu_to_le32(sg_block_paddr);
5476                         } else {
5477                                 /* Request's second or later scatter-gather block. */
5478                                 sgblkp->next_sgblkp = reqp->sgblkp;
5479                                 reqp->sgblkp = sgblkp;
5480
5481                                 /*
5482                                  * Point the previous ADV_SG_BLOCK structure to
5483                                  * the newly allocated ADV_SG_BLOCK structure.
5484                                  */
5485                                 ASC_ASSERT(prev_sg_block != NULL);
5486                                 prev_sg_block->sg_ptr =
5487                                     cpu_to_le32(sg_block_paddr);
5488                         }
5489                 }
5490
5491                 for (i = 0; i < NO_OF_SG_PER_BLOCK; i++) {
5492                         sg_block->sg_list[i].sg_addr =
5493                             cpu_to_le32(sg_dma_address(slp));
5494                         sg_block->sg_list[i].sg_count =
5495                             cpu_to_le32(sg_dma_len(slp));
5496                         ASC_STATS_ADD(scp->device->host, sg_xfer,
5497                                       ASC_CEILING(sg_dma_len(slp), 512));
5498
5499                         if (--sg_elem_cnt == 0) {       /* Last ADV_SG_BLOCK and scatter-gather entry. */
5500                                 sg_block->sg_cnt = i + 1;
5501                                 sg_block->sg_ptr = 0L;  /* Last ADV_SG_BLOCK in list. */
5502                                 return ADV_SUCCESS;
5503                         }
5504                         slp++;
5505                 }
5506                 sg_block->sg_cnt = NO_OF_SG_PER_BLOCK;
5507                 prev_sg_block = sg_block;
5508         }
5509         while (1);
5510         /* NOTREACHED */
5511 }
5512
5513 /*
5514  * asc_isr_callback() - Second Level Interrupt Handler called by AscISR().
5515  *
5516  * Interrupt callback function for the Narrow SCSI Asc Library.
5517  */
5518 static void asc_isr_callback(ASC_DVC_VAR *asc_dvc_varp, ASC_QDONE_INFO *qdonep)
5519 {
5520         asc_board_t *boardp;
5521         struct scsi_cmnd *scp;
5522         struct Scsi_Host *shost;
5523         int i;
5524
5525         ASC_DBG2(1, "asc_isr_callback: asc_dvc_varp 0x%lx, qdonep 0x%lx\n",
5526                  (ulong)asc_dvc_varp, (ulong)qdonep);
5527         ASC_DBG_PRT_ASC_QDONE_INFO(2, qdonep);
5528
5529         /*
5530          * Get the struct scsi_cmnd structure and Scsi_Host structure for the
5531          * command that has been completed.
5532          */
5533         scp = (struct scsi_cmnd *)ASC_U32_TO_VADDR(qdonep->d2.srb_ptr);
5534         ASC_DBG1(1, "asc_isr_callback: scp 0x%lx\n", (ulong)scp);
5535
5536         if (scp == NULL) {
5537                 ASC_PRINT("asc_isr_callback: scp is NULL\n");
5538                 return;
5539         }
5540         ASC_DBG_PRT_CDB(2, scp->cmnd, scp->cmd_len);
5541
5542         /*
5543          * If the request's host pointer is not valid, display a
5544          * message and return.
5545          */
5546         shost = scp->device->host;
5547         for (i = 0; i < asc_board_count; i++) {
5548                 if (asc_host[i] == shost) {
5549                         break;
5550                 }
5551         }
5552         if (i == asc_board_count) {
5553                 ASC_PRINT2
5554                     ("asc_isr_callback: scp 0x%lx has bad host pointer, host 0x%lx\n",
5555                      (ulong)scp, (ulong)shost);
5556                 return;
5557         }
5558
5559         ASC_STATS(shost, callback);
5560         ASC_DBG1(1, "asc_isr_callback: shost 0x%lx\n", (ulong)shost);
5561
5562         /*
5563          * If the request isn't found on the active queue, it may
5564          * have been removed to handle a reset request.
5565          * Display a message and return.
5566          */
5567         boardp = ASC_BOARDP(shost);
5568         ASC_ASSERT(asc_dvc_varp == &boardp->dvc_var.asc_dvc_var);
5569         if (asc_rmqueue(&boardp->active, scp) == ASC_FALSE) {
5570                 ASC_PRINT2
5571                     ("asc_isr_callback: board %d: scp 0x%lx not on active queue\n",
5572                      boardp->id, (ulong)scp);
5573                 return;
5574         }
5575
5576         /*
5577          * 'qdonep' contains the command's ending status.
5578          */
5579         switch (qdonep->d3.done_stat) {
5580         case QD_NO_ERROR:
5581                 ASC_DBG(2, "asc_isr_callback: QD_NO_ERROR\n");
5582                 scp->result = 0;
5583
5584                 /*
5585                  * If an INQUIRY command completed successfully, then call
5586                  * the AscInquiryHandling() function to set-up the device.
5587                  */
5588                 if (scp->cmnd[0] == INQUIRY && scp->device->lun == 0 &&
5589                     (scp->request_bufflen - qdonep->remain_bytes) >= 8) {
5590                         AscInquiryHandling(asc_dvc_varp, scp->device->id & 0x7,
5591                                            (ASC_SCSI_INQUIRY *)scp->
5592                                            request_buffer);
5593                 }
5594
5595                 /*
5596                  * Check for an underrun condition.
5597                  *
5598                  * If there was no error and an underrun condition, then
5599                  * then return the number of underrun bytes.
5600                  */
5601                 if (scp->request_bufflen != 0 && qdonep->remain_bytes != 0 &&
5602                     qdonep->remain_bytes <= scp->request_bufflen) {
5603                         ASC_DBG1(1,
5604                                  "asc_isr_callback: underrun condition %u bytes\n",
5605                                  (unsigned)qdonep->remain_bytes);
5606                         scp->resid = qdonep->remain_bytes;
5607                 }
5608                 break;
5609
5610         case QD_WITH_ERROR:
5611                 ASC_DBG(2, "asc_isr_callback: QD_WITH_ERROR\n");
5612                 switch (qdonep->d3.host_stat) {
5613                 case QHSTA_NO_ERROR:
5614                         if (qdonep->d3.scsi_stat == SAM_STAT_CHECK_CONDITION) {
5615                                 ASC_DBG(2,
5616                                         "asc_isr_callback: SAM_STAT_CHECK_CONDITION\n");
5617                                 ASC_DBG_PRT_SENSE(2, scp->sense_buffer,
5618                                                   sizeof(scp->sense_buffer));
5619                                 /*
5620                                  * Note: The 'status_byte()' macro used by target drivers
5621                                  * defined in scsi.h shifts the status byte returned by
5622                                  * host drivers right by 1 bit. This is why target drivers
5623                                  * also use right shifted status byte definitions. For
5624                                  * instance target drivers use CHECK_CONDITION, defined to
5625                                  * 0x1, instead of the SCSI defined check condition value
5626                                  * of 0x2. Host drivers are supposed to return the status
5627                                  * byte as it is defined by SCSI.
5628                                  */
5629                                 scp->result = DRIVER_BYTE(DRIVER_SENSE) |
5630                                     STATUS_BYTE(qdonep->d3.scsi_stat);
5631                         } else {
5632                                 scp->result = STATUS_BYTE(qdonep->d3.scsi_stat);
5633                         }
5634                         break;
5635
5636                 default:
5637                         /* QHSTA error occurred */
5638                         ASC_DBG1(1, "asc_isr_callback: host_stat 0x%x\n",
5639                                  qdonep->d3.host_stat);
5640                         scp->result = HOST_BYTE(DID_BAD_TARGET);
5641                         break;
5642                 }
5643                 break;
5644
5645         case QD_ABORTED_BY_HOST:
5646                 ASC_DBG(1, "asc_isr_callback: QD_ABORTED_BY_HOST\n");
5647                 scp->result =
5648                     HOST_BYTE(DID_ABORT) | MSG_BYTE(qdonep->d3.
5649                                                     scsi_msg) |
5650                     STATUS_BYTE(qdonep->d3.scsi_stat);
5651                 break;
5652
5653         default:
5654                 ASC_DBG1(1, "asc_isr_callback: done_stat 0x%x\n",
5655                          qdonep->d3.done_stat);
5656                 scp->result =
5657                     HOST_BYTE(DID_ERROR) | MSG_BYTE(qdonep->d3.
5658                                                     scsi_msg) |
5659                     STATUS_BYTE(qdonep->d3.scsi_stat);
5660                 break;
5661         }
5662
5663         /*
5664          * If the 'init_tidmask' bit isn't already set for the target and the
5665          * current request finished normally, then set the bit for the target
5666          * to indicate that a device is present.
5667          */
5668         if ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(scp->device->id)) == 0 &&
5669             qdonep->d3.done_stat == QD_NO_ERROR &&
5670             qdonep->d3.host_stat == QHSTA_NO_ERROR) {
5671                 boardp->init_tidmask |= ADV_TID_TO_TIDMASK(scp->device->id);
5672         }
5673
5674         /*
5675          * Because interrupts may be enabled by the 'struct scsi_cmnd' done
5676          * function, add the command to the end of the board's done queue.
5677          * The done function for the command will be called from
5678          * advansys_interrupt().
5679          */
5680         asc_enqueue(&boardp->done, scp, ASC_BACK);
5681
5682         return;
5683 }
5684
5685 /*
5686  * adv_isr_callback() - Second Level Interrupt Handler called by AdvISR().
5687  *
5688  * Callback function for the Wide SCSI Adv Library.
5689  */
5690 static void adv_isr_callback(ADV_DVC_VAR *adv_dvc_varp, ADV_SCSI_REQ_Q *scsiqp)
5691 {
5692         asc_board_t *boardp;
5693         adv_req_t *reqp;
5694         adv_sgblk_t *sgblkp;
5695         struct scsi_cmnd *scp;
5696         struct Scsi_Host *shost;
5697         int i;
5698         ADV_DCNT resid_cnt;
5699
5700         ASC_DBG2(1, "adv_isr_callback: adv_dvc_varp 0x%lx, scsiqp 0x%lx\n",
5701                  (ulong)adv_dvc_varp, (ulong)scsiqp);
5702         ASC_DBG_PRT_ADV_SCSI_REQ_Q(2, scsiqp);
5703
5704         /*
5705          * Get the adv_req_t structure for the command that has been
5706          * completed. The adv_req_t structure actually contains the
5707          * completed ADV_SCSI_REQ_Q structure.
5708          */
5709         reqp = (adv_req_t *)ADV_U32_TO_VADDR(scsiqp->srb_ptr);
5710         ASC_DBG1(1, "adv_isr_callback: reqp 0x%lx\n", (ulong)reqp);
5711         if (reqp == NULL) {
5712                 ASC_PRINT("adv_isr_callback: reqp is NULL\n");
5713                 return;
5714         }
5715
5716         /*
5717          * Get the struct scsi_cmnd structure and Scsi_Host structure for the
5718          * command that has been completed.
5719          *
5720          * Note: The adv_req_t request structure and adv_sgblk_t structure,
5721          * if any, are dropped, because a board structure pointer can not be
5722          * determined.
5723          */
5724         scp = reqp->cmndp;
5725         ASC_DBG1(1, "adv_isr_callback: scp 0x%lx\n", (ulong)scp);
5726         if (scp == NULL) {
5727                 ASC_PRINT
5728                     ("adv_isr_callback: scp is NULL; adv_req_t dropped.\n");
5729                 return;
5730         }
5731         ASC_DBG_PRT_CDB(2, scp->cmnd, scp->cmd_len);
5732
5733         /*
5734          * If the request's host pointer is not valid, display a message
5735          * and return.
5736          */
5737         shost = scp->device->host;
5738         for (i = 0; i < asc_board_count; i++) {
5739                 if (asc_host[i] == shost) {
5740                         break;
5741                 }
5742         }
5743         /*
5744          * Note: If the host structure is not found, the adv_req_t request
5745          * structure and adv_sgblk_t structure, if any, is dropped.
5746          */
5747         if (i == asc_board_count) {
5748                 ASC_PRINT2
5749                     ("adv_isr_callback: scp 0x%lx has bad host pointer, host 0x%lx\n",
5750                      (ulong)scp, (ulong)shost);
5751                 return;
5752         }
5753
5754         ASC_STATS(shost, callback);
5755         ASC_DBG1(1, "adv_isr_callback: shost 0x%lx\n", (ulong)shost);
5756
5757         /*
5758          * If the request isn't found on the active queue, it may have been
5759          * removed to handle a reset request. Display a message and return.
5760          *
5761          * Note: Because the structure may still be in use don't attempt
5762          * to free the adv_req_t and adv_sgblk_t, if any, structures.
5763          */
5764         boardp = ASC_BOARDP(shost);
5765         ASC_ASSERT(adv_dvc_varp == &boardp->dvc_var.adv_dvc_var);
5766         if (asc_rmqueue(&boardp->active, scp) == ASC_FALSE) {
5767                 ASC_PRINT2
5768                     ("adv_isr_callback: board %d: scp 0x%lx not on active queue\n",
5769                      boardp->id, (ulong)scp);
5770                 return;
5771         }
5772
5773         /*
5774          * 'done_status' contains the command's ending status.
5775          */
5776         switch (scsiqp->done_status) {
5777         case QD_NO_ERROR:
5778                 ASC_DBG(2, "adv_isr_callback: QD_NO_ERROR\n");
5779                 scp->result = 0;
5780
5781                 /*
5782                  * Check for an underrun condition.
5783                  *
5784                  * If there was no error and an underrun condition, then
5785                  * then return the number of underrun bytes.
5786                  */
5787                 resid_cnt = le32_to_cpu(scsiqp->data_cnt);
5788                 if (scp->request_bufflen != 0 && resid_cnt != 0 &&
5789                     resid_cnt <= scp->request_bufflen) {
5790                         ASC_DBG1(1,
5791                                  "adv_isr_callback: underrun condition %lu bytes\n",
5792                                  (ulong)resid_cnt);
5793                         scp->resid = resid_cnt;
5794                 }
5795                 break;
5796
5797         case QD_WITH_ERROR:
5798                 ASC_DBG(2, "adv_isr_callback: QD_WITH_ERROR\n");
5799                 switch (scsiqp->host_status) {
5800                 case QHSTA_NO_ERROR:
5801                         if (scsiqp->scsi_status == SAM_STAT_CHECK_CONDITION) {
5802                                 ASC_DBG(2,
5803                                         "adv_isr_callback: SAM_STAT_CHECK_CONDITION\n");
5804                                 ASC_DBG_PRT_SENSE(2, scp->sense_buffer,
5805                                                   sizeof(scp->sense_buffer));
5806                                 /*
5807                                  * Note: The 'status_byte()' macro used by target drivers
5808                                  * defined in scsi.h shifts the status byte returned by
5809                                  * host drivers right by 1 bit. This is why target drivers
5810                                  * also use right shifted status byte definitions. For
5811                                  * instance target drivers use CHECK_CONDITION, defined to
5812                                  * 0x1, instead of the SCSI defined check condition value
5813                                  * of 0x2. Host drivers are supposed to return the status
5814                                  * byte as it is defined by SCSI.
5815                                  */
5816                                 scp->result = DRIVER_BYTE(DRIVER_SENSE) |
5817                                     STATUS_BYTE(scsiqp->scsi_status);
5818                         } else {
5819                                 scp->result = STATUS_BYTE(scsiqp->scsi_status);
5820                         }
5821                         break;
5822
5823                 default:
5824                         /* Some other QHSTA error occurred. */
5825                         ASC_DBG1(1, "adv_isr_callback: host_status 0x%x\n",
5826                                  scsiqp->host_status);
5827                         scp->result = HOST_BYTE(DID_BAD_TARGET);
5828                         break;
5829                 }
5830                 break;
5831
5832         case QD_ABORTED_BY_HOST:
5833                 ASC_DBG(1, "adv_isr_callback: QD_ABORTED_BY_HOST\n");
5834                 scp->result =
5835                     HOST_BYTE(DID_ABORT) | STATUS_BYTE(scsiqp->scsi_status);
5836                 break;
5837
5838         default:
5839                 ASC_DBG1(1, "adv_isr_callback: done_status 0x%x\n",
5840                          scsiqp->done_status);
5841                 scp->result =
5842                     HOST_BYTE(DID_ERROR) | STATUS_BYTE(scsiqp->scsi_status);
5843                 break;
5844         }
5845
5846         /*
5847          * If the 'init_tidmask' bit isn't already set for the target and the
5848          * current request finished normally, then set the bit for the target
5849          * to indicate that a device is present.
5850          */
5851         if ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(scp->device->id)) == 0 &&
5852             scsiqp->done_status == QD_NO_ERROR &&
5853             scsiqp->host_status == QHSTA_NO_ERROR) {
5854                 boardp->init_tidmask |= ADV_TID_TO_TIDMASK(scp->device->id);
5855         }
5856
5857         /*
5858          * Because interrupts may be enabled by the 'struct scsi_cmnd' done
5859          * function, add the command to the end of the board's done queue.
5860          * The done function for the command will be called from
5861          * advansys_interrupt().
5862          */
5863         asc_enqueue(&boardp->done, scp, ASC_BACK);
5864
5865         /*
5866          * Free all 'adv_sgblk_t' structures allocated for the request.
5867          */
5868         while ((sgblkp = reqp->sgblkp) != NULL) {
5869                 /* Remove 'sgblkp' from the request list. */
5870                 reqp->sgblkp = sgblkp->next_sgblkp;
5871
5872                 /* Add 'sgblkp' to the board free list. */
5873                 sgblkp->next_sgblkp = boardp->adv_sgblkp;
5874                 boardp->adv_sgblkp = sgblkp;
5875         }
5876
5877         /*
5878          * Free the adv_req_t structure used with the command by adding
5879          * it back to the board free list.
5880          */
5881         reqp->next_reqp = boardp->adv_reqp;
5882         boardp->adv_reqp = reqp;
5883
5884         ASC_DBG(1, "adv_isr_callback: done\n");
5885
5886         return;
5887 }
5888
5889 /*
5890  * adv_async_callback() - Adv Library asynchronous event callback function.
5891  */
5892 static void adv_async_callback(ADV_DVC_VAR *adv_dvc_varp, uchar code)
5893 {
5894         switch (code) {
5895         case ADV_ASYNC_SCSI_BUS_RESET_DET:
5896                 /*
5897                  * The firmware detected a SCSI Bus reset.
5898                  */
5899                 ASC_DBG(0,
5900                         "adv_async_callback: ADV_ASYNC_SCSI_BUS_RESET_DET\n");
5901                 break;
5902
5903         case ADV_ASYNC_RDMA_FAILURE:
5904                 /*
5905                  * Handle RDMA failure by resetting the SCSI Bus and
5906                  * possibly the chip if it is unresponsive. Log the error
5907                  * with a unique code.
5908                  */
5909                 ASC_DBG(0, "adv_async_callback: ADV_ASYNC_RDMA_FAILURE\n");
5910                 AdvResetChipAndSB(adv_dvc_varp);
5911                 break;
5912
5913         case ADV_HOST_SCSI_BUS_RESET:
5914                 /*
5915                  * Host generated SCSI bus reset occurred.
5916                  */
5917                 ASC_DBG(0, "adv_async_callback: ADV_HOST_SCSI_BUS_RESET\n");
5918                 break;
5919
5920         default:
5921                 ASC_DBG1(0, "DvcAsyncCallBack: unknown code 0x%x\n", code);
5922                 break;
5923         }
5924 }
5925
5926 /*
5927  * Add a 'REQP' to the end of specified queue. Set 'tidmask'
5928  * to indicate a command is queued for the device.
5929  *
5930  * 'flag' may be either ASC_FRONT or ASC_BACK.
5931  *
5932  * 'REQPNEXT(reqp)' returns reqp's next pointer.
5933  */
5934 static void asc_enqueue(asc_queue_t *ascq, REQP reqp, int flag)
5935 {
5936         int tid;
5937
5938         ASC_DBG3(3, "asc_enqueue: ascq 0x%lx, reqp 0x%lx, flag %d\n",
5939                  (ulong)ascq, (ulong)reqp, flag);
5940         ASC_ASSERT(reqp != NULL);
5941         ASC_ASSERT(flag == ASC_FRONT || flag == ASC_BACK);
5942         tid = REQPTID(reqp);
5943         ASC_ASSERT(tid >= 0 && tid <= ADV_MAX_TID);
5944         if (flag == ASC_FRONT) {
5945                 reqp->host_scribble = (unsigned char *)ascq->q_first[tid];
5946                 ascq->q_first[tid] = reqp;
5947                 /* If the queue was empty, set the last pointer. */
5948                 if (ascq->q_last[tid] == NULL) {
5949                         ascq->q_last[tid] = reqp;
5950                 }
5951         } else {                /* ASC_BACK */
5952                 if (ascq->q_last[tid] != NULL) {
5953                         ascq->q_last[tid]->host_scribble =
5954                             (unsigned char *)reqp;
5955                 }
5956                 ascq->q_last[tid] = reqp;
5957                 reqp->host_scribble = NULL;
5958                 /* If the queue was empty, set the first pointer. */
5959                 if (ascq->q_first[tid] == NULL) {
5960                         ascq->q_first[tid] = reqp;
5961                 }
5962         }
5963         /* The queue has at least one entry, set its bit. */
5964         ascq->q_tidmask |= ADV_TID_TO_TIDMASK(tid);
5965 #ifdef ADVANSYS_STATS
5966         /* Maintain request queue statistics. */
5967         ascq->q_tot_cnt[tid]++;
5968         ascq->q_cur_cnt[tid]++;
5969         if (ascq->q_cur_cnt[tid] > ascq->q_max_cnt[tid]) {
5970                 ascq->q_max_cnt[tid] = ascq->q_cur_cnt[tid];
5971                 ASC_DBG2(2, "asc_enqueue: new q_max_cnt[%d] %d\n",
5972                          tid, ascq->q_max_cnt[tid]);
5973         }
5974         REQPTIME(reqp) = REQTIMESTAMP();
5975 #endif /* ADVANSYS_STATS */
5976         ASC_DBG1(3, "asc_enqueue: reqp 0x%lx\n", (ulong)reqp);
5977         return;
5978 }
5979
5980 /*
5981  * Return first queued 'REQP' on the specified queue for
5982  * the specified target device. Clear the 'tidmask' bit for
5983  * the device if no more commands are left queued for it.
5984  *
5985  * 'REQPNEXT(reqp)' returns reqp's next pointer.
5986  */
5987 static REQP asc_dequeue(asc_queue_t *ascq, int tid)
5988 {
5989         REQP reqp;
5990
5991         ASC_DBG2(3, "asc_dequeue: ascq 0x%lx, tid %d\n", (ulong)ascq, tid);
5992         ASC_ASSERT(tid >= 0 && tid <= ADV_MAX_TID);
5993         if ((reqp = ascq->q_first[tid]) != NULL) {
5994                 ASC_ASSERT(ascq->q_tidmask & ADV_TID_TO_TIDMASK(tid));
5995                 ascq->q_first[tid] = REQPNEXT(reqp);
5996                 /* If the queue is empty, clear its bit and the last pointer. */
5997                 if (ascq->q_first[tid] == NULL) {
5998                         ascq->q_tidmask &= ~ADV_TID_TO_TIDMASK(tid);
5999                         ASC_ASSERT(ascq->q_last[tid] == reqp);
6000                         ascq->q_last[tid] = NULL;
6001                 }
6002 #ifdef ADVANSYS_STATS
6003                 /* Maintain request queue statistics. */
6004                 ascq->q_cur_cnt[tid]--;
6005                 ASC_ASSERT(ascq->q_cur_cnt[tid] >= 0);
6006                 REQTIMESTAT("asc_dequeue", ascq, reqp, tid);
6007 #endif /* ADVANSYS_STATS */
6008         }
6009         ASC_DBG1(3, "asc_dequeue: reqp 0x%lx\n", (ulong)reqp);
6010         return reqp;
6011 }
6012
6013 /*
6014  * Return a pointer to a singly linked list of all the requests queued
6015  * for 'tid' on the 'asc_queue_t' pointed to by 'ascq'.
6016  *
6017  * If 'lastpp' is not NULL, '*lastpp' will be set to point to the
6018  * the last request returned in the singly linked list.
6019  *
6020  * 'tid' should either be a valid target id or if it is ASC_TID_ALL,
6021  * then all queued requests are concatenated into one list and
6022  * returned.
6023  *
6024  * Note: If 'lastpp' is used to append a new list to the end of
6025  * an old list, only change the old list last pointer if '*lastpp'
6026  * (or the function return value) is not NULL, i.e. use a temporary
6027  * variable for 'lastpp' and check its value after the function return
6028  * before assigning it to the list last pointer.
6029  *
6030  * Unfortunately collecting queuing time statistics adds overhead to
6031  * the function that isn't inherent to the function's algorithm.
6032  */
6033 static REQP asc_dequeue_list(asc_queue_t *ascq, REQP *lastpp, int tid)
6034 {
6035         REQP firstp, lastp;
6036         int i;
6037
6038         ASC_DBG2(3, "asc_dequeue_list: ascq 0x%lx, tid %d\n", (ulong)ascq, tid);
6039         ASC_ASSERT((tid == ASC_TID_ALL) || (tid >= 0 && tid <= ADV_MAX_TID));
6040
6041         /*
6042          * If 'tid' is not ASC_TID_ALL, return requests only for
6043          * the specified 'tid'. If 'tid' is ASC_TID_ALL, return all
6044          * requests for all tids.
6045          */
6046         if (tid != ASC_TID_ALL) {
6047                 /* Return all requests for the specified 'tid'. */
6048                 if ((ascq->q_tidmask & ADV_TID_TO_TIDMASK(tid)) == 0) {
6049                         /* List is empty; Set first and last return pointers to NULL. */
6050                         firstp = lastp = NULL;
6051                 } else {
6052                         firstp = ascq->q_first[tid];
6053                         lastp = ascq->q_last[tid];
6054                         ascq->q_first[tid] = ascq->q_last[tid] = NULL;
6055                         ascq->q_tidmask &= ~ADV_TID_TO_TIDMASK(tid);
6056 #ifdef ADVANSYS_STATS
6057                         {
6058                                 REQP reqp;
6059                                 ascq->q_cur_cnt[tid] = 0;
6060                                 for (reqp = firstp; reqp; reqp = REQPNEXT(reqp)) {
6061                                         REQTIMESTAT("asc_dequeue_list", ascq,
6062                                                     reqp, tid);
6063                                 }
6064                         }
6065 #endif /* ADVANSYS_STATS */
6066                 }
6067         } else {
6068                 /* Return all requests for all tids. */
6069                 firstp = lastp = NULL;
6070                 for (i = 0; i <= ADV_MAX_TID; i++) {
6071                         if (ascq->q_tidmask & ADV_TID_TO_TIDMASK(i)) {
6072                                 if (firstp == NULL) {
6073                                         firstp = ascq->q_first[i];
6074                                         lastp = ascq->q_last[i];
6075                                 } else {
6076                                         ASC_ASSERT(lastp != NULL);
6077                                         lastp->host_scribble =
6078                                             (unsigned char *)ascq->q_first[i];
6079                                         lastp = ascq->q_last[i];
6080                                 }
6081                                 ascq->q_first[i] = ascq->q_last[i] = NULL;
6082                                 ascq->q_tidmask &= ~ADV_TID_TO_TIDMASK(i);
6083 #ifdef ADVANSYS_STATS
6084                                 ascq->q_cur_cnt[i] = 0;
6085 #endif /* ADVANSYS_STATS */
6086                         }
6087                 }
6088 #ifdef ADVANSYS_STATS
6089                 {
6090                         REQP reqp;
6091                         for (reqp = firstp; reqp; reqp = REQPNEXT(reqp)) {
6092                                 REQTIMESTAT("asc_dequeue_list", ascq, reqp,
6093                                             reqp->device->id);
6094                         }
6095                 }
6096 #endif /* ADVANSYS_STATS */
6097         }
6098         if (lastpp) {
6099                 *lastpp = lastp;
6100         }
6101         ASC_DBG1(3, "asc_dequeue_list: firstp 0x%lx\n", (ulong)firstp);
6102         return firstp;
6103 }
6104
6105 /*
6106  * Remove the specified 'REQP' from the specified queue for
6107  * the specified target device. Clear the 'tidmask' bit for the
6108  * device if no more commands are left queued for it.
6109  *
6110  * 'REQPNEXT(reqp)' returns reqp's the next pointer.
6111  *
6112  * Return ASC_TRUE if the command was found and removed,
6113  * otherwise return ASC_FALSE.
6114  */
6115 static int asc_rmqueue(asc_queue_t *ascq, REQP reqp)
6116 {
6117         REQP currp, prevp;
6118         int tid;
6119         int ret = ASC_FALSE;
6120
6121         ASC_DBG2(3, "asc_rmqueue: ascq 0x%lx, reqp 0x%lx\n",
6122                  (ulong)ascq, (ulong)reqp);
6123         ASC_ASSERT(reqp != NULL);
6124
6125         tid = REQPTID(reqp);
6126         ASC_ASSERT(tid >= 0 && tid <= ADV_MAX_TID);
6127
6128         /*
6129          * Handle the common case of 'reqp' being the first
6130          * entry on the queue.
6131          */
6132         if (reqp == ascq->q_first[tid]) {
6133                 ret = ASC_TRUE;
6134                 ascq->q_first[tid] = REQPNEXT(reqp);
6135                 /* If the queue is now empty, clear its bit and the last pointer. */
6136                 if (ascq->q_first[tid] == NULL) {
6137                         ascq->q_tidmask &= ~ADV_TID_TO_TIDMASK(tid);
6138                         ASC_ASSERT(ascq->q_last[tid] == reqp);
6139                         ascq->q_last[tid] = NULL;
6140                 }
6141         } else if (ascq->q_first[tid] != NULL) {
6142                 ASC_ASSERT(ascq->q_last[tid] != NULL);
6143                 /*
6144                  * Because the case of 'reqp' being the first entry has been
6145                  * handled above and it is known the queue is not empty, if
6146                  * 'reqp' is found on the queue it is guaranteed the queue will
6147                  * not become empty and that 'q_first[tid]' will not be changed.
6148                  *
6149                  * Set 'prevp' to the first entry, 'currp' to the second entry,
6150                  * and search for 'reqp'.
6151                  */
6152                 for (prevp = ascq->q_first[tid], currp = REQPNEXT(prevp);
6153                      currp; prevp = currp, currp = REQPNEXT(currp)) {
6154                         if (currp == reqp) {
6155                                 ret = ASC_TRUE;
6156                                 prevp->host_scribble =
6157                                     (unsigned char *)REQPNEXT(currp);
6158                                 reqp->host_scribble = NULL;
6159                                 if (ascq->q_last[tid] == reqp) {
6160                                         ascq->q_last[tid] = prevp;
6161                                 }
6162                                 break;
6163                         }
6164                 }
6165         }
6166 #ifdef ADVANSYS_STATS
6167         /* Maintain request queue statistics. */
6168         if (ret == ASC_TRUE) {
6169                 ascq->q_cur_cnt[tid]--;
6170                 REQTIMESTAT("asc_rmqueue", ascq, reqp, tid);
6171         }
6172         ASC_ASSERT(ascq->q_cur_cnt[tid] >= 0);
6173 #endif /* ADVANSYS_STATS */
6174         ASC_DBG2(3, "asc_rmqueue: reqp 0x%lx, ret %d\n", (ulong)reqp, ret);
6175         return ret;
6176 }
6177
6178 /*
6179  * Execute as many queued requests as possible for the specified queue.
6180  *
6181  * Calls asc_execute_scsi_cmnd() to execute a REQP/struct scsi_cmnd.
6182  */
6183 static void asc_execute_queue(asc_queue_t *ascq)
6184 {
6185         ADV_SCSI_BIT_ID_TYPE scan_tidmask;
6186         REQP reqp;
6187         int i;
6188
6189         ASC_DBG1(1, "asc_execute_queue: ascq 0x%lx\n", (ulong)ascq);
6190         /*
6191          * Execute queued commands for devices attached to
6192          * the current board in round-robin fashion.
6193          */
6194         scan_tidmask = ascq->q_tidmask;
6195         do {
6196                 for (i = 0; i <= ADV_MAX_TID; i++) {
6197                         if (scan_tidmask & ADV_TID_TO_TIDMASK(i)) {
6198                                 if ((reqp = asc_dequeue(ascq, i)) == NULL) {
6199                                         scan_tidmask &= ~ADV_TID_TO_TIDMASK(i);
6200                                 } else
6201                                     if (asc_execute_scsi_cmnd
6202                                         ((struct scsi_cmnd *)reqp)
6203                                         == ASC_BUSY) {
6204                                         scan_tidmask &= ~ADV_TID_TO_TIDMASK(i);
6205                                         /*
6206                                          * The request returned ASC_BUSY. Enqueue at the front of
6207                                          * target's waiting list to maintain correct ordering.
6208                                          */
6209                                         asc_enqueue(ascq, reqp, ASC_FRONT);
6210                                 }
6211                         }
6212                 }
6213         } while (scan_tidmask);
6214         return;
6215 }
6216
6217 #ifdef CONFIG_PROC_FS
6218 /*
6219  * asc_prt_board_devices()
6220  *
6221  * Print driver information for devices attached to the board.
6222  *
6223  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
6224  * cf. asc_prt_line().
6225  *
6226  * Return the number of characters copied into 'cp'. No more than
6227  * 'cplen' characters will be copied to 'cp'.
6228  */
6229 static int asc_prt_board_devices(struct Scsi_Host *shost, char *cp, int cplen)
6230 {
6231         asc_board_t *boardp;
6232         int leftlen;
6233         int totlen;
6234         int len;
6235         int chip_scsi_id;
6236         int i;
6237
6238         boardp = ASC_BOARDP(shost);
6239         leftlen = cplen;
6240         totlen = len = 0;
6241
6242         len = asc_prt_line(cp, leftlen,
6243                            "\nDevice Information for AdvanSys SCSI Host %d:\n",
6244                            shost->host_no);
6245         ASC_PRT_NEXT();
6246
6247         if (ASC_NARROW_BOARD(boardp)) {
6248                 chip_scsi_id = boardp->dvc_cfg.asc_dvc_cfg.chip_scsi_id;
6249         } else {
6250                 chip_scsi_id = boardp->dvc_var.adv_dvc_var.chip_scsi_id;
6251         }
6252
6253         len = asc_prt_line(cp, leftlen, "Target IDs Detected:");
6254         ASC_PRT_NEXT();
6255         for (i = 0; i <= ADV_MAX_TID; i++) {
6256                 if (boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) {
6257                         len = asc_prt_line(cp, leftlen, " %X,", i);
6258                         ASC_PRT_NEXT();
6259                 }
6260         }
6261         len = asc_prt_line(cp, leftlen, " (%X=Host Adapter)\n", chip_scsi_id);
6262         ASC_PRT_NEXT();
6263
6264         return totlen;
6265 }
6266
6267 /*
6268  * Display Wide Board BIOS Information.
6269  */
6270 static int asc_prt_adv_bios(struct Scsi_Host *shost, char *cp, int cplen)
6271 {
6272         asc_board_t *boardp;
6273         int leftlen;
6274         int totlen;
6275         int len;
6276         ushort major, minor, letter;
6277
6278         boardp = ASC_BOARDP(shost);
6279         leftlen = cplen;
6280         totlen = len = 0;
6281
6282         len = asc_prt_line(cp, leftlen, "\nROM BIOS Version: ");
6283         ASC_PRT_NEXT();
6284
6285         /*
6286          * If the BIOS saved a valid signature, then fill in
6287          * the BIOS code segment base address.
6288          */
6289         if (boardp->bios_signature != 0x55AA) {
6290                 len = asc_prt_line(cp, leftlen, "Disabled or Pre-3.1\n");
6291                 ASC_PRT_NEXT();
6292                 len = asc_prt_line(cp, leftlen,
6293                                    "BIOS either disabled or Pre-3.1. If it is pre-3.1, then a newer version\n");
6294                 ASC_PRT_NEXT();
6295                 len = asc_prt_line(cp, leftlen,
6296                                    "can be found at the ConnectCom FTP site: ftp://ftp.connectcom.net/pub\n");
6297                 ASC_PRT_NEXT();
6298         } else {
6299                 major = (boardp->bios_version >> 12) & 0xF;
6300                 minor = (boardp->bios_version >> 8) & 0xF;
6301                 letter = (boardp->bios_version & 0xFF);
6302
6303                 len = asc_prt_line(cp, leftlen, "%d.%d%c\n",
6304                                    major, minor,
6305                                    letter >= 26 ? '?' : letter + 'A');
6306                 ASC_PRT_NEXT();
6307
6308                 /*
6309                  * Current available ROM BIOS release is 3.1I for UW
6310                  * and 3.2I for U2W. This code doesn't differentiate
6311                  * UW and U2W boards.
6312                  */
6313                 if (major < 3 || (major <= 3 && minor < 1) ||
6314                     (major <= 3 && minor <= 1 && letter < ('I' - 'A'))) {
6315                         len = asc_prt_line(cp, leftlen,
6316                                            "Newer version of ROM BIOS is available at the ConnectCom FTP site:\n");
6317                         ASC_PRT_NEXT();
6318                         len = asc_prt_line(cp, leftlen,
6319                                            "ftp://ftp.connectcom.net/pub\n");
6320                         ASC_PRT_NEXT();
6321                 }
6322         }
6323
6324         return totlen;
6325 }
6326
6327 /*
6328  * Add serial number to information bar if signature AAh
6329  * is found in at bit 15-9 (7 bits) of word 1.
6330  *
6331  * Serial Number consists fo 12 alpha-numeric digits.
6332  *
6333  *       1 - Product type (A,B,C,D..)  Word0: 15-13 (3 bits)
6334  *       2 - MFG Location (A,B,C,D..)  Word0: 12-10 (3 bits)
6335  *     3-4 - Product ID (0-99)         Word0: 9-0 (10 bits)
6336  *       5 - Product revision (A-J)    Word0:  "         "
6337  *
6338  *           Signature                 Word1: 15-9 (7 bits)
6339  *       6 - Year (0-9)                Word1: 8-6 (3 bits) & Word2: 15 (1 bit)
6340  *     7-8 - Week of the year (1-52)   Word1: 5-0 (6 bits)
6341  *
6342  *    9-12 - Serial Number (A001-Z999) Word2: 14-0 (15 bits)
6343  *
6344  * Note 1: Only production cards will have a serial number.
6345  *
6346  * Note 2: Signature is most significant 7 bits (0xFE).
6347  *
6348  * Returns ASC_TRUE if serial number found, otherwise returns ASC_FALSE.
6349  */
6350 static int asc_get_eeprom_string(ushort *serialnum, uchar *cp)
6351 {
6352         ushort w, num;
6353
6354         if ((serialnum[1] & 0xFE00) != ((ushort)0xAA << 8)) {
6355                 return ASC_FALSE;
6356         } else {
6357                 /*
6358                  * First word - 6 digits.
6359                  */
6360                 w = serialnum[0];
6361
6362                 /* Product type - 1st digit. */
6363                 if ((*cp = 'A' + ((w & 0xE000) >> 13)) == 'H') {
6364                         /* Product type is P=Prototype */
6365                         *cp += 0x8;
6366                 }
6367                 cp++;
6368
6369                 /* Manufacturing location - 2nd digit. */
6370                 *cp++ = 'A' + ((w & 0x1C00) >> 10);
6371
6372                 /* Product ID - 3rd, 4th digits. */
6373                 num = w & 0x3FF;
6374                 *cp++ = '0' + (num / 100);
6375                 num %= 100;
6376                 *cp++ = '0' + (num / 10);
6377
6378                 /* Product revision - 5th digit. */
6379                 *cp++ = 'A' + (num % 10);
6380
6381                 /*
6382                  * Second word
6383                  */
6384                 w = serialnum[1];
6385
6386                 /*
6387                  * Year - 6th digit.
6388                  *
6389                  * If bit 15 of third word is set, then the
6390                  * last digit of the year is greater than 7.
6391                  */
6392                 if (serialnum[2] & 0x8000) {
6393                         *cp++ = '8' + ((w & 0x1C0) >> 6);
6394                 } else {
6395                         *cp++ = '0' + ((w & 0x1C0) >> 6);
6396                 }
6397
6398                 /* Week of year - 7th, 8th digits. */
6399                 num = w & 0x003F;
6400                 *cp++ = '0' + num / 10;
6401                 num %= 10;
6402                 *cp++ = '0' + num;
6403
6404                 /*
6405                  * Third word
6406                  */
6407                 w = serialnum[2] & 0x7FFF;
6408
6409                 /* Serial number - 9th digit. */
6410                 *cp++ = 'A' + (w / 1000);
6411
6412                 /* 10th, 11th, 12th digits. */
6413                 num = w % 1000;
6414                 *cp++ = '0' + num / 100;
6415                 num %= 100;
6416                 *cp++ = '0' + num / 10;
6417                 num %= 10;
6418                 *cp++ = '0' + num;
6419
6420                 *cp = '\0';     /* Null Terminate the string. */
6421                 return ASC_TRUE;
6422         }
6423 }
6424
6425 /*
6426  * asc_prt_asc_board_eeprom()
6427  *
6428  * Print board EEPROM configuration.
6429  *
6430  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
6431  * cf. asc_prt_line().
6432  *
6433  * Return the number of characters copied into 'cp'. No more than
6434  * 'cplen' characters will be copied to 'cp'.
6435  */
6436 static int asc_prt_asc_board_eeprom(struct Scsi_Host *shost, char *cp, int cplen)
6437 {
6438         asc_board_t *boardp;
6439         ASC_DVC_VAR *asc_dvc_varp;
6440         int leftlen;
6441         int totlen;
6442         int len;
6443         ASCEEP_CONFIG *ep;
6444         int i;
6445 #ifdef CONFIG_ISA
6446         int isa_dma_speed[] = { 10, 8, 7, 6, 5, 4, 3, 2 };
6447 #endif /* CONFIG_ISA */
6448         uchar serialstr[13];
6449
6450         boardp = ASC_BOARDP(shost);
6451         asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
6452         ep = &boardp->eep_config.asc_eep;
6453
6454         leftlen = cplen;
6455         totlen = len = 0;
6456
6457         len = asc_prt_line(cp, leftlen,
6458                            "\nEEPROM Settings for AdvanSys SCSI Host %d:\n",
6459                            shost->host_no);
6460         ASC_PRT_NEXT();
6461
6462         if (asc_get_eeprom_string((ushort *)&ep->adapter_info[0], serialstr)
6463             == ASC_TRUE) {
6464                 len =
6465                     asc_prt_line(cp, leftlen, " Serial Number: %s\n",
6466                                  serialstr);
6467                 ASC_PRT_NEXT();
6468         } else {
6469                 if (ep->adapter_info[5] == 0xBB) {
6470                         len = asc_prt_line(cp, leftlen,
6471                                            " Default Settings Used for EEPROM-less Adapter.\n");
6472                         ASC_PRT_NEXT();
6473                 } else {
6474                         len = asc_prt_line(cp, leftlen,
6475                                            " Serial Number Signature Not Present.\n");
6476                         ASC_PRT_NEXT();
6477                 }
6478         }
6479
6480         len = asc_prt_line(cp, leftlen,
6481                            " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
6482                            ASC_EEP_GET_CHIP_ID(ep), ep->max_total_qng,
6483                            ep->max_tag_qng);
6484         ASC_PRT_NEXT();
6485
6486         len = asc_prt_line(cp, leftlen,
6487                            " cntl 0x%x, no_scam 0x%x\n", ep->cntl, ep->no_scam);
6488         ASC_PRT_NEXT();
6489
6490         len = asc_prt_line(cp, leftlen, " Target ID:           ");
6491         ASC_PRT_NEXT();
6492         for (i = 0; i <= ASC_MAX_TID; i++) {
6493                 len = asc_prt_line(cp, leftlen, " %d", i);
6494                 ASC_PRT_NEXT();
6495         }
6496         len = asc_prt_line(cp, leftlen, "\n");
6497         ASC_PRT_NEXT();
6498
6499         len = asc_prt_line(cp, leftlen, " Disconnects:         ");
6500         ASC_PRT_NEXT();
6501         for (i = 0; i <= ASC_MAX_TID; i++) {
6502                 len = asc_prt_line(cp, leftlen, " %c",
6503                                    (ep->
6504                                     disc_enable & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
6505                                    'N');
6506                 ASC_PRT_NEXT();
6507         }
6508         len = asc_prt_line(cp, leftlen, "\n");
6509         ASC_PRT_NEXT();
6510
6511         len = asc_prt_line(cp, leftlen, " Command Queuing:     ");
6512         ASC_PRT_NEXT();
6513         for (i = 0; i <= ASC_MAX_TID; i++) {
6514                 len = asc_prt_line(cp, leftlen, " %c",
6515                                    (ep->
6516                                     use_cmd_qng & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
6517                                    'N');
6518                 ASC_PRT_NEXT();
6519         }
6520         len = asc_prt_line(cp, leftlen, "\n");
6521         ASC_PRT_NEXT();
6522
6523         len = asc_prt_line(cp, leftlen, " Start Motor:         ");
6524         ASC_PRT_NEXT();
6525         for (i = 0; i <= ASC_MAX_TID; i++) {
6526                 len = asc_prt_line(cp, leftlen, " %c",
6527                                    (ep->
6528                                     start_motor & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
6529                                    'N');
6530                 ASC_PRT_NEXT();
6531         }
6532         len = asc_prt_line(cp, leftlen, "\n");
6533         ASC_PRT_NEXT();
6534
6535         len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
6536         ASC_PRT_NEXT();
6537         for (i = 0; i <= ASC_MAX_TID; i++) {
6538                 len = asc_prt_line(cp, leftlen, " %c",
6539                                    (ep->
6540                                     init_sdtr & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
6541                                    'N');
6542                 ASC_PRT_NEXT();
6543         }
6544         len = asc_prt_line(cp, leftlen, "\n");
6545         ASC_PRT_NEXT();
6546
6547 #ifdef CONFIG_ISA
6548         if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
6549                 len = asc_prt_line(cp, leftlen,
6550                                    " Host ISA DMA speed:   %d MB/S\n",
6551                                    isa_dma_speed[ASC_EEP_GET_DMA_SPD(ep)]);
6552                 ASC_PRT_NEXT();
6553         }
6554 #endif /* CONFIG_ISA */
6555
6556         return totlen;
6557 }
6558
6559 /*
6560  * asc_prt_adv_board_eeprom()
6561  *
6562  * Print board EEPROM configuration.
6563  *
6564  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
6565  * cf. asc_prt_line().
6566  *
6567  * Return the number of characters copied into 'cp'. No more than
6568  * 'cplen' characters will be copied to 'cp'.
6569  */
6570 static int asc_prt_adv_board_eeprom(struct Scsi_Host *shost, char *cp, int cplen)
6571 {
6572         asc_board_t *boardp;
6573         ADV_DVC_VAR *adv_dvc_varp;
6574         int leftlen;
6575         int totlen;
6576         int len;
6577         int i;
6578         char *termstr;
6579         uchar serialstr[13];
6580         ADVEEP_3550_CONFIG *ep_3550 = NULL;
6581         ADVEEP_38C0800_CONFIG *ep_38C0800 = NULL;
6582         ADVEEP_38C1600_CONFIG *ep_38C1600 = NULL;
6583         ushort word;
6584         ushort *wordp;
6585         ushort sdtr_speed = 0;
6586
6587         boardp = ASC_BOARDP(shost);
6588         adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
6589         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6590                 ep_3550 = &boardp->eep_config.adv_3550_eep;
6591         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6592                 ep_38C0800 = &boardp->eep_config.adv_38C0800_eep;
6593         } else {
6594                 ep_38C1600 = &boardp->eep_config.adv_38C1600_eep;
6595         }
6596
6597         leftlen = cplen;
6598         totlen = len = 0;
6599
6600         len = asc_prt_line(cp, leftlen,
6601                            "\nEEPROM Settings for AdvanSys SCSI Host %d:\n",
6602                            shost->host_no);
6603         ASC_PRT_NEXT();
6604
6605         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6606                 wordp = &ep_3550->serial_number_word1;
6607         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6608                 wordp = &ep_38C0800->serial_number_word1;
6609         } else {
6610                 wordp = &ep_38C1600->serial_number_word1;
6611         }
6612
6613         if (asc_get_eeprom_string(wordp, serialstr) == ASC_TRUE) {
6614                 len =
6615                     asc_prt_line(cp, leftlen, " Serial Number: %s\n",
6616                                  serialstr);
6617                 ASC_PRT_NEXT();
6618         } else {
6619                 len = asc_prt_line(cp, leftlen,
6620                                    " Serial Number Signature Not Present.\n");
6621                 ASC_PRT_NEXT();
6622         }
6623
6624         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6625                 len = asc_prt_line(cp, leftlen,
6626                                    " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
6627                                    ep_3550->adapter_scsi_id,
6628                                    ep_3550->max_host_qng, ep_3550->max_dvc_qng);
6629                 ASC_PRT_NEXT();
6630         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6631                 len = asc_prt_line(cp, leftlen,
6632                                    " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
6633                                    ep_38C0800->adapter_scsi_id,
6634                                    ep_38C0800->max_host_qng,
6635                                    ep_38C0800->max_dvc_qng);
6636                 ASC_PRT_NEXT();
6637         } else {
6638                 len = asc_prt_line(cp, leftlen,
6639                                    " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
6640                                    ep_38C1600->adapter_scsi_id,
6641                                    ep_38C1600->max_host_qng,
6642                                    ep_38C1600->max_dvc_qng);
6643                 ASC_PRT_NEXT();
6644         }
6645         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6646                 word = ep_3550->termination;
6647         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6648                 word = ep_38C0800->termination_lvd;
6649         } else {
6650                 word = ep_38C1600->termination_lvd;
6651         }
6652         switch (word) {
6653         case 1:
6654                 termstr = "Low Off/High Off";
6655                 break;
6656         case 2:
6657                 termstr = "Low Off/High On";
6658                 break;
6659         case 3:
6660                 termstr = "Low On/High On";
6661                 break;
6662         default:
6663         case 0:
6664                 termstr = "Automatic";
6665                 break;
6666         }
6667
6668         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6669                 len = asc_prt_line(cp, leftlen,
6670                                    " termination: %u (%s), bios_ctrl: 0x%x\n",
6671                                    ep_3550->termination, termstr,
6672                                    ep_3550->bios_ctrl);
6673                 ASC_PRT_NEXT();
6674         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6675                 len = asc_prt_line(cp, leftlen,
6676                                    " termination: %u (%s), bios_ctrl: 0x%x\n",
6677                                    ep_38C0800->termination_lvd, termstr,
6678                                    ep_38C0800->bios_ctrl);
6679                 ASC_PRT_NEXT();
6680         } else {
6681                 len = asc_prt_line(cp, leftlen,
6682                                    " termination: %u (%s), bios_ctrl: 0x%x\n",
6683                                    ep_38C1600->termination_lvd, termstr,
6684                                    ep_38C1600->bios_ctrl);
6685                 ASC_PRT_NEXT();
6686         }
6687
6688         len = asc_prt_line(cp, leftlen, " Target ID:           ");
6689         ASC_PRT_NEXT();
6690         for (i = 0; i <= ADV_MAX_TID; i++) {
6691                 len = asc_prt_line(cp, leftlen, " %X", i);
6692                 ASC_PRT_NEXT();
6693         }
6694         len = asc_prt_line(cp, leftlen, "\n");
6695         ASC_PRT_NEXT();
6696
6697         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6698                 word = ep_3550->disc_enable;
6699         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6700                 word = ep_38C0800->disc_enable;
6701         } else {
6702                 word = ep_38C1600->disc_enable;
6703         }
6704         len = asc_prt_line(cp, leftlen, " Disconnects:         ");
6705         ASC_PRT_NEXT();
6706         for (i = 0; i <= ADV_MAX_TID; i++) {
6707                 len = asc_prt_line(cp, leftlen, " %c",
6708                                    (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
6709                 ASC_PRT_NEXT();
6710         }
6711         len = asc_prt_line(cp, leftlen, "\n");
6712         ASC_PRT_NEXT();
6713
6714         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6715                 word = ep_3550->tagqng_able;
6716         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6717                 word = ep_38C0800->tagqng_able;
6718         } else {
6719                 word = ep_38C1600->tagqng_able;
6720         }
6721         len = asc_prt_line(cp, leftlen, " Command Queuing:     ");
6722         ASC_PRT_NEXT();
6723         for (i = 0; i <= ADV_MAX_TID; i++) {
6724                 len = asc_prt_line(cp, leftlen, " %c",
6725                                    (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
6726                 ASC_PRT_NEXT();
6727         }
6728         len = asc_prt_line(cp, leftlen, "\n");
6729         ASC_PRT_NEXT();
6730
6731         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6732                 word = ep_3550->start_motor;
6733         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6734                 word = ep_38C0800->start_motor;
6735         } else {
6736                 word = ep_38C1600->start_motor;
6737         }
6738         len = asc_prt_line(cp, leftlen, " Start Motor:         ");
6739         ASC_PRT_NEXT();
6740         for (i = 0; i <= ADV_MAX_TID; i++) {
6741                 len = asc_prt_line(cp, leftlen, " %c",
6742                                    (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
6743                 ASC_PRT_NEXT();
6744         }
6745         len = asc_prt_line(cp, leftlen, "\n");
6746         ASC_PRT_NEXT();
6747
6748         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6749                 len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
6750                 ASC_PRT_NEXT();
6751                 for (i = 0; i <= ADV_MAX_TID; i++) {
6752                         len = asc_prt_line(cp, leftlen, " %c",
6753                                            (ep_3550->
6754                                             sdtr_able & ADV_TID_TO_TIDMASK(i)) ?
6755                                            'Y' : 'N');
6756                         ASC_PRT_NEXT();
6757                 }
6758                 len = asc_prt_line(cp, leftlen, "\n");
6759                 ASC_PRT_NEXT();
6760         }
6761
6762         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6763                 len = asc_prt_line(cp, leftlen, " Ultra Transfer:      ");
6764                 ASC_PRT_NEXT();
6765                 for (i = 0; i <= ADV_MAX_TID; i++) {
6766                         len = asc_prt_line(cp, leftlen, " %c",
6767                                            (ep_3550->
6768                                             ultra_able & ADV_TID_TO_TIDMASK(i))
6769                                            ? 'Y' : 'N');
6770                         ASC_PRT_NEXT();
6771                 }
6772                 len = asc_prt_line(cp, leftlen, "\n");
6773                 ASC_PRT_NEXT();
6774         }
6775
6776         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
6777                 word = ep_3550->wdtr_able;
6778         } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
6779                 word = ep_38C0800->wdtr_able;
6780         } else {
6781                 word = ep_38C1600->wdtr_able;
6782         }
6783         len = asc_prt_line(cp, leftlen, " Wide Transfer:       ");
6784         ASC_PRT_NEXT();
6785         for (i = 0; i <= ADV_MAX_TID; i++) {
6786                 len = asc_prt_line(cp, leftlen, " %c",
6787                                    (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
6788                 ASC_PRT_NEXT();
6789         }
6790         len = asc_prt_line(cp, leftlen, "\n");
6791         ASC_PRT_NEXT();
6792
6793         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800 ||
6794             adv_dvc_varp->chip_type == ADV_CHIP_ASC38C1600) {
6795                 len = asc_prt_line(cp, leftlen,
6796                                    " Synchronous Transfer Speed (Mhz):\n  ");
6797                 ASC_PRT_NEXT();
6798                 for (i = 0; i <= ADV_MAX_TID; i++) {
6799                         char *speed_str;
6800
6801                         if (i == 0) {
6802                                 sdtr_speed = adv_dvc_varp->sdtr_speed1;
6803                         } else if (i == 4) {
6804                                 sdtr_speed = adv_dvc_varp->sdtr_speed2;
6805                         } else if (i == 8) {
6806                                 sdtr_speed = adv_dvc_varp->sdtr_speed3;
6807                         } else if (i == 12) {
6808                                 sdtr_speed = adv_dvc_varp->sdtr_speed4;
6809                         }
6810                         switch (sdtr_speed & ADV_MAX_TID) {
6811                         case 0:
6812                                 speed_str = "Off";
6813                                 break;
6814                         case 1:
6815                                 speed_str = "  5";
6816                                 break;
6817                         case 2:
6818                                 speed_str = " 10";
6819                                 break;
6820                         case 3:
6821                                 speed_str = " 20";
6822                                 break;
6823                         case 4:
6824                                 speed_str = " 40";
6825                                 break;
6826                         case 5:
6827                                 speed_str = " 80";
6828                                 break;
6829                         default:
6830                                 speed_str = "Unk";
6831                                 break;
6832                         }
6833                         len = asc_prt_line(cp, leftlen, "%X:%s ", i, speed_str);
6834                         ASC_PRT_NEXT();
6835                         if (i == 7) {
6836                                 len = asc_prt_line(cp, leftlen, "\n  ");
6837                                 ASC_PRT_NEXT();
6838                         }
6839                         sdtr_speed >>= 4;
6840                 }
6841                 len = asc_prt_line(cp, leftlen, "\n");
6842                 ASC_PRT_NEXT();
6843         }
6844
6845         return totlen;
6846 }
6847
6848 /*
6849  * asc_prt_driver_conf()
6850  *
6851  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
6852  * cf. asc_prt_line().
6853  *
6854  * Return the number of characters copied into 'cp'. No more than
6855  * 'cplen' characters will be copied to 'cp'.
6856  */
6857 static int asc_prt_driver_conf(struct Scsi_Host *shost, char *cp, int cplen)
6858 {
6859         asc_board_t *boardp;
6860         int leftlen;
6861         int totlen;
6862         int len;
6863         int chip_scsi_id;
6864
6865         boardp = ASC_BOARDP(shost);
6866
6867         leftlen = cplen;
6868         totlen = len = 0;
6869
6870         len = asc_prt_line(cp, leftlen,
6871                            "\nLinux Driver Configuration and Information for AdvanSys SCSI Host %d:\n",
6872                            shost->host_no);
6873         ASC_PRT_NEXT();
6874
6875         len = asc_prt_line(cp, leftlen,
6876                            " host_busy %u, last_reset %u, max_id %u, max_lun %u, max_channel %u\n",
6877                            shost->host_busy, shost->last_reset, shost->max_id,
6878                            shost->max_lun, shost->max_channel);
6879         ASC_PRT_NEXT();
6880
6881         len = asc_prt_line(cp, leftlen,
6882                            " unique_id %d, can_queue %d, this_id %d, sg_tablesize %u, cmd_per_lun %u\n",
6883                            shost->unique_id, shost->can_queue, shost->this_id,
6884                            shost->sg_tablesize, shost->cmd_per_lun);
6885         ASC_PRT_NEXT();
6886
6887         len = asc_prt_line(cp, leftlen,
6888                            " unchecked_isa_dma %d, use_clustering %d\n",
6889                            shost->unchecked_isa_dma, shost->use_clustering);
6890         ASC_PRT_NEXT();
6891
6892         len = asc_prt_line(cp, leftlen,
6893                            " flags 0x%x, last_reset 0x%x, jiffies 0x%x, asc_n_io_port 0x%x\n",
6894                            boardp->flags, boardp->last_reset, jiffies,
6895                            boardp->asc_n_io_port);
6896         ASC_PRT_NEXT();
6897
6898         /* 'shost->n_io_port' may be truncated because it is only one byte. */
6899         len = asc_prt_line(cp, leftlen,
6900                            " io_port 0x%x, n_io_port 0x%x\n",
6901                            shost->io_port, shost->n_io_port);
6902         ASC_PRT_NEXT();
6903
6904         if (ASC_NARROW_BOARD(boardp)) {
6905                 chip_scsi_id = boardp->dvc_cfg.asc_dvc_cfg.chip_scsi_id;
6906         } else {
6907                 chip_scsi_id = boardp->dvc_var.adv_dvc_var.chip_scsi_id;
6908         }
6909
6910         return totlen;
6911 }
6912
6913 /*
6914  * asc_prt_asc_board_info()
6915  *
6916  * Print dynamic board configuration information.
6917  *
6918  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
6919  * cf. asc_prt_line().
6920  *
6921  * Return the number of characters copied into 'cp'. No more than
6922  * 'cplen' characters will be copied to 'cp'.
6923  */
6924 static int asc_prt_asc_board_info(struct Scsi_Host *shost, char *cp, int cplen)
6925 {
6926         asc_board_t *boardp;
6927         int chip_scsi_id;
6928         int leftlen;
6929         int totlen;
6930         int len;
6931         ASC_DVC_VAR *v;
6932         ASC_DVC_CFG *c;
6933         int i;
6934         int renegotiate = 0;
6935
6936         boardp = ASC_BOARDP(shost);
6937         v = &boardp->dvc_var.asc_dvc_var;
6938         c = &boardp->dvc_cfg.asc_dvc_cfg;
6939         chip_scsi_id = c->chip_scsi_id;
6940
6941         leftlen = cplen;
6942         totlen = len = 0;
6943
6944         len = asc_prt_line(cp, leftlen,
6945                            "\nAsc Library Configuration and Statistics for AdvanSys SCSI Host %d:\n",
6946                            shost->host_no);
6947         ASC_PRT_NEXT();
6948
6949         len = asc_prt_line(cp, leftlen,
6950                            " chip_version %u, lib_version 0x%x, lib_serial_no %u, mcode_date 0x%x\n",
6951                            c->chip_version, c->lib_version, c->lib_serial_no,
6952                            c->mcode_date);
6953         ASC_PRT_NEXT();
6954
6955         len = asc_prt_line(cp, leftlen,
6956                            " mcode_version 0x%x, err_code %u\n",
6957                            c->mcode_version, v->err_code);
6958         ASC_PRT_NEXT();
6959
6960         /* Current number of commands waiting for the host. */
6961         len = asc_prt_line(cp, leftlen,
6962                            " Total Command Pending: %d\n", v->cur_total_qng);
6963         ASC_PRT_NEXT();
6964
6965         len = asc_prt_line(cp, leftlen, " Command Queuing:");
6966         ASC_PRT_NEXT();
6967         for (i = 0; i <= ASC_MAX_TID; i++) {
6968                 if ((chip_scsi_id == i) ||
6969                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
6970                         continue;
6971                 }
6972                 len = asc_prt_line(cp, leftlen, " %X:%c",
6973                                    i,
6974                                    (v->
6975                                     use_tagged_qng & ADV_TID_TO_TIDMASK(i)) ?
6976                                    'Y' : 'N');
6977                 ASC_PRT_NEXT();
6978         }
6979         len = asc_prt_line(cp, leftlen, "\n");
6980         ASC_PRT_NEXT();
6981
6982         /* Current number of commands waiting for a device. */
6983         len = asc_prt_line(cp, leftlen, " Command Queue Pending:");
6984         ASC_PRT_NEXT();
6985         for (i = 0; i <= ASC_MAX_TID; i++) {
6986                 if ((chip_scsi_id == i) ||
6987                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
6988                         continue;
6989                 }
6990                 len = asc_prt_line(cp, leftlen, " %X:%u", i, v->cur_dvc_qng[i]);
6991                 ASC_PRT_NEXT();
6992         }
6993         len = asc_prt_line(cp, leftlen, "\n");
6994         ASC_PRT_NEXT();
6995
6996         /* Current limit on number of commands that can be sent to a device. */
6997         len = asc_prt_line(cp, leftlen, " Command Queue Limit:");
6998         ASC_PRT_NEXT();
6999         for (i = 0; i <= ASC_MAX_TID; i++) {
7000                 if ((chip_scsi_id == i) ||
7001                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7002                         continue;
7003                 }
7004                 len = asc_prt_line(cp, leftlen, " %X:%u", i, v->max_dvc_qng[i]);
7005                 ASC_PRT_NEXT();
7006         }
7007         len = asc_prt_line(cp, leftlen, "\n");
7008         ASC_PRT_NEXT();
7009
7010         /* Indicate whether the device has returned queue full status. */
7011         len = asc_prt_line(cp, leftlen, " Command Queue Full:");
7012         ASC_PRT_NEXT();
7013         for (i = 0; i <= ASC_MAX_TID; i++) {
7014                 if ((chip_scsi_id == i) ||
7015                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7016                         continue;
7017                 }
7018                 if (boardp->queue_full & ADV_TID_TO_TIDMASK(i)) {
7019                         len = asc_prt_line(cp, leftlen, " %X:Y-%d",
7020                                            i, boardp->queue_full_cnt[i]);
7021                 } else {
7022                         len = asc_prt_line(cp, leftlen, " %X:N", i);
7023                 }
7024                 ASC_PRT_NEXT();
7025         }
7026         len = asc_prt_line(cp, leftlen, "\n");
7027         ASC_PRT_NEXT();
7028
7029         len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
7030         ASC_PRT_NEXT();
7031         for (i = 0; i <= ASC_MAX_TID; i++) {
7032                 if ((chip_scsi_id == i) ||
7033                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7034                         continue;
7035                 }
7036                 len = asc_prt_line(cp, leftlen, " %X:%c",
7037                                    i,
7038                                    (v->
7039                                     sdtr_done & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
7040                                    'N');
7041                 ASC_PRT_NEXT();
7042         }
7043         len = asc_prt_line(cp, leftlen, "\n");
7044         ASC_PRT_NEXT();
7045
7046         for (i = 0; i <= ASC_MAX_TID; i++) {
7047                 uchar syn_period_ix;
7048
7049                 if ((chip_scsi_id == i) ||
7050                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0) ||
7051                     ((v->init_sdtr & ADV_TID_TO_TIDMASK(i)) == 0)) {
7052                         continue;
7053                 }
7054
7055                 len = asc_prt_line(cp, leftlen, "  %X:", i);
7056                 ASC_PRT_NEXT();
7057
7058                 if ((boardp->sdtr_data[i] & ASC_SYN_MAX_OFFSET) == 0) {
7059                         len = asc_prt_line(cp, leftlen, " Asynchronous");
7060                         ASC_PRT_NEXT();
7061                 } else {
7062                         syn_period_ix =
7063                             (boardp->sdtr_data[i] >> 4) & (v->max_sdtr_index -
7064                                                            1);
7065
7066                         len = asc_prt_line(cp, leftlen,
7067                                            " Transfer Period Factor: %d (%d.%d Mhz),",
7068                                            v->sdtr_period_tbl[syn_period_ix],
7069                                            250 /
7070                                            v->sdtr_period_tbl[syn_period_ix],
7071                                            ASC_TENTHS(250,
7072                                                       v->
7073                                                       sdtr_period_tbl
7074                                                       [syn_period_ix]));
7075                         ASC_PRT_NEXT();
7076
7077                         len = asc_prt_line(cp, leftlen, " REQ/ACK Offset: %d",
7078                                            boardp->
7079                                            sdtr_data[i] & ASC_SYN_MAX_OFFSET);
7080                         ASC_PRT_NEXT();
7081                 }
7082
7083                 if ((v->sdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
7084                         len = asc_prt_line(cp, leftlen, "*\n");
7085                         renegotiate = 1;
7086                 } else {
7087                         len = asc_prt_line(cp, leftlen, "\n");
7088                 }
7089                 ASC_PRT_NEXT();
7090         }
7091
7092         if (renegotiate) {
7093                 len = asc_prt_line(cp, leftlen,
7094                                    " * = Re-negotiation pending before next command.\n");
7095                 ASC_PRT_NEXT();
7096         }
7097
7098         return totlen;
7099 }
7100
7101 /*
7102  * asc_prt_adv_board_info()
7103  *
7104  * Print dynamic board configuration information.
7105  *
7106  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
7107  * cf. asc_prt_line().
7108  *
7109  * Return the number of characters copied into 'cp'. No more than
7110  * 'cplen' characters will be copied to 'cp'.
7111  */
7112 static int asc_prt_adv_board_info(struct Scsi_Host *shost, char *cp, int cplen)
7113 {
7114         asc_board_t *boardp;
7115         int leftlen;
7116         int totlen;
7117         int len;
7118         int i;
7119         ADV_DVC_VAR *v;
7120         ADV_DVC_CFG *c;
7121         AdvPortAddr iop_base;
7122         ushort chip_scsi_id;
7123         ushort lramword;
7124         uchar lrambyte;
7125         ushort tagqng_able;
7126         ushort sdtr_able, wdtr_able;
7127         ushort wdtr_done, sdtr_done;
7128         ushort period = 0;
7129         int renegotiate = 0;
7130
7131         boardp = ASC_BOARDP(shost);
7132         v = &boardp->dvc_var.adv_dvc_var;
7133         c = &boardp->dvc_cfg.adv_dvc_cfg;
7134         iop_base = v->iop_base;
7135         chip_scsi_id = v->chip_scsi_id;
7136
7137         leftlen = cplen;
7138         totlen = len = 0;
7139
7140         len = asc_prt_line(cp, leftlen,
7141                            "\nAdv Library Configuration and Statistics for AdvanSys SCSI Host %d:\n",
7142                            shost->host_no);
7143         ASC_PRT_NEXT();
7144
7145         len = asc_prt_line(cp, leftlen,
7146                            " iop_base 0x%lx, cable_detect: %X, err_code %u\n",
7147                            v->iop_base,
7148                            AdvReadWordRegister(iop_base,
7149                                                IOPW_SCSI_CFG1) & CABLE_DETECT,
7150                            v->err_code);
7151         ASC_PRT_NEXT();
7152
7153         len = asc_prt_line(cp, leftlen,
7154                            " chip_version %u, lib_version 0x%x, mcode_date 0x%x, mcode_version 0x%x\n",
7155                            c->chip_version, c->lib_version, c->mcode_date,
7156                            c->mcode_version);
7157         ASC_PRT_NEXT();
7158
7159         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
7160         len = asc_prt_line(cp, leftlen, " Queuing Enabled:");
7161         ASC_PRT_NEXT();
7162         for (i = 0; i <= ADV_MAX_TID; i++) {
7163                 if ((chip_scsi_id == i) ||
7164                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7165                         continue;
7166                 }
7167
7168                 len = asc_prt_line(cp, leftlen, " %X:%c",
7169                                    i,
7170                                    (tagqng_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
7171                                    'N');
7172                 ASC_PRT_NEXT();
7173         }
7174         len = asc_prt_line(cp, leftlen, "\n");
7175         ASC_PRT_NEXT();
7176
7177         len = asc_prt_line(cp, leftlen, " Queue Limit:");
7178         ASC_PRT_NEXT();
7179         for (i = 0; i <= ADV_MAX_TID; i++) {
7180                 if ((chip_scsi_id == i) ||
7181                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7182                         continue;
7183                 }
7184
7185                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + i,
7186                                 lrambyte);
7187
7188                 len = asc_prt_line(cp, leftlen, " %X:%d", i, lrambyte);
7189                 ASC_PRT_NEXT();
7190         }
7191         len = asc_prt_line(cp, leftlen, "\n");
7192         ASC_PRT_NEXT();
7193
7194         len = asc_prt_line(cp, leftlen, " Command Pending:");
7195         ASC_PRT_NEXT();
7196         for (i = 0; i <= ADV_MAX_TID; i++) {
7197                 if ((chip_scsi_id == i) ||
7198                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7199                         continue;
7200                 }
7201
7202                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_QUEUED_CMD + i,
7203                                 lrambyte);
7204
7205                 len = asc_prt_line(cp, leftlen, " %X:%d", i, lrambyte);
7206                 ASC_PRT_NEXT();
7207         }
7208         len = asc_prt_line(cp, leftlen, "\n");
7209         ASC_PRT_NEXT();
7210
7211         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
7212         len = asc_prt_line(cp, leftlen, " Wide Enabled:");
7213         ASC_PRT_NEXT();
7214         for (i = 0; i <= ADV_MAX_TID; i++) {
7215                 if ((chip_scsi_id == i) ||
7216                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7217                         continue;
7218                 }
7219
7220                 len = asc_prt_line(cp, leftlen, " %X:%c",
7221                                    i,
7222                                    (wdtr_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
7223                                    'N');
7224                 ASC_PRT_NEXT();
7225         }
7226         len = asc_prt_line(cp, leftlen, "\n");
7227         ASC_PRT_NEXT();
7228
7229         AdvReadWordLram(iop_base, ASC_MC_WDTR_DONE, wdtr_done);
7230         len = asc_prt_line(cp, leftlen, " Transfer Bit Width:");
7231         ASC_PRT_NEXT();
7232         for (i = 0; i <= ADV_MAX_TID; i++) {
7233                 if ((chip_scsi_id == i) ||
7234                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7235                         continue;
7236                 }
7237
7238                 AdvReadWordLram(iop_base,
7239                                 ASC_MC_DEVICE_HSHK_CFG_TABLE + (2 * i),
7240                                 lramword);
7241
7242                 len = asc_prt_line(cp, leftlen, " %X:%d",
7243                                    i, (lramword & 0x8000) ? 16 : 8);
7244                 ASC_PRT_NEXT();
7245
7246                 if ((wdtr_able & ADV_TID_TO_TIDMASK(i)) &&
7247                     (wdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
7248                         len = asc_prt_line(cp, leftlen, "*");
7249                         ASC_PRT_NEXT();
7250                         renegotiate = 1;
7251                 }
7252         }
7253         len = asc_prt_line(cp, leftlen, "\n");
7254         ASC_PRT_NEXT();
7255
7256         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
7257         len = asc_prt_line(cp, leftlen, " Synchronous Enabled:");
7258         ASC_PRT_NEXT();
7259         for (i = 0; i <= ADV_MAX_TID; i++) {
7260                 if ((chip_scsi_id == i) ||
7261                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
7262                         continue;
7263                 }
7264
7265                 len = asc_prt_line(cp, leftlen, " %X:%c",
7266                                    i,
7267                                    (sdtr_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
7268                                    'N');
7269                 ASC_PRT_NEXT();
7270         }
7271         len = asc_prt_line(cp, leftlen, "\n");
7272         ASC_PRT_NEXT();
7273
7274         AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE, sdtr_done);
7275         for (i = 0; i <= ADV_MAX_TID; i++) {
7276
7277                 AdvReadWordLram(iop_base,
7278                                 ASC_MC_DEVICE_HSHK_CFG_TABLE + (2 * i),
7279                                 lramword);
7280                 lramword &= ~0x8000;
7281
7282                 if ((chip_scsi_id == i) ||
7283                     ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0) ||
7284                     ((sdtr_able & ADV_TID_TO_TIDMASK(i)) == 0)) {
7285                         continue;
7286                 }
7287
7288                 len = asc_prt_line(cp, leftlen, "  %X:", i);
7289                 ASC_PRT_NEXT();
7290
7291                 if ((lramword & 0x1F) == 0) {   /* Check for REQ/ACK Offset 0. */
7292                         len = asc_prt_line(cp, leftlen, " Asynchronous");
7293                         ASC_PRT_NEXT();
7294                 } else {
7295                         len =
7296                             asc_prt_line(cp, leftlen,
7297                                          " Transfer Period Factor: ");
7298                         ASC_PRT_NEXT();
7299
7300                         if ((lramword & 0x1F00) == 0x1100) {    /* 80 Mhz */
7301                                 len =
7302                                     asc_prt_line(cp, leftlen, "9 (80.0 Mhz),");
7303                                 ASC_PRT_NEXT();
7304                         } else if ((lramword & 0x1F00) == 0x1000) {     /* 40 Mhz */
7305                                 len =
7306                                     asc_prt_line(cp, leftlen, "10 (40.0 Mhz),");
7307                                 ASC_PRT_NEXT();
7308                         } else {        /* 20 Mhz or below. */
7309
7310                                 period = (((lramword >> 8) * 25) + 50) / 4;
7311
7312                                 if (period == 0) {      /* Should never happen. */
7313                                         len =
7314                                             asc_prt_line(cp, leftlen,
7315                                                          "%d (? Mhz), ");
7316                                         ASC_PRT_NEXT();
7317                                 } else {
7318                                         len = asc_prt_line(cp, leftlen,
7319                                                            "%d (%d.%d Mhz),",
7320                                                            period, 250 / period,
7321                                                            ASC_TENTHS(250,
7322                                                                       period));
7323                                         ASC_PRT_NEXT();
7324                                 }
7325                         }
7326
7327                         len = asc_prt_line(cp, leftlen, " REQ/ACK Offset: %d",
7328                                            lramword & 0x1F);
7329                         ASC_PRT_NEXT();
7330                 }
7331
7332                 if ((sdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
7333                         len = asc_prt_line(cp, leftlen, "*\n");
7334                         renegotiate = 1;
7335                 } else {
7336                         len = asc_prt_line(cp, leftlen, "\n");
7337                 }
7338                 ASC_PRT_NEXT();
7339         }
7340
7341         if (renegotiate) {
7342                 len = asc_prt_line(cp, leftlen,
7343                                    " * = Re-negotiation pending before next command.\n");
7344                 ASC_PRT_NEXT();
7345         }
7346
7347         return totlen;
7348 }
7349
7350 /*
7351  * asc_proc_copy()
7352  *
7353  * Copy proc information to a read buffer taking into account the current
7354  * read offset in the file and the remaining space in the read buffer.
7355  */
7356 static int
7357 asc_proc_copy(off_t advoffset, off_t offset, char *curbuf, int leftlen,
7358               char *cp, int cplen)
7359 {
7360         int cnt = 0;
7361
7362         ASC_DBG3(2, "asc_proc_copy: offset %d, advoffset %d, cplen %d\n",
7363                  (unsigned)offset, (unsigned)advoffset, cplen);
7364         if (offset <= advoffset) {
7365                 /* Read offset below current offset, copy everything. */
7366                 cnt = min(cplen, leftlen);
7367                 ASC_DBG3(2, "asc_proc_copy: curbuf 0x%lx, cp 0x%lx, cnt %d\n",
7368                          (ulong)curbuf, (ulong)cp, cnt);
7369                 memcpy(curbuf, cp, cnt);
7370         } else if (offset < advoffset + cplen) {
7371                 /* Read offset within current range, partial copy. */
7372                 cnt = (advoffset + cplen) - offset;
7373                 cp = (cp + cplen) - cnt;
7374                 cnt = min(cnt, leftlen);
7375                 ASC_DBG3(2, "asc_proc_copy: curbuf 0x%lx, cp 0x%lx, cnt %d\n",
7376                          (ulong)curbuf, (ulong)cp, cnt);
7377                 memcpy(curbuf, cp, cnt);
7378         }
7379         return cnt;
7380 }
7381
7382 /*
7383  * asc_prt_line()
7384  *
7385  * If 'cp' is NULL print to the console, otherwise print to a buffer.
7386  *
7387  * Return 0 if printing to the console, otherwise return the number of
7388  * bytes written to the buffer.
7389  *
7390  * Note: If any single line is greater than ASC_PRTLINE_SIZE bytes the stack
7391  * will be corrupted. 's[]' is defined to be ASC_PRTLINE_SIZE bytes.
7392  */
7393 static int asc_prt_line(char *buf, int buflen, char *fmt, ...)
7394 {
7395         va_list args;
7396         int ret;
7397         char s[ASC_PRTLINE_SIZE];
7398
7399         va_start(args, fmt);
7400         ret = vsprintf(s, fmt, args);
7401         ASC_ASSERT(ret < ASC_PRTLINE_SIZE);
7402         if (buf == NULL) {
7403                 (void)printk(s);
7404                 ret = 0;
7405         } else {
7406                 ret = min(buflen, ret);
7407                 memcpy(buf, s, ret);
7408         }
7409         va_end(args);
7410         return ret;
7411 }
7412 #endif /* CONFIG_PROC_FS */
7413
7414 /*
7415  * --- Functions Required by the Asc Library
7416  */
7417
7418 /*
7419  * Delay for 'n' milliseconds. Don't use the 'jiffies'
7420  * global variable which is incremented once every 5 ms
7421  * from a timer interrupt, because this function may be
7422  * called when interrupts are disabled.
7423  */
7424 static void DvcSleepMilliSecond(ADV_DCNT n)
7425 {
7426         ASC_DBG1(4, "DvcSleepMilliSecond: %lu\n", (ulong)n);
7427         mdelay(n);
7428 }
7429
7430 /*
7431  * Currently and inline noop but leave as a placeholder.
7432  * Leave DvcEnterCritical() as a noop placeholder.
7433  */
7434 static inline ulong DvcEnterCritical(void)
7435 {
7436         return 0;
7437 }
7438
7439 /*
7440  * Critical sections are all protected by the board spinlock.
7441  * Leave DvcLeaveCritical() as a noop placeholder.
7442  */
7443 static inline void DvcLeaveCritical(ulong flags)
7444 {
7445         return;
7446 }
7447
7448 /*
7449  * void
7450  * DvcPutScsiQ(PortAddr iop_base, ushort s_addr, uchar *outbuf, int words)
7451  *
7452  * Calling/Exit State:
7453  *    none
7454  *
7455  * Description:
7456  *     Output an ASC_SCSI_Q structure to the chip
7457  */
7458 static void
7459 DvcPutScsiQ(PortAddr iop_base, ushort s_addr, uchar *outbuf, int words)
7460 {
7461         int i;
7462
7463         ASC_DBG_PRT_HEX(2, "DvcPutScsiQ", outbuf, 2 * words);
7464         AscSetChipLramAddr(iop_base, s_addr);
7465         for (i = 0; i < 2 * words; i += 2) {
7466                 if (i == 4 || i == 20) {
7467                         continue;
7468                 }
7469                 outpw(iop_base + IOP_RAM_DATA,
7470                       ((ushort)outbuf[i + 1] << 8) | outbuf[i]);
7471         }
7472 }
7473
7474 /*
7475  * void
7476  * DvcGetQinfo(PortAddr iop_base, ushort s_addr, uchar *inbuf, int words)
7477  *
7478  * Calling/Exit State:
7479  *    none
7480  *
7481  * Description:
7482  *     Input an ASC_QDONE_INFO structure from the chip
7483  */
7484 static void
7485 DvcGetQinfo(PortAddr iop_base, ushort s_addr, uchar *inbuf, int words)
7486 {
7487         int i;
7488         ushort word;
7489
7490         AscSetChipLramAddr(iop_base, s_addr);
7491         for (i = 0; i < 2 * words; i += 2) {
7492                 if (i == 10) {
7493                         continue;
7494                 }
7495                 word = inpw(iop_base + IOP_RAM_DATA);
7496                 inbuf[i] = word & 0xff;
7497                 inbuf[i + 1] = (word >> 8) & 0xff;
7498         }
7499         ASC_DBG_PRT_HEX(2, "DvcGetQinfo", inbuf, 2 * words);
7500 }
7501
7502 /*
7503  * Read a PCI configuration byte.
7504  */
7505 static uchar __init DvcReadPCIConfigByte(ASC_DVC_VAR *asc_dvc, ushort offset)
7506 {
7507 #ifdef CONFIG_PCI
7508         uchar byte_data;
7509         pci_read_config_byte(to_pci_dev(asc_dvc->cfg->dev), offset, &byte_data);
7510         return byte_data;
7511 #else /* !defined(CONFIG_PCI) */
7512         return 0;
7513 #endif /* !defined(CONFIG_PCI) */
7514 }
7515
7516 /*
7517  * Write a PCI configuration byte.
7518  */
7519 static void __init
7520 DvcWritePCIConfigByte(ASC_DVC_VAR *asc_dvc, ushort offset, uchar byte_data)
7521 {
7522 #ifdef CONFIG_PCI
7523         pci_write_config_byte(to_pci_dev(asc_dvc->cfg->dev), offset, byte_data);
7524 #endif /* CONFIG_PCI */
7525 }
7526
7527 /*
7528  * Return the BIOS address of the adapter at the specified
7529  * I/O port and with the specified bus type.
7530  */
7531 static ushort __init AscGetChipBiosAddress(PortAddr iop_base, ushort bus_type)
7532 {
7533         ushort cfg_lsw;
7534         ushort bios_addr;
7535
7536         /*
7537          * The PCI BIOS is re-located by the motherboard BIOS. Because
7538          * of this the driver can not determine where a PCI BIOS is
7539          * loaded and executes.
7540          */
7541         if (bus_type & ASC_IS_PCI) {
7542                 return (0);
7543         }
7544 #ifdef CONFIG_ISA
7545         if ((bus_type & ASC_IS_EISA) != 0) {
7546                 cfg_lsw = AscGetEisaChipCfg(iop_base);
7547                 cfg_lsw &= 0x000F;
7548                 bios_addr = (ushort)(ASC_BIOS_MIN_ADDR +
7549                                      (cfg_lsw * ASC_BIOS_BANK_SIZE));
7550                 return (bios_addr);
7551         }                       /* if */
7552 #endif /* CONFIG_ISA */
7553
7554         cfg_lsw = AscGetChipCfgLsw(iop_base);
7555
7556         /*
7557          *  ISA PnP uses the top bit as the 32K BIOS flag
7558          */
7559         if (bus_type == ASC_IS_ISAPNP) {
7560                 cfg_lsw &= 0x7FFF;
7561         }
7562         /* if */
7563         bios_addr = (ushort)(((cfg_lsw >> 12) * ASC_BIOS_BANK_SIZE) +
7564                              ASC_BIOS_MIN_ADDR);
7565         return (bios_addr);
7566 }
7567
7568 /*
7569  * --- Functions Required by the Adv Library
7570  */
7571
7572 /*
7573  * DvcGetPhyAddr()
7574  *
7575  * Return the physical address of 'vaddr' and set '*lenp' to the
7576  * number of physically contiguous bytes that follow 'vaddr'.
7577  * 'flag' indicates the type of structure whose physical address
7578  * is being translated.
7579  *
7580  * Note: Because Linux currently doesn't page the kernel and all
7581  * kernel buffers are physically contiguous, leave '*lenp' unchanged.
7582  */
7583 ADV_PADDR
7584 DvcGetPhyAddr(ADV_DVC_VAR *asc_dvc, ADV_SCSI_REQ_Q *scsiq,
7585               uchar *vaddr, ADV_SDCNT *lenp, int flag)
7586 {
7587         ADV_PADDR paddr;
7588
7589         paddr = virt_to_bus(vaddr);
7590
7591         ASC_DBG4(4,
7592                  "DvcGetPhyAddr: vaddr 0x%lx, lenp 0x%lx *lenp %lu, paddr 0x%lx\n",
7593                  (ulong)vaddr, (ulong)lenp, (ulong)*((ulong *)lenp),
7594                  (ulong)paddr);
7595
7596         return paddr;
7597 }
7598
7599 /*
7600  * Read a PCI configuration byte.
7601  */
7602 static uchar __init DvcAdvReadPCIConfigByte(ADV_DVC_VAR *asc_dvc, ushort offset)
7603 {
7604 #ifdef CONFIG_PCI
7605         uchar byte_data;
7606         pci_read_config_byte(to_pci_dev(asc_dvc->cfg->dev), offset, &byte_data);
7607         return byte_data;
7608 #else /* CONFIG_PCI */
7609         return 0;
7610 #endif /* CONFIG_PCI */
7611 }
7612
7613 /*
7614  * Write a PCI configuration byte.
7615  */
7616 static void __init
7617 DvcAdvWritePCIConfigByte(ADV_DVC_VAR *asc_dvc, ushort offset, uchar byte_data)
7618 {
7619 #ifdef CONFIG_PCI
7620         pci_write_config_byte(to_pci_dev(asc_dvc->cfg->dev), offset, byte_data);
7621 #else /* CONFIG_PCI */
7622         return;
7623 #endif /* CONFIG_PCI */
7624 }
7625
7626 /*
7627  * --- Tracing and Debugging Functions
7628  */
7629
7630 #ifdef ADVANSYS_STATS
7631 #ifdef CONFIG_PROC_FS
7632 /*
7633  * asc_prt_board_stats()
7634  *
7635  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
7636  * cf. asc_prt_line().
7637  *
7638  * Return the number of characters copied into 'cp'. No more than
7639  * 'cplen' characters will be copied to 'cp'.
7640  */
7641 static int asc_prt_board_stats(struct Scsi_Host *shost, char *cp, int cplen)
7642 {
7643         int leftlen;
7644         int totlen;
7645         int len;
7646         struct asc_stats *s;
7647         asc_board_t *boardp;
7648
7649         leftlen = cplen;
7650         totlen = len = 0;
7651
7652         boardp = ASC_BOARDP(shost);
7653         s = &boardp->asc_stats;
7654
7655         len = asc_prt_line(cp, leftlen,
7656                            "\nLinux Driver Statistics for AdvanSys SCSI Host %d:\n",
7657                            shost->host_no);
7658         ASC_PRT_NEXT();
7659
7660         len = asc_prt_line(cp, leftlen,
7661                            " queuecommand %lu, reset %lu, biosparam %lu, interrupt %lu\n",
7662                            s->queuecommand, s->reset, s->biosparam,
7663                            s->interrupt);
7664         ASC_PRT_NEXT();
7665
7666         len = asc_prt_line(cp, leftlen,
7667                            " callback %lu, done %lu, build_error %lu, build_noreq %lu, build_nosg %lu\n",
7668                            s->callback, s->done, s->build_error,
7669                            s->adv_build_noreq, s->adv_build_nosg);
7670         ASC_PRT_NEXT();
7671
7672         len = asc_prt_line(cp, leftlen,
7673                            " exe_noerror %lu, exe_busy %lu, exe_error %lu, exe_unknown %lu\n",
7674                            s->exe_noerror, s->exe_busy, s->exe_error,
7675                            s->exe_unknown);
7676         ASC_PRT_NEXT();
7677
7678         /*
7679          * Display data transfer statistics.
7680          */
7681         if (s->cont_cnt > 0) {
7682                 len = asc_prt_line(cp, leftlen, " cont_cnt %lu, ", s->cont_cnt);
7683                 ASC_PRT_NEXT();
7684
7685                 len = asc_prt_line(cp, leftlen, "cont_xfer %lu.%01lu kb ",
7686                                    s->cont_xfer / 2,
7687                                    ASC_TENTHS(s->cont_xfer, 2));
7688                 ASC_PRT_NEXT();
7689
7690                 /* Contiguous transfer average size */
7691                 len = asc_prt_line(cp, leftlen, "avg_xfer %lu.%01lu kb\n",
7692                                    (s->cont_xfer / 2) / s->cont_cnt,
7693                                    ASC_TENTHS((s->cont_xfer / 2), s->cont_cnt));
7694                 ASC_PRT_NEXT();
7695         }
7696
7697         if (s->sg_cnt > 0) {
7698
7699                 len = asc_prt_line(cp, leftlen, " sg_cnt %lu, sg_elem %lu, ",
7700                                    s->sg_cnt, s->sg_elem);
7701                 ASC_PRT_NEXT();
7702
7703                 len = asc_prt_line(cp, leftlen, "sg_xfer %lu.%01lu kb\n",
7704                                    s->sg_xfer / 2, ASC_TENTHS(s->sg_xfer, 2));
7705                 ASC_PRT_NEXT();
7706
7707                 /* Scatter gather transfer statistics */
7708                 len = asc_prt_line(cp, leftlen, " avg_num_elem %lu.%01lu, ",
7709                                    s->sg_elem / s->sg_cnt,
7710                                    ASC_TENTHS(s->sg_elem, s->sg_cnt));
7711                 ASC_PRT_NEXT();
7712
7713                 len = asc_prt_line(cp, leftlen, "avg_elem_size %lu.%01lu kb, ",
7714                                    (s->sg_xfer / 2) / s->sg_elem,
7715                                    ASC_TENTHS((s->sg_xfer / 2), s->sg_elem));
7716                 ASC_PRT_NEXT();
7717
7718                 len = asc_prt_line(cp, leftlen, "avg_xfer_size %lu.%01lu kb\n",
7719                                    (s->sg_xfer / 2) / s->sg_cnt,
7720                                    ASC_TENTHS((s->sg_xfer / 2), s->sg_cnt));
7721                 ASC_PRT_NEXT();
7722         }
7723
7724         /*
7725          * Display request queuing statistics.
7726          */
7727         len = asc_prt_line(cp, leftlen,
7728                            " Active and Waiting Request Queues (Time Unit: %d HZ):\n",
7729                            HZ);
7730         ASC_PRT_NEXT();
7731
7732         return totlen;
7733 }
7734
7735 /*
7736  * asc_prt_target_stats()
7737  *
7738  * Note: no single line should be greater than ASC_PRTLINE_SIZE,
7739  * cf. asc_prt_line().
7740  *
7741  * This is separated from asc_prt_board_stats because a full set
7742  * of targets will overflow ASC_PRTBUF_SIZE.
7743  *
7744  * Return the number of characters copied into 'cp'. No more than
7745  * 'cplen' characters will be copied to 'cp'.
7746  */
7747 static int
7748 asc_prt_target_stats(struct Scsi_Host *shost, int tgt_id, char *cp, int cplen)
7749 {
7750         int leftlen;
7751         int totlen;
7752         int len;
7753         struct asc_stats *s;
7754         ushort chip_scsi_id;
7755         asc_board_t *boardp;
7756         asc_queue_t *active;
7757         asc_queue_t *waiting;
7758
7759         leftlen = cplen;
7760         totlen = len = 0;
7761
7762         boardp = ASC_BOARDP(shost);
7763         s = &boardp->asc_stats;
7764
7765         active = &ASC_BOARDP(shost)->active;
7766         waiting = &ASC_BOARDP(shost)->waiting;
7767
7768         if (ASC_NARROW_BOARD(boardp)) {
7769                 chip_scsi_id = boardp->dvc_cfg.asc_dvc_cfg.chip_scsi_id;
7770         } else {
7771                 chip_scsi_id = boardp->dvc_var.adv_dvc_var.chip_scsi_id;
7772         }
7773
7774         if ((chip_scsi_id == tgt_id) ||
7775             ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(tgt_id)) == 0)) {
7776                 return 0;
7777         }
7778
7779         do {
7780                 if (active->q_tot_cnt[tgt_id] > 0
7781                     || waiting->q_tot_cnt[tgt_id] > 0) {
7782                         len = asc_prt_line(cp, leftlen, " target %d\n", tgt_id);
7783                         ASC_PRT_NEXT();
7784
7785                         len = asc_prt_line(cp, leftlen,
7786                                            "   active: cnt [cur %d, max %d, tot %u], time [min %d, max %d, avg %lu.%01lu]\n",
7787                                            active->q_cur_cnt[tgt_id],
7788                                            active->q_max_cnt[tgt_id],
7789                                            active->q_tot_cnt[tgt_id],
7790                                            active->q_min_tim[tgt_id],
7791                                            active->q_max_tim[tgt_id],
7792                                            (active->q_tot_cnt[tgt_id] ==
7793                                             0) ? 0 : (active->
7794                                                       q_tot_tim[tgt_id] /
7795                                                       active->
7796                                                       q_tot_cnt[tgt_id]),
7797                                            (active->q_tot_cnt[tgt_id] ==
7798                                             0) ? 0 : ASC_TENTHS(active->
7799                                                                 q_tot_tim
7800                                                                 [tgt_id],
7801                                                                 active->
7802                                                                 q_tot_cnt
7803                                                                 [tgt_id]));
7804                         ASC_PRT_NEXT();
7805
7806                         len = asc_prt_line(cp, leftlen,
7807                                            "   waiting: cnt [cur %d, max %d, tot %u], time [min %u, max %u, avg %lu.%01lu]\n",
7808                                            waiting->q_cur_cnt[tgt_id],
7809                                            waiting->q_max_cnt[tgt_id],
7810                                            waiting->q_tot_cnt[tgt_id],
7811                                            waiting->q_min_tim[tgt_id],
7812                                            waiting->q_max_tim[tgt_id],
7813                                            (waiting->q_tot_cnt[tgt_id] ==
7814                                             0) ? 0 : (waiting->
7815                                                       q_tot_tim[tgt_id] /
7816                                                       waiting->
7817                                                       q_tot_cnt[tgt_id]),
7818                                            (waiting->q_tot_cnt[tgt_id] ==
7819                                             0) ? 0 : ASC_TENTHS(waiting->
7820                                                                 q_tot_tim
7821                                                                 [tgt_id],
7822                                                                 waiting->
7823                                                                 q_tot_cnt
7824                                                                 [tgt_id]));
7825                         ASC_PRT_NEXT();
7826                 }
7827         } while (0);
7828
7829         return totlen;
7830 }
7831 #endif /* CONFIG_PROC_FS */
7832 #endif /* ADVANSYS_STATS */
7833
7834 #ifdef ADVANSYS_DEBUG
7835 /*
7836  * asc_prt_scsi_host()
7837  */
7838 static void asc_prt_scsi_host(struct Scsi_Host *s)
7839 {
7840         asc_board_t *boardp;
7841
7842         boardp = ASC_BOARDP(s);
7843
7844         printk("Scsi_Host at addr 0x%lx\n", (ulong)s);
7845         printk(" host_busy %u, host_no %d, last_reset %d,\n",
7846                s->host_busy, s->host_no, (unsigned)s->last_reset);
7847
7848         printk(" base 0x%lx, io_port 0x%lx, n_io_port %u, irq 0x%x,\n",
7849                (ulong)s->base, (ulong)s->io_port, s->n_io_port, s->irq);
7850
7851         printk(" dma_channel %d, this_id %d, can_queue %d,\n",
7852                s->dma_channel, s->this_id, s->can_queue);
7853
7854         printk(" cmd_per_lun %d, sg_tablesize %d, unchecked_isa_dma %d\n",
7855                s->cmd_per_lun, s->sg_tablesize, s->unchecked_isa_dma);
7856
7857         if (ASC_NARROW_BOARD(boardp)) {
7858                 asc_prt_asc_dvc_var(&ASC_BOARDP(s)->dvc_var.asc_dvc_var);
7859                 asc_prt_asc_dvc_cfg(&ASC_BOARDP(s)->dvc_cfg.asc_dvc_cfg);
7860         } else {
7861                 asc_prt_adv_dvc_var(&ASC_BOARDP(s)->dvc_var.adv_dvc_var);
7862                 asc_prt_adv_dvc_cfg(&ASC_BOARDP(s)->dvc_cfg.adv_dvc_cfg);
7863         }
7864 }
7865
7866 /*
7867  * asc_prt_scsi_cmnd()
7868  */
7869 static void asc_prt_scsi_cmnd(struct scsi_cmnd *s)
7870 {
7871         printk("struct scsi_cmnd at addr 0x%lx\n", (ulong)s);
7872
7873         printk(" host 0x%lx, device 0x%lx, target %u, lun %u, channel %u,\n",
7874                (ulong)s->device->host, (ulong)s->device, s->device->id,
7875                s->device->lun, s->device->channel);
7876
7877         asc_prt_hex(" CDB", s->cmnd, s->cmd_len);
7878
7879         printk("sc_data_direction %u, resid %d\n",
7880                s->sc_data_direction, s->resid);
7881
7882         printk(" use_sg %u, sglist_len %u\n", s->use_sg, s->sglist_len);
7883
7884         printk(" serial_number 0x%x, retries %d, allowed %d\n",
7885                (unsigned)s->serial_number, s->retries, s->allowed);
7886
7887         printk(" timeout_per_command %d\n", s->timeout_per_command);
7888
7889         printk
7890             (" scsi_done 0x%lx, done 0x%lx, host_scribble 0x%lx, result 0x%x\n",
7891              (ulong)s->scsi_done, (ulong)s->done, (ulong)s->host_scribble,
7892              s->result);
7893
7894         printk(" tag %u, pid %u\n", (unsigned)s->tag, (unsigned)s->pid);
7895 }
7896
7897 /*
7898  * asc_prt_asc_dvc_var()
7899  */
7900 static void asc_prt_asc_dvc_var(ASC_DVC_VAR *h)
7901 {
7902         printk("ASC_DVC_VAR at addr 0x%lx\n", (ulong)h);
7903
7904         printk
7905             (" iop_base 0x%x, err_code 0x%x, dvc_cntl 0x%x, bug_fix_cntl %d,\n",
7906              h->iop_base, h->err_code, h->dvc_cntl, h->bug_fix_cntl);
7907
7908         printk
7909             (" bus_type %d, isr_callback 0x%lx, exe_callback 0x%lx, init_sdtr 0x%x,\n",
7910              h->bus_type, (ulong)h->isr_callback, (ulong)h->exe_callback,
7911              (unsigned)h->init_sdtr);
7912
7913         printk
7914             (" sdtr_done 0x%x, use_tagged_qng 0x%x, unit_not_ready 0x%x, chip_no 0x%x,\n",
7915              (unsigned)h->sdtr_done, (unsigned)h->use_tagged_qng,
7916              (unsigned)h->unit_not_ready, (unsigned)h->chip_no);
7917
7918         printk
7919             (" queue_full_or_busy 0x%x, start_motor 0x%x, scsi_reset_wait %u,\n",
7920              (unsigned)h->queue_full_or_busy, (unsigned)h->start_motor,
7921              (unsigned)h->scsi_reset_wait);
7922
7923         printk
7924             (" is_in_int %u, max_total_qng %u, cur_total_qng %u, in_critical_cnt %u,\n",
7925              (unsigned)h->is_in_int, (unsigned)h->max_total_qng,
7926              (unsigned)h->cur_total_qng, (unsigned)h->in_critical_cnt);
7927
7928         printk
7929             (" last_q_shortage %u, init_state 0x%x, no_scam 0x%x, pci_fix_asyn_xfer 0x%x,\n",
7930              (unsigned)h->last_q_shortage, (unsigned)h->init_state,
7931              (unsigned)h->no_scam, (unsigned)h->pci_fix_asyn_xfer);
7932
7933         printk(" cfg 0x%lx, irq_no 0x%x\n", (ulong)h->cfg, (unsigned)h->irq_no);
7934 }
7935
7936 /*
7937  * asc_prt_asc_dvc_cfg()
7938  */
7939 static void asc_prt_asc_dvc_cfg(ASC_DVC_CFG *h)
7940 {
7941         printk("ASC_DVC_CFG at addr 0x%lx\n", (ulong)h);
7942
7943         printk(" can_tagged_qng 0x%x, cmd_qng_enabled 0x%x,\n",
7944                h->can_tagged_qng, h->cmd_qng_enabled);
7945         printk(" disc_enable 0x%x, sdtr_enable 0x%x,\n",
7946                h->disc_enable, h->sdtr_enable);
7947
7948         printk
7949             (" chip_scsi_id %d, isa_dma_speed %d, isa_dma_channel %d, chip_version %d,\n",
7950              h->chip_scsi_id, h->isa_dma_speed, h->isa_dma_channel,
7951              h->chip_version);
7952
7953         printk
7954             (" pci_device_id %d, lib_serial_no %u, lib_version %u, mcode_date 0x%x,\n",
7955              to_pci_dev(h->dev)->device, h->lib_serial_no, h->lib_version,
7956              h->mcode_date);
7957
7958         printk(" mcode_version %d, overrun_buf 0x%lx\n",
7959                h->mcode_version, (ulong)h->overrun_buf);
7960 }
7961
7962 /*
7963  * asc_prt_asc_scsi_q()
7964  */
7965 static void asc_prt_asc_scsi_q(ASC_SCSI_Q *q)
7966 {
7967         ASC_SG_HEAD *sgp;
7968         int i;
7969
7970         printk("ASC_SCSI_Q at addr 0x%lx\n", (ulong)q);
7971
7972         printk
7973             (" target_ix 0x%x, target_lun %u, srb_ptr 0x%lx, tag_code 0x%x,\n",
7974              q->q2.target_ix, q->q1.target_lun, (ulong)q->q2.srb_ptr,
7975              q->q2.tag_code);
7976
7977         printk
7978             (" data_addr 0x%lx, data_cnt %lu, sense_addr 0x%lx, sense_len %u,\n",
7979              (ulong)le32_to_cpu(q->q1.data_addr),
7980              (ulong)le32_to_cpu(q->q1.data_cnt),
7981              (ulong)le32_to_cpu(q->q1.sense_addr), q->q1.sense_len);
7982
7983         printk(" cdbptr 0x%lx, cdb_len %u, sg_head 0x%lx, sg_queue_cnt %u\n",
7984                (ulong)q->cdbptr, q->q2.cdb_len,
7985                (ulong)q->sg_head, q->q1.sg_queue_cnt);
7986
7987         if (q->sg_head) {
7988                 sgp = q->sg_head;
7989                 printk("ASC_SG_HEAD at addr 0x%lx\n", (ulong)sgp);
7990                 printk(" entry_cnt %u, queue_cnt %u\n", sgp->entry_cnt,
7991                        sgp->queue_cnt);
7992                 for (i = 0; i < sgp->entry_cnt; i++) {
7993                         printk(" [%u]: addr 0x%lx, bytes %lu\n",
7994                                i, (ulong)le32_to_cpu(sgp->sg_list[i].addr),
7995                                (ulong)le32_to_cpu(sgp->sg_list[i].bytes));
7996                 }
7997
7998         }
7999 }
8000
8001 /*
8002  * asc_prt_asc_qdone_info()
8003  */
8004 static void asc_prt_asc_qdone_info(ASC_QDONE_INFO *q)
8005 {
8006         printk("ASC_QDONE_INFO at addr 0x%lx\n", (ulong)q);
8007         printk(" srb_ptr 0x%lx, target_ix %u, cdb_len %u, tag_code %u,\n",
8008                (ulong)q->d2.srb_ptr, q->d2.target_ix, q->d2.cdb_len,
8009                q->d2.tag_code);
8010         printk
8011             (" done_stat 0x%x, host_stat 0x%x, scsi_stat 0x%x, scsi_msg 0x%x\n",
8012              q->d3.done_stat, q->d3.host_stat, q->d3.scsi_stat, q->d3.scsi_msg);
8013 }
8014
8015 /*
8016  * asc_prt_adv_dvc_var()
8017  *
8018  * Display an ADV_DVC_VAR structure.
8019  */
8020 static void asc_prt_adv_dvc_var(ADV_DVC_VAR *h)
8021 {
8022         printk(" ADV_DVC_VAR at addr 0x%lx\n", (ulong)h);
8023
8024         printk("  iop_base 0x%lx, err_code 0x%x, ultra_able 0x%x\n",
8025                (ulong)h->iop_base, h->err_code, (unsigned)h->ultra_able);
8026
8027         printk("  isr_callback 0x%lx, sdtr_able 0x%x, wdtr_able 0x%x\n",
8028                (ulong)h->isr_callback, (unsigned)h->sdtr_able,
8029                (unsigned)h->wdtr_able);
8030
8031         printk("  start_motor 0x%x, scsi_reset_wait 0x%x, irq_no 0x%x,\n",
8032                (unsigned)h->start_motor,
8033                (unsigned)h->scsi_reset_wait, (unsigned)h->irq_no);
8034
8035         printk("  max_host_qng %u, max_dvc_qng %u, carr_freelist 0x%lxn\n",
8036                (unsigned)h->max_host_qng, (unsigned)h->max_dvc_qng,
8037                (ulong)h->carr_freelist);
8038
8039         printk("  icq_sp 0x%lx, irq_sp 0x%lx\n",
8040                (ulong)h->icq_sp, (ulong)h->irq_sp);
8041
8042         printk("  no_scam 0x%x, tagqng_able 0x%x\n",
8043                (unsigned)h->no_scam, (unsigned)h->tagqng_able);
8044
8045         printk("  chip_scsi_id 0x%x, cfg 0x%lx\n",
8046                (unsigned)h->chip_scsi_id, (ulong)h->cfg);
8047 }
8048
8049 /*
8050  * asc_prt_adv_dvc_cfg()
8051  *
8052  * Display an ADV_DVC_CFG structure.
8053  */
8054 static void asc_prt_adv_dvc_cfg(ADV_DVC_CFG *h)
8055 {
8056         printk(" ADV_DVC_CFG at addr 0x%lx\n", (ulong)h);
8057
8058         printk("  disc_enable 0x%x, termination 0x%x\n",
8059                h->disc_enable, h->termination);
8060
8061         printk("  chip_version 0x%x, mcode_date 0x%x\n",
8062                h->chip_version, h->mcode_date);
8063
8064         printk("  mcode_version 0x%x, pci_device_id 0x%x, lib_version %u\n",
8065                h->mcode_version, to_pci_dev(h->dev)->device, h->lib_version);
8066
8067         printk("  control_flag 0x%x, pci_slot_info 0x%x\n",
8068                h->control_flag, h->pci_slot_info);
8069 }
8070
8071 /*
8072  * asc_prt_adv_scsi_req_q()
8073  *
8074  * Display an ADV_SCSI_REQ_Q structure.
8075  */
8076 static void asc_prt_adv_scsi_req_q(ADV_SCSI_REQ_Q *q)
8077 {
8078         int sg_blk_cnt;
8079         struct asc_sg_block *sg_ptr;
8080
8081         printk("ADV_SCSI_REQ_Q at addr 0x%lx\n", (ulong)q);
8082
8083         printk("  target_id %u, target_lun %u, srb_ptr 0x%lx, a_flag 0x%x\n",
8084                q->target_id, q->target_lun, (ulong)q->srb_ptr, q->a_flag);
8085
8086         printk("  cntl 0x%x, data_addr 0x%lx, vdata_addr 0x%lx\n",
8087                q->cntl, (ulong)le32_to_cpu(q->data_addr), (ulong)q->vdata_addr);
8088
8089         printk("  data_cnt %lu, sense_addr 0x%lx, sense_len %u,\n",
8090                (ulong)le32_to_cpu(q->data_cnt),
8091                (ulong)le32_to_cpu(q->sense_addr), q->sense_len);
8092
8093         printk
8094             ("  cdb_len %u, done_status 0x%x, host_status 0x%x, scsi_status 0x%x\n",
8095              q->cdb_len, q->done_status, q->host_status, q->scsi_status);
8096
8097         printk("  sg_working_ix 0x%x, target_cmd %u\n",
8098                q->sg_working_ix, q->target_cmd);
8099
8100         printk("  scsiq_rptr 0x%lx, sg_real_addr 0x%lx, sg_list_ptr 0x%lx\n",
8101                (ulong)le32_to_cpu(q->scsiq_rptr),
8102                (ulong)le32_to_cpu(q->sg_real_addr), (ulong)q->sg_list_ptr);
8103
8104         /* Display the request's ADV_SG_BLOCK structures. */
8105         if (q->sg_list_ptr != NULL) {
8106                 sg_blk_cnt = 0;
8107                 while (1) {
8108                         /*
8109                          * 'sg_ptr' is a physical address. Convert it to a virtual
8110                          * address by indexing 'sg_blk_cnt' into the virtual address
8111                          * array 'sg_list_ptr'.
8112                          *
8113                          * XXX - Assumes all SG physical blocks are virtually contiguous.
8114                          */
8115                         sg_ptr =
8116                             &(((ADV_SG_BLOCK *)(q->sg_list_ptr))[sg_blk_cnt]);
8117                         asc_prt_adv_sgblock(sg_blk_cnt, sg_ptr);
8118                         if (sg_ptr->sg_ptr == 0) {
8119                                 break;
8120                         }
8121                         sg_blk_cnt++;
8122                 }
8123         }
8124 }
8125
8126 /*
8127  * asc_prt_adv_sgblock()
8128  *
8129  * Display an ADV_SG_BLOCK structure.
8130  */
8131 static void asc_prt_adv_sgblock(int sgblockno, ADV_SG_BLOCK *b)
8132 {
8133         int i;
8134
8135         printk(" ASC_SG_BLOCK at addr 0x%lx (sgblockno %d)\n",
8136                (ulong)b, sgblockno);
8137         printk("  sg_cnt %u, sg_ptr 0x%lx\n",
8138                b->sg_cnt, (ulong)le32_to_cpu(b->sg_ptr));
8139         ASC_ASSERT(b->sg_cnt <= NO_OF_SG_PER_BLOCK);
8140         if (b->sg_ptr != 0) {
8141                 ASC_ASSERT(b->sg_cnt == NO_OF_SG_PER_BLOCK);
8142         }
8143         for (i = 0; i < b->sg_cnt; i++) {
8144                 printk("  [%u]: sg_addr 0x%lx, sg_count 0x%lx\n",
8145                        i, (ulong)b->sg_list[i].sg_addr,
8146                        (ulong)b->sg_list[i].sg_count);
8147         }
8148 }
8149
8150 /*
8151  * asc_prt_hex()
8152  *
8153  * Print hexadecimal output in 4 byte groupings 32 bytes
8154  * or 8 double-words per line.
8155  */
8156 static void asc_prt_hex(char *f, uchar *s, int l)
8157 {
8158         int i;
8159         int j;
8160         int k;
8161         int m;
8162
8163         printk("%s: (%d bytes)\n", f, l);
8164
8165         for (i = 0; i < l; i += 32) {
8166
8167                 /* Display a maximum of 8 double-words per line. */
8168                 if ((k = (l - i) / 4) >= 8) {
8169                         k = 8;
8170                         m = 0;
8171                 } else {
8172                         m = (l - i) % 4;
8173                 }
8174
8175                 for (j = 0; j < k; j++) {
8176                         printk(" %2.2X%2.2X%2.2X%2.2X",
8177                                (unsigned)s[i + (j * 4)],
8178                                (unsigned)s[i + (j * 4) + 1],
8179                                (unsigned)s[i + (j * 4) + 2],
8180                                (unsigned)s[i + (j * 4) + 3]);
8181                 }
8182
8183                 switch (m) {
8184                 case 0:
8185                 default:
8186                         break;
8187                 case 1:
8188                         printk(" %2.2X", (unsigned)s[i + (j * 4)]);
8189                         break;
8190                 case 2:
8191                         printk(" %2.2X%2.2X",
8192                                (unsigned)s[i + (j * 4)],
8193                                (unsigned)s[i + (j * 4) + 1]);
8194                         break;
8195                 case 3:
8196                         printk(" %2.2X%2.2X%2.2X",
8197                                (unsigned)s[i + (j * 4) + 1],
8198                                (unsigned)s[i + (j * 4) + 2],
8199                                (unsigned)s[i + (j * 4) + 3]);
8200                         break;
8201                 }
8202
8203                 printk("\n");
8204         }
8205 }
8206 #endif /* ADVANSYS_DEBUG */
8207
8208 /*
8209  * --- Asc Library Functions
8210  */
8211
8212 static ushort __init AscGetEisaChipCfg(PortAddr iop_base)
8213 {
8214         PortAddr eisa_cfg_iop;
8215
8216         eisa_cfg_iop = (PortAddr) ASC_GET_EISA_SLOT(iop_base) |
8217             (PortAddr) (ASC_EISA_CFG_IOP_MASK);
8218         return (inpw(eisa_cfg_iop));
8219 }
8220
8221 static uchar __init AscSetChipScsiID(PortAddr iop_base, uchar new_host_id)
8222 {
8223         ushort cfg_lsw;
8224
8225         if (AscGetChipScsiID(iop_base) == new_host_id) {
8226                 return (new_host_id);
8227         }
8228         cfg_lsw = AscGetChipCfgLsw(iop_base);
8229         cfg_lsw &= 0xF8FF;
8230         cfg_lsw |= (ushort)((new_host_id & ASC_MAX_TID) << 8);
8231         AscSetChipCfgLsw(iop_base, cfg_lsw);
8232         return (AscGetChipScsiID(iop_base));
8233 }
8234
8235 static uchar __init AscGetChipScsiCtrl(PortAddr iop_base)
8236 {
8237         uchar sc;
8238
8239         AscSetBank(iop_base, 1);
8240         sc = inp(iop_base + IOP_REG_SC);
8241         AscSetBank(iop_base, 0);
8242         return (sc);
8243 }
8244
8245 static uchar __init AscGetChipVersion(PortAddr iop_base, ushort bus_type)
8246 {
8247         if ((bus_type & ASC_IS_EISA) != 0) {
8248                 PortAddr eisa_iop;
8249                 uchar revision;
8250                 eisa_iop = (PortAddr) ASC_GET_EISA_SLOT(iop_base) |
8251                     (PortAddr) ASC_EISA_REV_IOP_MASK;
8252                 revision = inp(eisa_iop);
8253                 return ((uchar)((ASC_CHIP_MIN_VER_EISA - 1) + revision));
8254         }
8255         return (AscGetChipVerNo(iop_base));
8256 }
8257
8258 static ushort __init AscGetChipBusType(PortAddr iop_base)
8259 {
8260         ushort chip_ver;
8261
8262         chip_ver = AscGetChipVerNo(iop_base);
8263         if ((chip_ver >= ASC_CHIP_MIN_VER_VL)
8264             && (chip_ver <= ASC_CHIP_MAX_VER_VL)
8265             ) {
8266                 if (((iop_base & 0x0C30) == 0x0C30)
8267                     || ((iop_base & 0x0C50) == 0x0C50)
8268                     ) {
8269                         return (ASC_IS_EISA);
8270                 }
8271                 return (ASC_IS_VL);
8272         }
8273         if ((chip_ver >= ASC_CHIP_MIN_VER_ISA) &&
8274             (chip_ver <= ASC_CHIP_MAX_VER_ISA)) {
8275                 if (chip_ver >= ASC_CHIP_MIN_VER_ISA_PNP) {
8276                         return (ASC_IS_ISAPNP);
8277                 }
8278                 return (ASC_IS_ISA);
8279         } else if ((chip_ver >= ASC_CHIP_MIN_VER_PCI) &&
8280                    (chip_ver <= ASC_CHIP_MAX_VER_PCI)) {
8281                 return (ASC_IS_PCI);
8282         }
8283         return (0);
8284 }
8285
8286 static ASC_DCNT
8287 AscLoadMicroCode(PortAddr iop_base,
8288                  ushort s_addr, uchar *mcode_buf, ushort mcode_size)
8289 {
8290         ASC_DCNT chksum;
8291         ushort mcode_word_size;
8292         ushort mcode_chksum;
8293
8294         /* Write the microcode buffer starting at LRAM address 0. */
8295         mcode_word_size = (ushort)(mcode_size >> 1);
8296         AscMemWordSetLram(iop_base, s_addr, 0, mcode_word_size);
8297         AscMemWordCopyPtrToLram(iop_base, s_addr, mcode_buf, mcode_word_size);
8298
8299         chksum = AscMemSumLramWord(iop_base, s_addr, mcode_word_size);
8300         ASC_DBG1(1, "AscLoadMicroCode: chksum 0x%lx\n", (ulong)chksum);
8301         mcode_chksum = (ushort)AscMemSumLramWord(iop_base,
8302                                                  (ushort)ASC_CODE_SEC_BEG,
8303                                                  (ushort)((mcode_size -
8304                                                            s_addr - (ushort)
8305                                                            ASC_CODE_SEC_BEG) /
8306                                                           2));
8307         ASC_DBG1(1, "AscLoadMicroCode: mcode_chksum 0x%lx\n",
8308                  (ulong)mcode_chksum);
8309         AscWriteLramWord(iop_base, ASCV_MCODE_CHKSUM_W, mcode_chksum);
8310         AscWriteLramWord(iop_base, ASCV_MCODE_SIZE_W, mcode_size);
8311         return (chksum);
8312 }
8313
8314 static int AscFindSignature(PortAddr iop_base)
8315 {
8316         ushort sig_word;
8317
8318         ASC_DBG2(1, "AscFindSignature: AscGetChipSignatureByte(0x%x) 0x%x\n",
8319                  iop_base, AscGetChipSignatureByte(iop_base));
8320         if (AscGetChipSignatureByte(iop_base) == (uchar)ASC_1000_ID1B) {
8321                 ASC_DBG2(1,
8322                          "AscFindSignature: AscGetChipSignatureWord(0x%x) 0x%x\n",
8323                          iop_base, AscGetChipSignatureWord(iop_base));
8324                 sig_word = AscGetChipSignatureWord(iop_base);
8325                 if ((sig_word == (ushort)ASC_1000_ID0W) ||
8326                     (sig_word == (ushort)ASC_1000_ID0W_FIX)) {
8327                         return (1);
8328                 }
8329         }
8330         return (0);
8331 }
8332
8333 static PortAddr _asc_def_iop_base[ASC_IOADR_TABLE_MAX_IX] __initdata = {
8334         0x100, ASC_IOADR_1, 0x120, ASC_IOADR_2, 0x140, ASC_IOADR_3, ASC_IOADR_4,
8335         ASC_IOADR_5, ASC_IOADR_6, ASC_IOADR_7, ASC_IOADR_8
8336 };
8337
8338 #ifdef CONFIG_ISA
8339 static uchar _isa_pnp_inited __initdata = 0;
8340
8341 static PortAddr __init AscSearchIOPortAddr(PortAddr iop_beg, ushort bus_type)
8342 {
8343         if (bus_type & ASC_IS_VL) {
8344                 while ((iop_beg = AscSearchIOPortAddr11(iop_beg)) != 0) {
8345                         if (AscGetChipVersion(iop_beg, bus_type) <=
8346                             ASC_CHIP_MAX_VER_VL) {
8347                                 return (iop_beg);
8348                         }
8349                 }
8350                 return (0);
8351         }
8352         if (bus_type & ASC_IS_ISA) {
8353                 if (_isa_pnp_inited == 0) {
8354                         AscSetISAPNPWaitForKey();
8355                         _isa_pnp_inited++;
8356                 }
8357                 while ((iop_beg = AscSearchIOPortAddr11(iop_beg)) != 0) {
8358                         if ((AscGetChipVersion(iop_beg, bus_type) &
8359                              ASC_CHIP_VER_ISA_BIT) != 0) {
8360                                 return (iop_beg);
8361                         }
8362                 }
8363                 return (0);
8364         }
8365         if (bus_type & ASC_IS_EISA) {
8366                 if ((iop_beg = AscSearchIOPortAddrEISA(iop_beg)) != 0) {
8367                         return (iop_beg);
8368                 }
8369                 return (0);
8370         }
8371         return (0);
8372 }
8373
8374 static PortAddr __init AscSearchIOPortAddr11(PortAddr s_addr)
8375 {
8376         int i;
8377         PortAddr iop_base;
8378
8379         for (i = 0; i < ASC_IOADR_TABLE_MAX_IX; i++) {
8380                 if (_asc_def_iop_base[i] > s_addr) {
8381                         break;
8382                 }
8383         }
8384         for (; i < ASC_IOADR_TABLE_MAX_IX; i++) {
8385                 iop_base = _asc_def_iop_base[i];
8386                 if (!request_region(iop_base, ASC_IOADR_GAP, "advansys")) {
8387                         ASC_DBG1(1,
8388                                  "AscSearchIOPortAddr11: check_region() failed I/O port 0x%x\n",
8389                                  iop_base);
8390                         continue;
8391                 }
8392                 ASC_DBG1(1, "AscSearchIOPortAddr11: probing I/O port 0x%x\n",
8393                          iop_base);
8394                 release_region(iop_base, ASC_IOADR_GAP);
8395                 if (AscFindSignature(iop_base)) {
8396                         return (iop_base);
8397                 }
8398         }
8399         return (0);
8400 }
8401
8402 static void __init AscSetISAPNPWaitForKey(void)
8403 {
8404         outp(ASC_ISA_PNP_PORT_ADDR, 0x02);
8405         outp(ASC_ISA_PNP_PORT_WRITE, 0x02);
8406         return;
8407 }
8408 #endif /* CONFIG_ISA */
8409
8410 static void __init AscToggleIRQAct(PortAddr iop_base)
8411 {
8412         AscSetChipStatus(iop_base, CIW_IRQ_ACT);
8413         AscSetChipStatus(iop_base, 0);
8414         return;
8415 }
8416
8417 static uchar __init AscGetChipIRQ(PortAddr iop_base, ushort bus_type)
8418 {
8419         ushort cfg_lsw;
8420         uchar chip_irq;
8421
8422         if ((bus_type & ASC_IS_EISA) != 0) {
8423                 cfg_lsw = AscGetEisaChipCfg(iop_base);
8424                 chip_irq = (uchar)(((cfg_lsw >> 8) & 0x07) + 10);
8425                 if ((chip_irq == 13) || (chip_irq > 15)) {
8426                         return (0);
8427                 }
8428                 return (chip_irq);
8429         }
8430         if ((bus_type & ASC_IS_VL) != 0) {
8431                 cfg_lsw = AscGetChipCfgLsw(iop_base);
8432                 chip_irq = (uchar)(((cfg_lsw >> 2) & 0x07));
8433                 if ((chip_irq == 0) || (chip_irq == 4) || (chip_irq == 7)) {
8434                         return (0);
8435                 }
8436                 return ((uchar)(chip_irq + (ASC_MIN_IRQ_NO - 1)));
8437         }
8438         cfg_lsw = AscGetChipCfgLsw(iop_base);
8439         chip_irq = (uchar)(((cfg_lsw >> 2) & 0x03));
8440         if (chip_irq == 3)
8441                 chip_irq += (uchar)2;
8442         return ((uchar)(chip_irq + ASC_MIN_IRQ_NO));
8443 }
8444
8445 static uchar __init
8446 AscSetChipIRQ(PortAddr iop_base, uchar irq_no, ushort bus_type)
8447 {
8448         ushort cfg_lsw;
8449
8450         if ((bus_type & ASC_IS_VL) != 0) {
8451                 if (irq_no != 0) {
8452                         if ((irq_no < ASC_MIN_IRQ_NO)
8453                             || (irq_no > ASC_MAX_IRQ_NO)) {
8454                                 irq_no = 0;
8455                         } else {
8456                                 irq_no -= (uchar)((ASC_MIN_IRQ_NO - 1));
8457                         }
8458                 }
8459                 cfg_lsw = (ushort)(AscGetChipCfgLsw(iop_base) & 0xFFE3);
8460                 cfg_lsw |= (ushort)0x0010;
8461                 AscSetChipCfgLsw(iop_base, cfg_lsw);
8462                 AscToggleIRQAct(iop_base);
8463                 cfg_lsw = (ushort)(AscGetChipCfgLsw(iop_base) & 0xFFE0);
8464                 cfg_lsw |= (ushort)((irq_no & 0x07) << 2);
8465                 AscSetChipCfgLsw(iop_base, cfg_lsw);
8466                 AscToggleIRQAct(iop_base);
8467                 return (AscGetChipIRQ(iop_base, bus_type));
8468         }
8469         if ((bus_type & (ASC_IS_ISA)) != 0) {
8470                 if (irq_no == 15)
8471                         irq_no -= (uchar)2;
8472                 irq_no -= (uchar)ASC_MIN_IRQ_NO;
8473                 cfg_lsw = (ushort)(AscGetChipCfgLsw(iop_base) & 0xFFF3);
8474                 cfg_lsw |= (ushort)((irq_no & 0x03) << 2);
8475                 AscSetChipCfgLsw(iop_base, cfg_lsw);
8476                 return (AscGetChipIRQ(iop_base, bus_type));
8477         }
8478         return (0);
8479 }
8480
8481 #ifdef CONFIG_ISA
8482 static void __init AscEnableIsaDma(uchar dma_channel)
8483 {
8484         if (dma_channel < 4) {
8485                 outp(0x000B, (ushort)(0xC0 | dma_channel));
8486                 outp(0x000A, dma_channel);
8487         } else if (dma_channel < 8) {
8488                 outp(0x00D6, (ushort)(0xC0 | (dma_channel - 4)));
8489                 outp(0x00D4, (ushort)(dma_channel - 4));
8490         }
8491         return;
8492 }
8493 #endif /* CONFIG_ISA */
8494
8495 static int AscIsrChipHalted(ASC_DVC_VAR *asc_dvc)
8496 {
8497         EXT_MSG ext_msg;
8498         EXT_MSG out_msg;
8499         ushort halt_q_addr;
8500         int sdtr_accept;
8501         ushort int_halt_code;
8502         ASC_SCSI_BIT_ID_TYPE scsi_busy;
8503         ASC_SCSI_BIT_ID_TYPE target_id;
8504         PortAddr iop_base;
8505         uchar tag_code;
8506         uchar q_status;
8507         uchar halt_qp;
8508         uchar sdtr_data;
8509         uchar target_ix;
8510         uchar q_cntl, tid_no;
8511         uchar cur_dvc_qng;
8512         uchar asyn_sdtr;
8513         uchar scsi_status;
8514         asc_board_t *boardp;
8515
8516         ASC_ASSERT(asc_dvc->drv_ptr != NULL);
8517         boardp = asc_dvc->drv_ptr;
8518
8519         iop_base = asc_dvc->iop_base;
8520         int_halt_code = AscReadLramWord(iop_base, ASCV_HALTCODE_W);
8521
8522         halt_qp = AscReadLramByte(iop_base, ASCV_CURCDB_B);
8523         halt_q_addr = ASC_QNO_TO_QADDR(halt_qp);
8524         target_ix = AscReadLramByte(iop_base,
8525                                     (ushort)(halt_q_addr +
8526                                              (ushort)ASC_SCSIQ_B_TARGET_IX));
8527         q_cntl =
8528             AscReadLramByte(iop_base,
8529                             (ushort)(halt_q_addr + (ushort)ASC_SCSIQ_B_CNTL));
8530         tid_no = ASC_TIX_TO_TID(target_ix);
8531         target_id = (uchar)ASC_TID_TO_TARGET_ID(tid_no);
8532         if (asc_dvc->pci_fix_asyn_xfer & target_id) {
8533                 asyn_sdtr = ASYN_SDTR_DATA_FIX_PCI_REV_AB;
8534         } else {
8535                 asyn_sdtr = 0;
8536         }
8537         if (int_halt_code == ASC_HALT_DISABLE_ASYN_USE_SYN_FIX) {
8538                 if (asc_dvc->pci_fix_asyn_xfer & target_id) {
8539                         AscSetChipSDTR(iop_base, 0, tid_no);
8540                         boardp->sdtr_data[tid_no] = 0;
8541                 }
8542                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8543                 return (0);
8544         } else if (int_halt_code == ASC_HALT_ENABLE_ASYN_USE_SYN_FIX) {
8545                 if (asc_dvc->pci_fix_asyn_xfer & target_id) {
8546                         AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
8547                         boardp->sdtr_data[tid_no] = asyn_sdtr;
8548                 }
8549                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8550                 return (0);
8551         } else if (int_halt_code == ASC_HALT_EXTMSG_IN) {
8552
8553                 AscMemWordCopyPtrFromLram(iop_base,
8554                                           ASCV_MSGIN_BEG,
8555                                           (uchar *)&ext_msg,
8556                                           sizeof(EXT_MSG) >> 1);
8557
8558                 if (ext_msg.msg_type == MS_EXTEND &&
8559                     ext_msg.msg_req == MS_SDTR_CODE &&
8560                     ext_msg.msg_len == MS_SDTR_LEN) {
8561                         sdtr_accept = TRUE;
8562                         if ((ext_msg.req_ack_offset > ASC_SYN_MAX_OFFSET)) {
8563
8564                                 sdtr_accept = FALSE;
8565                                 ext_msg.req_ack_offset = ASC_SYN_MAX_OFFSET;
8566                         }
8567                         if ((ext_msg.xfer_period <
8568                              asc_dvc->sdtr_period_tbl[asc_dvc->
8569                                                       host_init_sdtr_index])
8570                             || (ext_msg.xfer_period >
8571                                 asc_dvc->sdtr_period_tbl[asc_dvc->
8572                                                          max_sdtr_index])) {
8573                                 sdtr_accept = FALSE;
8574                                 ext_msg.xfer_period =
8575                                     asc_dvc->sdtr_period_tbl[asc_dvc->
8576                                                              host_init_sdtr_index];
8577                         }
8578                         if (sdtr_accept) {
8579                                 sdtr_data =
8580                                     AscCalSDTRData(asc_dvc, ext_msg.xfer_period,
8581                                                    ext_msg.req_ack_offset);
8582                                 if ((sdtr_data == 0xFF)) {
8583
8584                                         q_cntl |= QC_MSG_OUT;
8585                                         asc_dvc->init_sdtr &= ~target_id;
8586                                         asc_dvc->sdtr_done &= ~target_id;
8587                                         AscSetChipSDTR(iop_base, asyn_sdtr,
8588                                                        tid_no);
8589                                         boardp->sdtr_data[tid_no] = asyn_sdtr;
8590                                 }
8591                         }
8592                         if (ext_msg.req_ack_offset == 0) {
8593
8594                                 q_cntl &= ~QC_MSG_OUT;
8595                                 asc_dvc->init_sdtr &= ~target_id;
8596                                 asc_dvc->sdtr_done &= ~target_id;
8597                                 AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
8598                         } else {
8599                                 if (sdtr_accept && (q_cntl & QC_MSG_OUT)) {
8600
8601                                         q_cntl &= ~QC_MSG_OUT;
8602                                         asc_dvc->sdtr_done |= target_id;
8603                                         asc_dvc->init_sdtr |= target_id;
8604                                         asc_dvc->pci_fix_asyn_xfer &=
8605                                             ~target_id;
8606                                         sdtr_data =
8607                                             AscCalSDTRData(asc_dvc,
8608                                                            ext_msg.xfer_period,
8609                                                            ext_msg.
8610                                                            req_ack_offset);
8611                                         AscSetChipSDTR(iop_base, sdtr_data,
8612                                                        tid_no);
8613                                         boardp->sdtr_data[tid_no] = sdtr_data;
8614                                 } else {
8615
8616                                         q_cntl |= QC_MSG_OUT;
8617                                         AscMsgOutSDTR(asc_dvc,
8618                                                       ext_msg.xfer_period,
8619                                                       ext_msg.req_ack_offset);
8620                                         asc_dvc->pci_fix_asyn_xfer &=
8621                                             ~target_id;
8622                                         sdtr_data =
8623                                             AscCalSDTRData(asc_dvc,
8624                                                            ext_msg.xfer_period,
8625                                                            ext_msg.
8626                                                            req_ack_offset);
8627                                         AscSetChipSDTR(iop_base, sdtr_data,
8628                                                        tid_no);
8629                                         boardp->sdtr_data[tid_no] = sdtr_data;
8630                                         asc_dvc->sdtr_done |= target_id;
8631                                         asc_dvc->init_sdtr |= target_id;
8632                                 }
8633                         }
8634
8635                         AscWriteLramByte(iop_base,
8636                                          (ushort)(halt_q_addr +
8637                                                   (ushort)ASC_SCSIQ_B_CNTL),
8638                                          q_cntl);
8639                         AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8640                         return (0);
8641                 } else if (ext_msg.msg_type == MS_EXTEND &&
8642                            ext_msg.msg_req == MS_WDTR_CODE &&
8643                            ext_msg.msg_len == MS_WDTR_LEN) {
8644
8645                         ext_msg.wdtr_width = 0;
8646                         AscMemWordCopyPtrToLram(iop_base,
8647                                                 ASCV_MSGOUT_BEG,
8648                                                 (uchar *)&ext_msg,
8649                                                 sizeof(EXT_MSG) >> 1);
8650                         q_cntl |= QC_MSG_OUT;
8651                         AscWriteLramByte(iop_base,
8652                                          (ushort)(halt_q_addr +
8653                                                   (ushort)ASC_SCSIQ_B_CNTL),
8654                                          q_cntl);
8655                         AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8656                         return (0);
8657                 } else {
8658
8659                         ext_msg.msg_type = MESSAGE_REJECT;
8660                         AscMemWordCopyPtrToLram(iop_base,
8661                                                 ASCV_MSGOUT_BEG,
8662                                                 (uchar *)&ext_msg,
8663                                                 sizeof(EXT_MSG) >> 1);
8664                         q_cntl |= QC_MSG_OUT;
8665                         AscWriteLramByte(iop_base,
8666                                          (ushort)(halt_q_addr +
8667                                                   (ushort)ASC_SCSIQ_B_CNTL),
8668                                          q_cntl);
8669                         AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8670                         return (0);
8671                 }
8672         } else if (int_halt_code == ASC_HALT_CHK_CONDITION) {
8673
8674                 q_cntl |= QC_REQ_SENSE;
8675
8676                 if ((asc_dvc->init_sdtr & target_id) != 0) {
8677
8678                         asc_dvc->sdtr_done &= ~target_id;
8679
8680                         sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
8681                         q_cntl |= QC_MSG_OUT;
8682                         AscMsgOutSDTR(asc_dvc,
8683                                       asc_dvc->
8684                                       sdtr_period_tbl[(sdtr_data >> 4) &
8685                                                       (uchar)(asc_dvc->
8686                                                               max_sdtr_index -
8687                                                               1)],
8688                                       (uchar)(sdtr_data & (uchar)
8689                                               ASC_SYN_MAX_OFFSET));
8690                 }
8691
8692                 AscWriteLramByte(iop_base,
8693                                  (ushort)(halt_q_addr +
8694                                           (ushort)ASC_SCSIQ_B_CNTL), q_cntl);
8695
8696                 tag_code = AscReadLramByte(iop_base,
8697                                            (ushort)(halt_q_addr + (ushort)
8698                                                     ASC_SCSIQ_B_TAG_CODE));
8699                 tag_code &= 0xDC;
8700                 if ((asc_dvc->pci_fix_asyn_xfer & target_id)
8701                     && !(asc_dvc->pci_fix_asyn_xfer_always & target_id)
8702                     ) {
8703
8704                         tag_code |= (ASC_TAG_FLAG_DISABLE_DISCONNECT
8705                                      | ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX);
8706
8707                 }
8708                 AscWriteLramByte(iop_base,
8709                                  (ushort)(halt_q_addr +
8710                                           (ushort)ASC_SCSIQ_B_TAG_CODE),
8711                                  tag_code);
8712
8713                 q_status = AscReadLramByte(iop_base,
8714                                            (ushort)(halt_q_addr + (ushort)
8715                                                     ASC_SCSIQ_B_STATUS));
8716                 q_status |= (QS_READY | QS_BUSY);
8717                 AscWriteLramByte(iop_base,
8718                                  (ushort)(halt_q_addr +
8719                                           (ushort)ASC_SCSIQ_B_STATUS),
8720                                  q_status);
8721
8722                 scsi_busy = AscReadLramByte(iop_base, (ushort)ASCV_SCSIBUSY_B);
8723                 scsi_busy &= ~target_id;
8724                 AscWriteLramByte(iop_base, (ushort)ASCV_SCSIBUSY_B, scsi_busy);
8725
8726                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8727                 return (0);
8728         } else if (int_halt_code == ASC_HALT_SDTR_REJECTED) {
8729
8730                 AscMemWordCopyPtrFromLram(iop_base,
8731                                           ASCV_MSGOUT_BEG,
8732                                           (uchar *)&out_msg,
8733                                           sizeof(EXT_MSG) >> 1);
8734
8735                 if ((out_msg.msg_type == MS_EXTEND) &&
8736                     (out_msg.msg_len == MS_SDTR_LEN) &&
8737                     (out_msg.msg_req == MS_SDTR_CODE)) {
8738
8739                         asc_dvc->init_sdtr &= ~target_id;
8740                         asc_dvc->sdtr_done &= ~target_id;
8741                         AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
8742                         boardp->sdtr_data[tid_no] = asyn_sdtr;
8743                 }
8744                 q_cntl &= ~QC_MSG_OUT;
8745                 AscWriteLramByte(iop_base,
8746                                  (ushort)(halt_q_addr +
8747                                           (ushort)ASC_SCSIQ_B_CNTL), q_cntl);
8748                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8749                 return (0);
8750         } else if (int_halt_code == ASC_HALT_SS_QUEUE_FULL) {
8751
8752                 scsi_status = AscReadLramByte(iop_base,
8753                                               (ushort)((ushort)halt_q_addr +
8754                                                        (ushort)
8755                                                        ASC_SCSIQ_SCSI_STATUS));
8756                 cur_dvc_qng =
8757                     AscReadLramByte(iop_base,
8758                                     (ushort)((ushort)ASC_QADR_BEG +
8759                                              (ushort)target_ix));
8760                 if ((cur_dvc_qng > 0) && (asc_dvc->cur_dvc_qng[tid_no] > 0)) {
8761
8762                         scsi_busy = AscReadLramByte(iop_base,
8763                                                     (ushort)ASCV_SCSIBUSY_B);
8764                         scsi_busy |= target_id;
8765                         AscWriteLramByte(iop_base,
8766                                          (ushort)ASCV_SCSIBUSY_B, scsi_busy);
8767                         asc_dvc->queue_full_or_busy |= target_id;
8768
8769                         if (scsi_status == SAM_STAT_TASK_SET_FULL) {
8770                                 if (cur_dvc_qng > ASC_MIN_TAGGED_CMD) {
8771                                         cur_dvc_qng -= 1;
8772                                         asc_dvc->max_dvc_qng[tid_no] =
8773                                             cur_dvc_qng;
8774
8775                                         AscWriteLramByte(iop_base,
8776                                                          (ushort)((ushort)
8777                                                                   ASCV_MAX_DVC_QNG_BEG
8778                                                                   + (ushort)
8779                                                                   tid_no),
8780                                                          cur_dvc_qng);
8781
8782                                         /*
8783                                          * Set the device queue depth to the number of
8784                                          * active requests when the QUEUE FULL condition
8785                                          * was encountered.
8786                                          */
8787                                         boardp->queue_full |= target_id;
8788                                         boardp->queue_full_cnt[tid_no] =
8789                                             cur_dvc_qng;
8790                                 }
8791                         }
8792                 }
8793                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8794                 return (0);
8795         }
8796 #if CC_VERY_LONG_SG_LIST
8797         else if (int_halt_code == ASC_HALT_HOST_COPY_SG_LIST_TO_RISC) {
8798                 uchar q_no;
8799                 ushort q_addr;
8800                 uchar sg_wk_q_no;
8801                 uchar first_sg_wk_q_no;
8802                 ASC_SCSI_Q *scsiq;      /* Ptr to driver request. */
8803                 ASC_SG_HEAD *sg_head;   /* Ptr to driver SG request. */
8804                 ASC_SG_LIST_Q scsi_sg_q;        /* Structure written to queue. */
8805                 ushort sg_list_dwords;
8806                 ushort sg_entry_cnt;
8807                 uchar next_qp;
8808                 int i;
8809
8810                 q_no = AscReadLramByte(iop_base, (ushort)ASCV_REQ_SG_LIST_QP);
8811                 if (q_no == ASC_QLINK_END) {
8812                         return (0);
8813                 }
8814
8815                 q_addr = ASC_QNO_TO_QADDR(q_no);
8816
8817                 /*
8818                  * Convert the request's SRB pointer to a host ASC_SCSI_REQ
8819                  * structure pointer using a macro provided by the driver.
8820                  * The ASC_SCSI_REQ pointer provides a pointer to the
8821                  * host ASC_SG_HEAD structure.
8822                  */
8823                 /* Read request's SRB pointer. */
8824                 scsiq = (ASC_SCSI_Q *)
8825                     ASC_SRB2SCSIQ(ASC_U32_TO_VADDR(AscReadLramDWord(iop_base,
8826                                                                     (ushort)
8827                                                                     (q_addr +
8828                                                                      ASC_SCSIQ_D_SRBPTR))));
8829
8830                 /*
8831                  * Get request's first and working SG queue.
8832                  */
8833                 sg_wk_q_no = AscReadLramByte(iop_base,
8834                                              (ushort)(q_addr +
8835                                                       ASC_SCSIQ_B_SG_WK_QP));
8836
8837                 first_sg_wk_q_no = AscReadLramByte(iop_base,
8838                                                    (ushort)(q_addr +
8839                                                             ASC_SCSIQ_B_FIRST_SG_WK_QP));
8840
8841                 /*
8842                  * Reset request's working SG queue back to the
8843                  * first SG queue.
8844                  */
8845                 AscWriteLramByte(iop_base,
8846                                  (ushort)(q_addr +
8847                                           (ushort)ASC_SCSIQ_B_SG_WK_QP),
8848                                  first_sg_wk_q_no);
8849
8850                 sg_head = scsiq->sg_head;
8851
8852                 /*
8853                  * Set sg_entry_cnt to the number of SG elements
8854                  * that will be completed on this interrupt.
8855                  *
8856                  * Note: The allocated SG queues contain ASC_MAX_SG_LIST - 1
8857                  * SG elements. The data_cnt and data_addr fields which
8858                  * add 1 to the SG element capacity are not used when
8859                  * restarting SG handling after a halt.
8860                  */
8861                 if (scsiq->remain_sg_entry_cnt > (ASC_MAX_SG_LIST - 1)) {
8862                         sg_entry_cnt = ASC_MAX_SG_LIST - 1;
8863
8864                         /*
8865                          * Keep track of remaining number of SG elements that will
8866                          * need to be handled on the next interrupt.
8867                          */
8868                         scsiq->remain_sg_entry_cnt -= (ASC_MAX_SG_LIST - 1);
8869                 } else {
8870                         sg_entry_cnt = scsiq->remain_sg_entry_cnt;
8871                         scsiq->remain_sg_entry_cnt = 0;
8872                 }
8873
8874                 /*
8875                  * Copy SG elements into the list of allocated SG queues.
8876                  *
8877                  * Last index completed is saved in scsiq->next_sg_index.
8878                  */
8879                 next_qp = first_sg_wk_q_no;
8880                 q_addr = ASC_QNO_TO_QADDR(next_qp);
8881                 scsi_sg_q.sg_head_qp = q_no;
8882                 scsi_sg_q.cntl = QCSG_SG_XFER_LIST;
8883                 for (i = 0; i < sg_head->queue_cnt; i++) {
8884                         scsi_sg_q.seq_no = i + 1;
8885                         if (sg_entry_cnt > ASC_SG_LIST_PER_Q) {
8886                                 sg_list_dwords = (uchar)(ASC_SG_LIST_PER_Q * 2);
8887                                 sg_entry_cnt -= ASC_SG_LIST_PER_Q;
8888                                 /*
8889                                  * After very first SG queue RISC FW uses next
8890                                  * SG queue first element then checks sg_list_cnt
8891                                  * against zero and then decrements, so set
8892                                  * sg_list_cnt 1 less than number of SG elements
8893                                  * in each SG queue.
8894                                  */
8895                                 scsi_sg_q.sg_list_cnt = ASC_SG_LIST_PER_Q - 1;
8896                                 scsi_sg_q.sg_cur_list_cnt =
8897                                     ASC_SG_LIST_PER_Q - 1;
8898                         } else {
8899                                 /*
8900                                  * This is the last SG queue in the list of
8901                                  * allocated SG queues. If there are more
8902                                  * SG elements than will fit in the allocated
8903                                  * queues, then set the QCSG_SG_XFER_MORE flag.
8904                                  */
8905                                 if (scsiq->remain_sg_entry_cnt != 0) {
8906                                         scsi_sg_q.cntl |= QCSG_SG_XFER_MORE;
8907                                 } else {
8908                                         scsi_sg_q.cntl |= QCSG_SG_XFER_END;
8909                                 }
8910                                 /* equals sg_entry_cnt * 2 */
8911                                 sg_list_dwords = sg_entry_cnt << 1;
8912                                 scsi_sg_q.sg_list_cnt = sg_entry_cnt - 1;
8913                                 scsi_sg_q.sg_cur_list_cnt = sg_entry_cnt - 1;
8914                                 sg_entry_cnt = 0;
8915                         }
8916
8917                         scsi_sg_q.q_no = next_qp;
8918                         AscMemWordCopyPtrToLram(iop_base,
8919                                                 q_addr + ASC_SCSIQ_SGHD_CPY_BEG,
8920                                                 (uchar *)&scsi_sg_q,
8921                                                 sizeof(ASC_SG_LIST_Q) >> 1);
8922
8923                         AscMemDWordCopyPtrToLram(iop_base,
8924                                                  q_addr + ASC_SGQ_LIST_BEG,
8925                                                  (uchar *)&sg_head->
8926                                                  sg_list[scsiq->next_sg_index],
8927                                                  sg_list_dwords);
8928
8929                         scsiq->next_sg_index += ASC_SG_LIST_PER_Q;
8930
8931                         /*
8932                          * If the just completed SG queue contained the
8933                          * last SG element, then no more SG queues need
8934                          * to be written.
8935                          */
8936                         if (scsi_sg_q.cntl & QCSG_SG_XFER_END) {
8937                                 break;
8938                         }
8939
8940                         next_qp = AscReadLramByte(iop_base,
8941                                                   (ushort)(q_addr +
8942                                                            ASC_SCSIQ_B_FWD));
8943                         q_addr = ASC_QNO_TO_QADDR(next_qp);
8944                 }
8945
8946                 /*
8947                  * Clear the halt condition so the RISC will be restarted
8948                  * after the return.
8949                  */
8950                 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
8951                 return (0);
8952         }
8953 #endif /* CC_VERY_LONG_SG_LIST */
8954         return (0);
8955 }
8956
8957 static uchar
8958 _AscCopyLramScsiDoneQ(PortAddr iop_base,
8959                       ushort q_addr,
8960                       ASC_QDONE_INFO *scsiq, ASC_DCNT max_dma_count)
8961 {
8962         ushort _val;
8963         uchar sg_queue_cnt;
8964
8965         DvcGetQinfo(iop_base,
8966                     q_addr + ASC_SCSIQ_DONE_INFO_BEG,
8967                     (uchar *)scsiq,
8968                     (sizeof(ASC_SCSIQ_2) + sizeof(ASC_SCSIQ_3)) / 2);
8969
8970         _val = AscReadLramWord(iop_base,
8971                                (ushort)(q_addr + (ushort)ASC_SCSIQ_B_STATUS));
8972         scsiq->q_status = (uchar)_val;
8973         scsiq->q_no = (uchar)(_val >> 8);
8974         _val = AscReadLramWord(iop_base,
8975                                (ushort)(q_addr + (ushort)ASC_SCSIQ_B_CNTL));
8976         scsiq->cntl = (uchar)_val;
8977         sg_queue_cnt = (uchar)(_val >> 8);
8978         _val = AscReadLramWord(iop_base,
8979                                (ushort)(q_addr +
8980                                         (ushort)ASC_SCSIQ_B_SENSE_LEN));
8981         scsiq->sense_len = (uchar)_val;
8982         scsiq->extra_bytes = (uchar)(_val >> 8);
8983
8984         /*
8985          * Read high word of remain bytes from alternate location.
8986          */
8987         scsiq->remain_bytes = (((ADV_DCNT)AscReadLramWord(iop_base,
8988                                                           (ushort)(q_addr +
8989                                                                    (ushort)
8990                                                                    ASC_SCSIQ_W_ALT_DC1)))
8991                                << 16);
8992         /*
8993          * Read low word of remain bytes from original location.
8994          */
8995         scsiq->remain_bytes += AscReadLramWord(iop_base,
8996                                                (ushort)(q_addr + (ushort)
8997                                                         ASC_SCSIQ_DW_REMAIN_XFER_CNT));
8998
8999         scsiq->remain_bytes &= max_dma_count;
9000         return (sg_queue_cnt);
9001 }
9002
9003 static int AscIsrQDone(ASC_DVC_VAR *asc_dvc)
9004 {
9005         uchar next_qp;
9006         uchar n_q_used;
9007         uchar sg_list_qp;
9008         uchar sg_queue_cnt;
9009         uchar q_cnt;
9010         uchar done_q_tail;
9011         uchar tid_no;
9012         ASC_SCSI_BIT_ID_TYPE scsi_busy;
9013         ASC_SCSI_BIT_ID_TYPE target_id;
9014         PortAddr iop_base;
9015         ushort q_addr;
9016         ushort sg_q_addr;
9017         uchar cur_target_qng;
9018         ASC_QDONE_INFO scsiq_buf;
9019         ASC_QDONE_INFO *scsiq;
9020         int false_overrun;
9021         ASC_ISR_CALLBACK asc_isr_callback;
9022
9023         iop_base = asc_dvc->iop_base;
9024         asc_isr_callback = asc_dvc->isr_callback;
9025         n_q_used = 1;
9026         scsiq = (ASC_QDONE_INFO *)&scsiq_buf;
9027         done_q_tail = (uchar)AscGetVarDoneQTail(iop_base);
9028         q_addr = ASC_QNO_TO_QADDR(done_q_tail);
9029         next_qp = AscReadLramByte(iop_base,
9030                                   (ushort)(q_addr + (ushort)ASC_SCSIQ_B_FWD));
9031         if (next_qp != ASC_QLINK_END) {
9032                 AscPutVarDoneQTail(iop_base, next_qp);
9033                 q_addr = ASC_QNO_TO_QADDR(next_qp);
9034                 sg_queue_cnt = _AscCopyLramScsiDoneQ(iop_base, q_addr, scsiq,
9035                                                      asc_dvc->max_dma_count);
9036                 AscWriteLramByte(iop_base,
9037                                  (ushort)(q_addr +
9038                                           (ushort)ASC_SCSIQ_B_STATUS),
9039                                  (uchar)(scsiq->
9040                                          q_status & (uchar)~(QS_READY |
9041                                                              QS_ABORTED)));
9042                 tid_no = ASC_TIX_TO_TID(scsiq->d2.target_ix);
9043                 target_id = ASC_TIX_TO_TARGET_ID(scsiq->d2.target_ix);
9044                 if ((scsiq->cntl & QC_SG_HEAD) != 0) {
9045                         sg_q_addr = q_addr;
9046                         sg_list_qp = next_qp;
9047                         for (q_cnt = 0; q_cnt < sg_queue_cnt; q_cnt++) {
9048                                 sg_list_qp = AscReadLramByte(iop_base,
9049                                                              (ushort)(sg_q_addr
9050                                                                       + (ushort)
9051                                                                       ASC_SCSIQ_B_FWD));
9052                                 sg_q_addr = ASC_QNO_TO_QADDR(sg_list_qp);
9053                                 if (sg_list_qp == ASC_QLINK_END) {
9054                                         AscSetLibErrorCode(asc_dvc,
9055                                                            ASCQ_ERR_SG_Q_LINKS);
9056                                         scsiq->d3.done_stat = QD_WITH_ERROR;
9057                                         scsiq->d3.host_stat =
9058                                             QHSTA_D_QDONE_SG_LIST_CORRUPTED;
9059                                         goto FATAL_ERR_QDONE;
9060                                 }
9061                                 AscWriteLramByte(iop_base,
9062                                                  (ushort)(sg_q_addr + (ushort)
9063                                                           ASC_SCSIQ_B_STATUS),
9064                                                  QS_FREE);
9065                         }
9066                         n_q_used = sg_queue_cnt + 1;
9067                         AscPutVarDoneQTail(iop_base, sg_list_qp);
9068                 }
9069                 if (asc_dvc->queue_full_or_busy & target_id) {
9070                         cur_target_qng = AscReadLramByte(iop_base,
9071                                                          (ushort)((ushort)
9072                                                                   ASC_QADR_BEG
9073                                                                   + (ushort)
9074                                                                   scsiq->d2.
9075                                                                   target_ix));
9076                         if (cur_target_qng < asc_dvc->max_dvc_qng[tid_no]) {
9077                                 scsi_busy = AscReadLramByte(iop_base, (ushort)
9078                                                             ASCV_SCSIBUSY_B);
9079                                 scsi_busy &= ~target_id;
9080                                 AscWriteLramByte(iop_base,
9081                                                  (ushort)ASCV_SCSIBUSY_B,
9082                                                  scsi_busy);
9083                                 asc_dvc->queue_full_or_busy &= ~target_id;
9084                         }
9085                 }
9086                 if (asc_dvc->cur_total_qng >= n_q_used) {
9087                         asc_dvc->cur_total_qng -= n_q_used;
9088                         if (asc_dvc->cur_dvc_qng[tid_no] != 0) {
9089                                 asc_dvc->cur_dvc_qng[tid_no]--;
9090                         }
9091                 } else {
9092                         AscSetLibErrorCode(asc_dvc, ASCQ_ERR_CUR_QNG);
9093                         scsiq->d3.done_stat = QD_WITH_ERROR;
9094                         goto FATAL_ERR_QDONE;
9095                 }
9096                 if ((scsiq->d2.srb_ptr == 0UL) ||
9097                     ((scsiq->q_status & QS_ABORTED) != 0)) {
9098                         return (0x11);
9099                 } else if (scsiq->q_status == QS_DONE) {
9100                         false_overrun = FALSE;
9101                         if (scsiq->extra_bytes != 0) {
9102                                 scsiq->remain_bytes +=
9103                                     (ADV_DCNT)scsiq->extra_bytes;
9104                         }
9105                         if (scsiq->d3.done_stat == QD_WITH_ERROR) {
9106                                 if (scsiq->d3.host_stat ==
9107                                     QHSTA_M_DATA_OVER_RUN) {
9108                                         if ((scsiq->
9109                                              cntl & (QC_DATA_IN | QC_DATA_OUT))
9110                                             == 0) {
9111                                                 scsiq->d3.done_stat =
9112                                                     QD_NO_ERROR;
9113                                                 scsiq->d3.host_stat =
9114                                                     QHSTA_NO_ERROR;
9115                                         } else if (false_overrun) {
9116                                                 scsiq->d3.done_stat =
9117                                                     QD_NO_ERROR;
9118                                                 scsiq->d3.host_stat =
9119                                                     QHSTA_NO_ERROR;
9120                                         }
9121                                 } else if (scsiq->d3.host_stat ==
9122                                            QHSTA_M_HUNG_REQ_SCSI_BUS_RESET) {
9123                                         AscStopChip(iop_base);
9124                                         AscSetChipControl(iop_base,
9125                                                           (uchar)(CC_SCSI_RESET
9126                                                                   | CC_HALT));
9127                                         DvcDelayNanoSecond(asc_dvc, 60000);
9128                                         AscSetChipControl(iop_base, CC_HALT);
9129                                         AscSetChipStatus(iop_base,
9130                                                          CIW_CLR_SCSI_RESET_INT);
9131                                         AscSetChipStatus(iop_base, 0);
9132                                         AscSetChipControl(iop_base, 0);
9133                                 }
9134                         }
9135                         if ((scsiq->cntl & QC_NO_CALLBACK) == 0) {
9136                                 (*asc_isr_callback) (asc_dvc, scsiq);
9137                         } else {
9138                                 if ((AscReadLramByte(iop_base,
9139                                                      (ushort)(q_addr + (ushort)
9140                                                               ASC_SCSIQ_CDB_BEG))
9141                                      == START_STOP)) {
9142                                         asc_dvc->unit_not_ready &= ~target_id;
9143                                         if (scsiq->d3.done_stat != QD_NO_ERROR) {
9144                                                 asc_dvc->start_motor &=
9145                                                     ~target_id;
9146                                         }
9147                                 }
9148                         }
9149                         return (1);
9150                 } else {
9151                         AscSetLibErrorCode(asc_dvc, ASCQ_ERR_Q_STATUS);
9152  FATAL_ERR_QDONE:
9153                         if ((scsiq->cntl & QC_NO_CALLBACK) == 0) {
9154                                 (*asc_isr_callback) (asc_dvc, scsiq);
9155                         }
9156                         return (0x80);
9157                 }
9158         }
9159         return (0);
9160 }
9161
9162 static int AscISR(ASC_DVC_VAR *asc_dvc)
9163 {
9164         ASC_CS_TYPE chipstat;
9165         PortAddr iop_base;
9166         ushort saved_ram_addr;
9167         uchar ctrl_reg;
9168         uchar saved_ctrl_reg;
9169         int int_pending;
9170         int status;
9171         uchar host_flag;
9172
9173         iop_base = asc_dvc->iop_base;
9174         int_pending = FALSE;
9175
9176         if (AscIsIntPending(iop_base) == 0) {
9177                 return int_pending;
9178         }
9179
9180         if (((asc_dvc->init_state & ASC_INIT_STATE_END_LOAD_MC) == 0)
9181             || (asc_dvc->isr_callback == 0)
9182             ) {
9183                 return (ERR);
9184         }
9185         if (asc_dvc->in_critical_cnt != 0) {
9186                 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_ISR_ON_CRITICAL);
9187                 return (ERR);
9188         }
9189         if (asc_dvc->is_in_int) {
9190                 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_ISR_RE_ENTRY);
9191                 return (ERR);
9192         }
9193         asc_dvc->is_in_int = TRUE;
9194         ctrl_reg = AscGetChipControl(iop_base);
9195         saved_ctrl_reg = ctrl_reg & (~(CC_SCSI_RESET | CC_CHIP_RESET |
9196                                        CC_SINGLE_STEP | CC_DIAG | CC_TEST));
9197         chipstat = AscGetChipStatus(iop_base);
9198         if (chipstat & CSW_SCSI_RESET_LATCH) {
9199                 if (!(asc_dvc->bus_type & (ASC_IS_VL | ASC_IS_EISA))) {
9200                         int i = 10;
9201                         int_pending = TRUE;
9202                         asc_dvc->sdtr_done = 0;
9203                         saved_ctrl_reg &= (uchar)(~CC_HALT);
9204                         while ((AscGetChipStatus(iop_base) &
9205                                 CSW_SCSI_RESET_ACTIVE) && (i-- > 0)) {
9206                                 DvcSleepMilliSecond(100);
9207                         }
9208                         AscSetChipControl(iop_base, (CC_CHIP_RESET | CC_HALT));
9209                         AscSetChipControl(iop_base, CC_HALT);
9210                         AscSetChipStatus(iop_base, CIW_CLR_SCSI_RESET_INT);
9211                         AscSetChipStatus(iop_base, 0);
9212                         chipstat = AscGetChipStatus(iop_base);
9213                 }
9214         }
9215         saved_ram_addr = AscGetChipLramAddr(iop_base);
9216         host_flag = AscReadLramByte(iop_base,
9217                                     ASCV_HOST_FLAG_B) &
9218             (uchar)(~ASC_HOST_FLAG_IN_ISR);
9219         AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B,
9220                          (uchar)(host_flag | (uchar)ASC_HOST_FLAG_IN_ISR));
9221         if ((chipstat & CSW_INT_PENDING)
9222             || (int_pending)
9223             ) {
9224                 AscAckInterrupt(iop_base);
9225                 int_pending = TRUE;
9226                 if ((chipstat & CSW_HALTED) && (ctrl_reg & CC_SINGLE_STEP)) {
9227                         if (AscIsrChipHalted(asc_dvc) == ERR) {
9228                                 goto ISR_REPORT_QDONE_FATAL_ERROR;
9229                         } else {
9230                                 saved_ctrl_reg &= (uchar)(~CC_HALT);
9231                         }
9232                 } else {
9233  ISR_REPORT_QDONE_FATAL_ERROR:
9234                         if ((asc_dvc->dvc_cntl & ASC_CNTL_INT_MULTI_Q) != 0) {
9235                                 while (((status =
9236                                          AscIsrQDone(asc_dvc)) & 0x01) != 0) {
9237                                 }
9238                         } else {
9239                                 do {
9240                                         if ((status =
9241                                              AscIsrQDone(asc_dvc)) == 1) {
9242                                                 break;
9243                                         }
9244                                 } while (status == 0x11);
9245                         }
9246                         if ((status & 0x80) != 0)
9247                                 int_pending = ERR;
9248                 }
9249         }
9250         AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B, host_flag);
9251         AscSetChipLramAddr(iop_base, saved_ram_addr);
9252         AscSetChipControl(iop_base, saved_ctrl_reg);
9253         asc_dvc->is_in_int = FALSE;
9254         return (int_pending);
9255 }
9256
9257 /* Microcode buffer is kept after initialization for error recovery. */
9258 static uchar _asc_mcode_buf[] = {
9259         0x01, 0x03, 0x01, 0x19, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
9260         0x00, 0x00, 0x00, 0x00,
9261         0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x00, 0x00, 0x00, 0x00,
9262         0x00, 0x00, 0x00, 0x00,
9263         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
9264         0x00, 0x00, 0x00, 0x00,
9265         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
9266         0x00, 0x00, 0x00, 0x00,
9267         0x00, 0x00, 0x00, 0x00, 0xC3, 0x12, 0x0D, 0x05, 0x01, 0x00, 0x00, 0x00,
9268         0x00, 0xFF, 0x00, 0x00,
9269         0x00, 0x00, 0x00, 0x00, 0xFF, 0x80, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00,
9270         0x00, 0x00, 0x00, 0x00,
9271         0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0xFF,
9272         0x00, 0x00, 0x00, 0x00,
9273         0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE4, 0x88,
9274         0x00, 0x00, 0x00, 0x00,
9275         0x80, 0x73, 0x48, 0x04, 0x36, 0x00, 0x00, 0xA2, 0xC2, 0x00, 0x80, 0x73,
9276         0x03, 0x23, 0x36, 0x40,
9277         0xB6, 0x00, 0x36, 0x00, 0x05, 0xD6, 0x0C, 0xD2, 0x12, 0xDA, 0x00, 0xA2,
9278         0xC2, 0x00, 0x92, 0x80,
9279         0x1E, 0x98, 0x50, 0x00, 0xF5, 0x00, 0x48, 0x98, 0xDF, 0x23, 0x36, 0x60,
9280         0xB6, 0x00, 0x92, 0x80,
9281         0x4F, 0x00, 0xF5, 0x00, 0x48, 0x98, 0xEF, 0x23, 0x36, 0x60, 0xB6, 0x00,
9282         0x92, 0x80, 0x80, 0x62,
9283         0x92, 0x80, 0x00, 0x46, 0x15, 0xEE, 0x13, 0xEA, 0x02, 0x01, 0x09, 0xD8,
9284         0xCD, 0x04, 0x4D, 0x00,
9285         0x00, 0xA3, 0xD6, 0x00, 0xA6, 0x97, 0x7F, 0x23, 0x04, 0x61, 0x84, 0x01,
9286         0xE6, 0x84, 0xD2, 0xC1,
9287         0x80, 0x73, 0xCD, 0x04, 0x4D, 0x00, 0x00, 0xA3, 0xDA, 0x01, 0xA6, 0x97,
9288         0xC6, 0x81, 0xC2, 0x88,
9289         0x80, 0x73, 0x80, 0x77, 0x00, 0x01, 0x01, 0xA1, 0xFE, 0x00, 0x4F, 0x00,
9290         0x84, 0x97, 0x07, 0xA6,
9291         0x08, 0x01, 0x00, 0x33, 0x03, 0x00, 0xC2, 0x88, 0x03, 0x03, 0x01, 0xDE,
9292         0xC2, 0x88, 0xCE, 0x00,
9293         0x69, 0x60, 0xCE, 0x00, 0x02, 0x03, 0x4A, 0x60, 0x00, 0xA2, 0x78, 0x01,
9294         0x80, 0x63, 0x07, 0xA6,
9295         0x24, 0x01, 0x78, 0x81, 0x03, 0x03, 0x80, 0x63, 0xE2, 0x00, 0x07, 0xA6,
9296         0x34, 0x01, 0x00, 0x33,
9297         0x04, 0x00, 0xC2, 0x88, 0x03, 0x07, 0x02, 0x01, 0x04, 0xCA, 0x0D, 0x23,
9298         0x68, 0x98, 0x4D, 0x04,
9299         0x04, 0x85, 0x05, 0xD8, 0x0D, 0x23, 0x68, 0x98, 0xCD, 0x04, 0x15, 0x23,
9300         0xF8, 0x88, 0xFB, 0x23,
9301         0x02, 0x61, 0x82, 0x01, 0x80, 0x63, 0x02, 0x03, 0x06, 0xA3, 0x62, 0x01,
9302         0x00, 0x33, 0x0A, 0x00,
9303         0xC2, 0x88, 0x4E, 0x00, 0x07, 0xA3, 0x6E, 0x01, 0x00, 0x33, 0x0B, 0x00,
9304         0xC2, 0x88, 0xCD, 0x04,
9305         0x36, 0x2D, 0x00, 0x33, 0x1A, 0x00, 0xC2, 0x88, 0x50, 0x04, 0x88, 0x81,
9306         0x06, 0xAB, 0x82, 0x01,
9307         0x88, 0x81, 0x4E, 0x00, 0x07, 0xA3, 0x92, 0x01, 0x50, 0x00, 0x00, 0xA3,
9308         0x3C, 0x01, 0x00, 0x05,
9309         0x7C, 0x81, 0x46, 0x97, 0x02, 0x01, 0x05, 0xC6, 0x04, 0x23, 0xA0, 0x01,
9310         0x15, 0x23, 0xA1, 0x01,
9311         0xBE, 0x81, 0xFD, 0x23, 0x02, 0x61, 0x82, 0x01, 0x0A, 0xDA, 0x4A, 0x00,
9312         0x06, 0x61, 0x00, 0xA0,
9313         0xB4, 0x01, 0x80, 0x63, 0xCD, 0x04, 0x36, 0x2D, 0x00, 0x33, 0x1B, 0x00,
9314         0xC2, 0x88, 0x06, 0x23,
9315         0x68, 0x98, 0xCD, 0x04, 0xE6, 0x84, 0x06, 0x01, 0x00, 0xA2, 0xD4, 0x01,
9316         0x57, 0x60, 0x00, 0xA0,
9317         0xDA, 0x01, 0xE6, 0x84, 0x80, 0x23, 0xA0, 0x01, 0xE6, 0x84, 0x80, 0x73,
9318         0x4B, 0x00, 0x06, 0x61,
9319         0x00, 0xA2, 0x00, 0x02, 0x04, 0x01, 0x0C, 0xDE, 0x02, 0x01, 0x03, 0xCC,
9320         0x4F, 0x00, 0x84, 0x97,
9321         0xFC, 0x81, 0x08, 0x23, 0x02, 0x41, 0x82, 0x01, 0x4F, 0x00, 0x62, 0x97,
9322         0x48, 0x04, 0x84, 0x80,
9323         0xF0, 0x97, 0x00, 0x46, 0x56, 0x00, 0x03, 0xC0, 0x01, 0x23, 0xE8, 0x00,
9324         0x81, 0x73, 0x06, 0x29,
9325         0x03, 0x42, 0x06, 0xE2, 0x03, 0xEE, 0x6B, 0xEB, 0x11, 0x23, 0xF8, 0x88,
9326         0x04, 0x98, 0xF0, 0x80,
9327         0x80, 0x73, 0x80, 0x77, 0x07, 0xA4, 0x2A, 0x02, 0x7C, 0x95, 0x06, 0xA6,
9328         0x34, 0x02, 0x03, 0xA6,
9329         0x4C, 0x04, 0x46, 0x82, 0x04, 0x01, 0x03, 0xD8, 0xB4, 0x98, 0x6A, 0x96,
9330         0x46, 0x82, 0xFE, 0x95,
9331         0x80, 0x67, 0x83, 0x03, 0x80, 0x63, 0xB6, 0x2D, 0x02, 0xA6, 0x6C, 0x02,
9332         0x07, 0xA6, 0x5A, 0x02,
9333         0x06, 0xA6, 0x5E, 0x02, 0x03, 0xA6, 0x62, 0x02, 0xC2, 0x88, 0x7C, 0x95,
9334         0x48, 0x82, 0x60, 0x96,
9335         0x48, 0x82, 0x04, 0x23, 0xA0, 0x01, 0x14, 0x23, 0xA1, 0x01, 0x3C, 0x84,
9336         0x04, 0x01, 0x0C, 0xDC,
9337         0xE0, 0x23, 0x25, 0x61, 0xEF, 0x00, 0x14, 0x01, 0x4F, 0x04, 0xA8, 0x01,
9338         0x6F, 0x00, 0xA5, 0x01,
9339         0x03, 0x23, 0xA4, 0x01, 0x06, 0x23, 0x9C, 0x01, 0x24, 0x2B, 0x1C, 0x01,
9340         0x02, 0xA6, 0xAA, 0x02,
9341         0x07, 0xA6, 0x5A, 0x02, 0x06, 0xA6, 0x5E, 0x02, 0x03, 0xA6, 0x20, 0x04,
9342         0x01, 0xA6, 0xB4, 0x02,
9343         0x00, 0xA6, 0xB4, 0x02, 0x00, 0x33, 0x12, 0x00, 0xC2, 0x88, 0x00, 0x0E,
9344         0x80, 0x63, 0x00, 0x43,
9345         0x00, 0xA0, 0x8C, 0x02, 0x4D, 0x04, 0x04, 0x01, 0x0B, 0xDC, 0xE7, 0x23,
9346         0x04, 0x61, 0x84, 0x01,
9347         0x10, 0x31, 0x12, 0x35, 0x14, 0x01, 0xEC, 0x00, 0x6C, 0x38, 0x00, 0x3F,
9348         0x00, 0x00, 0xEA, 0x82,
9349         0x18, 0x23, 0x04, 0x61, 0x18, 0xA0, 0xE2, 0x02, 0x04, 0x01, 0xA2, 0xC8,
9350         0x00, 0x33, 0x1F, 0x00,
9351         0xC2, 0x88, 0x08, 0x31, 0x0A, 0x35, 0x0C, 0x39, 0x0E, 0x3D, 0x7E, 0x98,
9352         0xB6, 0x2D, 0x01, 0xA6,
9353         0x14, 0x03, 0x00, 0xA6, 0x14, 0x03, 0x07, 0xA6, 0x0C, 0x03, 0x06, 0xA6,
9354         0x10, 0x03, 0x03, 0xA6,
9355         0x20, 0x04, 0x02, 0xA6, 0x6C, 0x02, 0x00, 0x33, 0x33, 0x00, 0xC2, 0x88,
9356         0x7C, 0x95, 0xEE, 0x82,
9357         0x60, 0x96, 0xEE, 0x82, 0x82, 0x98, 0x80, 0x42, 0x7E, 0x98, 0x64, 0xE4,
9358         0x04, 0x01, 0x2D, 0xC8,
9359         0x31, 0x05, 0x07, 0x01, 0x00, 0xA2, 0x54, 0x03, 0x00, 0x43, 0x87, 0x01,
9360         0x05, 0x05, 0x86, 0x98,
9361         0x7E, 0x98, 0x00, 0xA6, 0x16, 0x03, 0x07, 0xA6, 0x4C, 0x03, 0x03, 0xA6,
9362         0x3C, 0x04, 0x06, 0xA6,
9363         0x50, 0x03, 0x01, 0xA6, 0x16, 0x03, 0x00, 0x33, 0x25, 0x00, 0xC2, 0x88,
9364         0x7C, 0x95, 0x32, 0x83,
9365         0x60, 0x96, 0x32, 0x83, 0x04, 0x01, 0x10, 0xCE, 0x07, 0xC8, 0x05, 0x05,
9366         0xEB, 0x04, 0x00, 0x33,
9367         0x00, 0x20, 0xC0, 0x20, 0x81, 0x62, 0x72, 0x83, 0x00, 0x01, 0x05, 0x05,
9368         0xFF, 0xA2, 0x7A, 0x03,
9369         0xB1, 0x01, 0x08, 0x23, 0xB2, 0x01, 0x2E, 0x83, 0x05, 0x05, 0x15, 0x01,
9370         0x00, 0xA2, 0x9A, 0x03,
9371         0xEC, 0x00, 0x6E, 0x00, 0x95, 0x01, 0x6C, 0x38, 0x00, 0x3F, 0x00, 0x00,
9372         0x01, 0xA6, 0x96, 0x03,
9373         0x00, 0xA6, 0x96, 0x03, 0x10, 0x84, 0x80, 0x42, 0x7E, 0x98, 0x01, 0xA6,
9374         0xA4, 0x03, 0x00, 0xA6,
9375         0xBC, 0x03, 0x10, 0x84, 0xA8, 0x98, 0x80, 0x42, 0x01, 0xA6, 0xA4, 0x03,
9376         0x07, 0xA6, 0xB2, 0x03,
9377         0xD4, 0x83, 0x7C, 0x95, 0xA8, 0x83, 0x00, 0x33, 0x2F, 0x00, 0xC2, 0x88,
9378         0xA8, 0x98, 0x80, 0x42,
9379         0x00, 0xA6, 0xBC, 0x03, 0x07, 0xA6, 0xCA, 0x03, 0xD4, 0x83, 0x7C, 0x95,
9380         0xC0, 0x83, 0x00, 0x33,
9381         0x26, 0x00, 0xC2, 0x88, 0x38, 0x2B, 0x80, 0x32, 0x80, 0x36, 0x04, 0x23,
9382         0xA0, 0x01, 0x12, 0x23,
9383         0xA1, 0x01, 0x10, 0x84, 0x07, 0xF0, 0x06, 0xA4, 0xF4, 0x03, 0x80, 0x6B,
9384         0x80, 0x67, 0x05, 0x23,
9385         0x83, 0x03, 0x80, 0x63, 0x03, 0xA6, 0x0E, 0x04, 0x07, 0xA6, 0x06, 0x04,
9386         0x06, 0xA6, 0x0A, 0x04,
9387         0x00, 0x33, 0x17, 0x00, 0xC2, 0x88, 0x7C, 0x95, 0xF4, 0x83, 0x60, 0x96,
9388         0xF4, 0x83, 0x20, 0x84,
9389         0x07, 0xF0, 0x06, 0xA4, 0x20, 0x04, 0x80, 0x6B, 0x80, 0x67, 0x05, 0x23,
9390         0x83, 0x03, 0x80, 0x63,
9391         0xB6, 0x2D, 0x03, 0xA6, 0x3C, 0x04, 0x07, 0xA6, 0x34, 0x04, 0x06, 0xA6,
9392         0x38, 0x04, 0x00, 0x33,
9393         0x30, 0x00, 0xC2, 0x88, 0x7C, 0x95, 0x20, 0x84, 0x60, 0x96, 0x20, 0x84,
9394         0x1D, 0x01, 0x06, 0xCC,
9395         0x00, 0x33, 0x00, 0x84, 0xC0, 0x20, 0x00, 0x23, 0xEA, 0x00, 0x81, 0x62,
9396         0xA2, 0x0D, 0x80, 0x63,
9397         0x07, 0xA6, 0x5A, 0x04, 0x00, 0x33, 0x18, 0x00, 0xC2, 0x88, 0x03, 0x03,
9398         0x80, 0x63, 0xA3, 0x01,
9399         0x07, 0xA4, 0x64, 0x04, 0x23, 0x01, 0x00, 0xA2, 0x86, 0x04, 0x0A, 0xA0,
9400         0x76, 0x04, 0xE0, 0x00,
9401         0x00, 0x33, 0x1D, 0x00, 0xC2, 0x88, 0x0B, 0xA0, 0x82, 0x04, 0xE0, 0x00,
9402         0x00, 0x33, 0x1E, 0x00,
9403         0xC2, 0x88, 0x42, 0x23, 0xF8, 0x88, 0x00, 0x23, 0x22, 0xA3, 0xE6, 0x04,
9404         0x08, 0x23, 0x22, 0xA3,
9405         0xA2, 0x04, 0x28, 0x23, 0x22, 0xA3, 0xAE, 0x04, 0x02, 0x23, 0x22, 0xA3,
9406         0xC4, 0x04, 0x42, 0x23,
9407         0xF8, 0x88, 0x4A, 0x00, 0x06, 0x61, 0x00, 0xA0, 0xAE, 0x04, 0x45, 0x23,
9408         0xF8, 0x88, 0x04, 0x98,
9409         0x00, 0xA2, 0xC0, 0x04, 0xB4, 0x98, 0x00, 0x33, 0x00, 0x82, 0xC0, 0x20,
9410         0x81, 0x62, 0xE8, 0x81,
9411         0x47, 0x23, 0xF8, 0x88, 0x04, 0x01, 0x0B, 0xDE, 0x04, 0x98, 0xB4, 0x98,
9412         0x00, 0x33, 0x00, 0x81,
9413         0xC0, 0x20, 0x81, 0x62, 0x14, 0x01, 0x00, 0xA0, 0x00, 0x02, 0x43, 0x23,
9414         0xF8, 0x88, 0x04, 0x23,
9415         0xA0, 0x01, 0x44, 0x23, 0xA1, 0x01, 0x80, 0x73, 0x4D, 0x00, 0x03, 0xA3,
9416         0xF4, 0x04, 0x00, 0x33,
9417         0x27, 0x00, 0xC2, 0x88, 0x04, 0x01, 0x04, 0xDC, 0x02, 0x23, 0xA2, 0x01,
9418         0x04, 0x23, 0xA0, 0x01,
9419         0x04, 0x98, 0x26, 0x95, 0x4B, 0x00, 0xF6, 0x00, 0x4F, 0x04, 0x4F, 0x00,
9420         0x00, 0xA3, 0x22, 0x05,
9421         0x00, 0x05, 0x76, 0x00, 0x06, 0x61, 0x00, 0xA2, 0x1C, 0x05, 0x0A, 0x85,
9422         0x46, 0x97, 0xCD, 0x04,
9423         0x24, 0x85, 0x48, 0x04, 0x84, 0x80, 0x02, 0x01, 0x03, 0xDA, 0x80, 0x23,
9424         0x82, 0x01, 0x34, 0x85,
9425         0x02, 0x23, 0xA0, 0x01, 0x4A, 0x00, 0x06, 0x61, 0x00, 0xA2, 0x40, 0x05,
9426         0x1D, 0x01, 0x04, 0xD6,
9427         0xFF, 0x23, 0x86, 0x41, 0x4B, 0x60, 0xCB, 0x00, 0xFF, 0x23, 0x80, 0x01,
9428         0x49, 0x00, 0x81, 0x01,
9429         0x04, 0x01, 0x02, 0xC8, 0x30, 0x01, 0x80, 0x01, 0xF7, 0x04, 0x03, 0x01,
9430         0x49, 0x04, 0x80, 0x01,
9431         0xC9, 0x00, 0x00, 0x05, 0x00, 0x01, 0xFF, 0xA0, 0x60, 0x05, 0x77, 0x04,
9432         0x01, 0x23, 0xEA, 0x00,
9433         0x5D, 0x00, 0xFE, 0xC7, 0x00, 0x62, 0x00, 0x23, 0xEA, 0x00, 0x00, 0x63,
9434         0x07, 0xA4, 0xF8, 0x05,
9435         0x03, 0x03, 0x02, 0xA0, 0x8E, 0x05, 0xF4, 0x85, 0x00, 0x33, 0x2D, 0x00,
9436         0xC2, 0x88, 0x04, 0xA0,
9437         0xB8, 0x05, 0x80, 0x63, 0x00, 0x23, 0xDF, 0x00, 0x4A, 0x00, 0x06, 0x61,
9438         0x00, 0xA2, 0xA4, 0x05,
9439         0x1D, 0x01, 0x06, 0xD6, 0x02, 0x23, 0x02, 0x41, 0x82, 0x01, 0x50, 0x00,
9440         0x62, 0x97, 0x04, 0x85,
9441         0x04, 0x23, 0x02, 0x41, 0x82, 0x01, 0x04, 0x85, 0x08, 0xA0, 0xBE, 0x05,
9442         0xF4, 0x85, 0x03, 0xA0,
9443         0xC4, 0x05, 0xF4, 0x85, 0x01, 0xA0, 0xCE, 0x05, 0x88, 0x00, 0x80, 0x63,
9444         0xCC, 0x86, 0x07, 0xA0,
9445         0xEE, 0x05, 0x5F, 0x00, 0x00, 0x2B, 0xDF, 0x08, 0x00, 0xA2, 0xE6, 0x05,
9446         0x80, 0x67, 0x80, 0x63,
9447         0x01, 0xA2, 0x7A, 0x06, 0x7C, 0x85, 0x06, 0x23, 0x68, 0x98, 0x48, 0x23,
9448         0xF8, 0x88, 0x07, 0x23,
9449         0x80, 0x00, 0x06, 0x87, 0x80, 0x63, 0x7C, 0x85, 0x00, 0x23, 0xDF, 0x00,
9450         0x00, 0x63, 0x4A, 0x00,
9451         0x06, 0x61, 0x00, 0xA2, 0x36, 0x06, 0x1D, 0x01, 0x16, 0xD4, 0xC0, 0x23,
9452         0x07, 0x41, 0x83, 0x03,
9453         0x80, 0x63, 0x06, 0xA6, 0x1C, 0x06, 0x00, 0x33, 0x37, 0x00, 0xC2, 0x88,
9454         0x1D, 0x01, 0x01, 0xD6,
9455         0x20, 0x23, 0x63, 0x60, 0x83, 0x03, 0x80, 0x63, 0x02, 0x23, 0xDF, 0x00,
9456         0x07, 0xA6, 0x7C, 0x05,
9457         0xEF, 0x04, 0x6F, 0x00, 0x00, 0x63, 0x4B, 0x00, 0x06, 0x41, 0xCB, 0x00,
9458         0x52, 0x00, 0x06, 0x61,
9459         0x00, 0xA2, 0x4E, 0x06, 0x1D, 0x01, 0x03, 0xCA, 0xC0, 0x23, 0x07, 0x41,
9460         0x00, 0x63, 0x1D, 0x01,
9461         0x04, 0xCC, 0x00, 0x33, 0x00, 0x83, 0xC0, 0x20, 0x81, 0x62, 0x80, 0x23,
9462         0x07, 0x41, 0x00, 0x63,
9463         0x80, 0x67, 0x08, 0x23, 0x83, 0x03, 0x80, 0x63, 0x00, 0x63, 0x01, 0x23,
9464         0xDF, 0x00, 0x06, 0xA6,
9465         0x84, 0x06, 0x07, 0xA6, 0x7C, 0x05, 0x80, 0x67, 0x80, 0x63, 0x00, 0x33,
9466         0x00, 0x40, 0xC0, 0x20,
9467         0x81, 0x62, 0x00, 0x63, 0x00, 0x00, 0xFE, 0x95, 0x83, 0x03, 0x80, 0x63,
9468         0x06, 0xA6, 0x94, 0x06,
9469         0x07, 0xA6, 0x7C, 0x05, 0x00, 0x00, 0x01, 0xA0, 0x14, 0x07, 0x00, 0x2B,
9470         0x40, 0x0E, 0x80, 0x63,
9471         0x01, 0x00, 0x06, 0xA6, 0xAA, 0x06, 0x07, 0xA6, 0x7C, 0x05, 0x40, 0x0E,
9472         0x80, 0x63, 0x00, 0x43,
9473         0x00, 0xA0, 0xA2, 0x06, 0x06, 0xA6, 0xBC, 0x06, 0x07, 0xA6, 0x7C, 0x05,
9474         0x80, 0x67, 0x40, 0x0E,
9475         0x80, 0x63, 0x07, 0xA6, 0x7C, 0x05, 0x00, 0x23, 0xDF, 0x00, 0x00, 0x63,
9476         0x07, 0xA6, 0xD6, 0x06,
9477         0x00, 0x33, 0x2A, 0x00, 0xC2, 0x88, 0x03, 0x03, 0x80, 0x63, 0x89, 0x00,
9478         0x0A, 0x2B, 0x07, 0xA6,
9479         0xE8, 0x06, 0x00, 0x33, 0x29, 0x00, 0xC2, 0x88, 0x00, 0x43, 0x00, 0xA2,
9480         0xF4, 0x06, 0xC0, 0x0E,
9481         0x80, 0x63, 0xDE, 0x86, 0xC0, 0x0E, 0x00, 0x33, 0x00, 0x80, 0xC0, 0x20,
9482         0x81, 0x62, 0x04, 0x01,
9483         0x02, 0xDA, 0x80, 0x63, 0x7C, 0x85, 0x80, 0x7B, 0x80, 0x63, 0x06, 0xA6,
9484         0x8C, 0x06, 0x00, 0x33,
9485         0x2C, 0x00, 0xC2, 0x88, 0x0C, 0xA2, 0x2E, 0x07, 0xFE, 0x95, 0x83, 0x03,
9486         0x80, 0x63, 0x06, 0xA6,
9487         0x2C, 0x07, 0x07, 0xA6, 0x7C, 0x05, 0x00, 0x33, 0x3D, 0x00, 0xC2, 0x88,
9488         0x00, 0x00, 0x80, 0x67,
9489         0x83, 0x03, 0x80, 0x63, 0x0C, 0xA0, 0x44, 0x07, 0x07, 0xA6, 0x7C, 0x05,
9490         0xBF, 0x23, 0x04, 0x61,
9491         0x84, 0x01, 0xE6, 0x84, 0x00, 0x63, 0xF0, 0x04, 0x01, 0x01, 0xF1, 0x00,
9492         0x00, 0x01, 0xF2, 0x00,
9493         0x01, 0x05, 0x80, 0x01, 0x72, 0x04, 0x71, 0x00, 0x81, 0x01, 0x70, 0x04,
9494         0x80, 0x05, 0x81, 0x05,
9495         0x00, 0x63, 0xF0, 0x04, 0xF2, 0x00, 0x72, 0x04, 0x01, 0x01, 0xF1, 0x00,
9496         0x70, 0x00, 0x81, 0x01,
9497         0x70, 0x04, 0x71, 0x00, 0x81, 0x01, 0x72, 0x00, 0x80, 0x01, 0x71, 0x04,
9498         0x70, 0x00, 0x80, 0x01,
9499         0x70, 0x04, 0x00, 0x63, 0xF0, 0x04, 0xF2, 0x00, 0x72, 0x04, 0x00, 0x01,
9500         0xF1, 0x00, 0x70, 0x00,
9501         0x80, 0x01, 0x70, 0x04, 0x71, 0x00, 0x80, 0x01, 0x72, 0x00, 0x81, 0x01,
9502         0x71, 0x04, 0x70, 0x00,
9503         0x81, 0x01, 0x70, 0x04, 0x00, 0x63, 0x00, 0x23, 0xB3, 0x01, 0x83, 0x05,
9504         0xA3, 0x01, 0xA2, 0x01,
9505         0xA1, 0x01, 0x01, 0x23, 0xA0, 0x01, 0x00, 0x01, 0xC8, 0x00, 0x03, 0xA1,
9506         0xC4, 0x07, 0x00, 0x33,
9507         0x07, 0x00, 0xC2, 0x88, 0x80, 0x05, 0x81, 0x05, 0x04, 0x01, 0x11, 0xC8,
9508         0x48, 0x00, 0xB0, 0x01,
9509         0xB1, 0x01, 0x08, 0x23, 0xB2, 0x01, 0x05, 0x01, 0x48, 0x04, 0x00, 0x43,
9510         0x00, 0xA2, 0xE4, 0x07,
9511         0x00, 0x05, 0xDA, 0x87, 0x00, 0x01, 0xC8, 0x00, 0xFF, 0x23, 0x80, 0x01,
9512         0x05, 0x05, 0x00, 0x63,
9513         0xF7, 0x04, 0x1A, 0x09, 0xF6, 0x08, 0x6E, 0x04, 0x00, 0x02, 0x80, 0x43,
9514         0x76, 0x08, 0x80, 0x02,
9515         0x77, 0x04, 0x00, 0x63, 0xF7, 0x04, 0x1A, 0x09, 0xF6, 0x08, 0x6E, 0x04,
9516         0x00, 0x02, 0x00, 0xA0,
9517         0x14, 0x08, 0x16, 0x88, 0x00, 0x43, 0x76, 0x08, 0x80, 0x02, 0x77, 0x04,
9518         0x00, 0x63, 0xF3, 0x04,
9519         0x00, 0x23, 0xF4, 0x00, 0x74, 0x00, 0x80, 0x43, 0xF4, 0x00, 0xCF, 0x40,
9520         0x00, 0xA2, 0x44, 0x08,
9521         0x74, 0x04, 0x02, 0x01, 0xF7, 0xC9, 0xF6, 0xD9, 0x00, 0x01, 0x01, 0xA1,
9522         0x24, 0x08, 0x04, 0x98,
9523         0x26, 0x95, 0x24, 0x88, 0x73, 0x04, 0x00, 0x63, 0xF3, 0x04, 0x75, 0x04,
9524         0x5A, 0x88, 0x02, 0x01,
9525         0x04, 0xD8, 0x46, 0x97, 0x04, 0x98, 0x26, 0x95, 0x4A, 0x88, 0x75, 0x00,
9526         0x00, 0xA3, 0x64, 0x08,
9527         0x00, 0x05, 0x4E, 0x88, 0x73, 0x04, 0x00, 0x63, 0x80, 0x7B, 0x80, 0x63,
9528         0x06, 0xA6, 0x76, 0x08,
9529         0x00, 0x33, 0x3E, 0x00, 0xC2, 0x88, 0x80, 0x67, 0x83, 0x03, 0x80, 0x63,
9530         0x00, 0x63, 0x38, 0x2B,
9531         0x9C, 0x88, 0x38, 0x2B, 0x92, 0x88, 0x32, 0x09, 0x31, 0x05, 0x92, 0x98,
9532         0x05, 0x05, 0xB2, 0x09,
9533         0x00, 0x63, 0x00, 0x32, 0x00, 0x36, 0x00, 0x3A, 0x00, 0x3E, 0x00, 0x63,
9534         0x80, 0x32, 0x80, 0x36,
9535         0x80, 0x3A, 0x80, 0x3E, 0xB4, 0x3D, 0x00, 0x63, 0x38, 0x2B, 0x40, 0x32,
9536         0x40, 0x36, 0x40, 0x3A,
9537         0x40, 0x3E, 0x00, 0x63, 0x5A, 0x20, 0xC9, 0x40, 0x00, 0xA0, 0xB4, 0x08,
9538         0x5D, 0x00, 0xFE, 0xC3,
9539         0x00, 0x63, 0x80, 0x73, 0xE6, 0x20, 0x02, 0x23, 0xE8, 0x00, 0x82, 0x73,
9540         0xFF, 0xFD, 0x80, 0x73,
9541         0x13, 0x23, 0xF8, 0x88, 0x66, 0x20, 0xC0, 0x20, 0x04, 0x23, 0xA0, 0x01,
9542         0xA1, 0x23, 0xA1, 0x01,
9543         0x81, 0x62, 0xE2, 0x88, 0x80, 0x73, 0x80, 0x77, 0x68, 0x00, 0x00, 0xA2,
9544         0x80, 0x00, 0x03, 0xC2,
9545         0xF1, 0xC7, 0x41, 0x23, 0xF8, 0x88, 0x11, 0x23, 0xA1, 0x01, 0x04, 0x23,
9546         0xA0, 0x01, 0xE6, 0x84,
9547 };
9548
9549 static ushort _asc_mcode_size = sizeof(_asc_mcode_buf);
9550 static ADV_DCNT _asc_mcode_chksum = 0x012C453FUL;
9551
9552 #define ASC_SYN_OFFSET_ONE_DISABLE_LIST  16
9553 static uchar _syn_offset_one_disable_cmd[ASC_SYN_OFFSET_ONE_DISABLE_LIST] = {
9554         INQUIRY,
9555         REQUEST_SENSE,
9556         READ_CAPACITY,
9557         READ_TOC,
9558         MODE_SELECT,
9559         MODE_SENSE,
9560         MODE_SELECT_10,
9561         MODE_SENSE_10,
9562         0xFF,
9563         0xFF,
9564         0xFF,
9565         0xFF,
9566         0xFF,
9567         0xFF,
9568         0xFF,
9569         0xFF
9570 };
9571
9572 static int AscExeScsiQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq)
9573 {
9574         PortAddr iop_base;
9575         ulong last_int_level;
9576         int sta;
9577         int n_q_required;
9578         int disable_syn_offset_one_fix;
9579         int i;
9580         ASC_PADDR addr;
9581         ASC_EXE_CALLBACK asc_exe_callback;
9582         ushort sg_entry_cnt = 0;
9583         ushort sg_entry_cnt_minus_one = 0;
9584         uchar target_ix;
9585         uchar tid_no;
9586         uchar sdtr_data;
9587         uchar extra_bytes;
9588         uchar scsi_cmd;
9589         uchar disable_cmd;
9590         ASC_SG_HEAD *sg_head;
9591         ASC_DCNT data_cnt;
9592
9593         iop_base = asc_dvc->iop_base;
9594         sg_head = scsiq->sg_head;
9595         asc_exe_callback = asc_dvc->exe_callback;
9596         if (asc_dvc->err_code != 0)
9597                 return (ERR);
9598         if (scsiq == (ASC_SCSI_Q *)0L) {
9599                 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_SCSIQ_NULL_PTR);
9600                 return (ERR);
9601         }
9602         scsiq->q1.q_no = 0;
9603         if ((scsiq->q2.tag_code & ASC_TAG_FLAG_EXTRA_BYTES) == 0) {
9604                 scsiq->q1.extra_bytes = 0;
9605         }
9606         sta = 0;
9607         target_ix = scsiq->q2.target_ix;
9608         tid_no = ASC_TIX_TO_TID(target_ix);
9609         n_q_required = 1;
9610         if (scsiq->cdbptr[0] == REQUEST_SENSE) {
9611                 if ((asc_dvc->init_sdtr & scsiq->q1.target_id) != 0) {
9612                         asc_dvc->sdtr_done &= ~scsiq->q1.target_id;
9613                         sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
9614                         AscMsgOutSDTR(asc_dvc,
9615                                       asc_dvc->
9616                                       sdtr_period_tbl[(sdtr_data >> 4) &
9617                                                       (uchar)(asc_dvc->
9618                                                               max_sdtr_index -
9619                                                               1)],
9620                                       (uchar)(sdtr_data & (uchar)
9621                                               ASC_SYN_MAX_OFFSET));
9622                         scsiq->q1.cntl |= (QC_MSG_OUT | QC_URGENT);
9623                 }
9624         }
9625         last_int_level = DvcEnterCritical();
9626         if (asc_dvc->in_critical_cnt != 0) {
9627                 DvcLeaveCritical(last_int_level);
9628                 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_CRITICAL_RE_ENTRY);
9629                 return (ERR);
9630         }
9631         asc_dvc->in_critical_cnt++;
9632         if ((scsiq->q1.cntl & QC_SG_HEAD) != 0) {
9633                 if ((sg_entry_cnt = sg_head->entry_cnt) == 0) {
9634                         asc_dvc->in_critical_cnt--;
9635                         DvcLeaveCritical(last_int_level);
9636                         return (ERR);
9637                 }
9638 #if !CC_VERY_LONG_SG_LIST
9639                 if (sg_entry_cnt > ASC_MAX_SG_LIST) {
9640                         asc_dvc->in_critical_cnt--;
9641                         DvcLeaveCritical(last_int_level);
9642                         return (ERR);
9643                 }
9644 #endif /* !CC_VERY_LONG_SG_LIST */
9645                 if (sg_entry_cnt == 1) {
9646                         scsiq->q1.data_addr =
9647                             (ADV_PADDR)sg_head->sg_list[0].addr;
9648                         scsiq->q1.data_cnt =
9649                             (ADV_DCNT)sg_head->sg_list[0].bytes;
9650                         scsiq->q1.cntl &= ~(QC_SG_HEAD | QC_SG_SWAP_QUEUE);
9651                 }
9652                 sg_entry_cnt_minus_one = sg_entry_cnt - 1;
9653         }
9654         scsi_cmd = scsiq->cdbptr[0];
9655         disable_syn_offset_one_fix = FALSE;
9656         if ((asc_dvc->pci_fix_asyn_xfer & scsiq->q1.target_id) &&
9657             !(asc_dvc->pci_fix_asyn_xfer_always & scsiq->q1.target_id)) {
9658                 if (scsiq->q1.cntl & QC_SG_HEAD) {
9659                         data_cnt = 0;
9660                         for (i = 0; i < sg_entry_cnt; i++) {
9661                                 data_cnt +=
9662                                     (ADV_DCNT)le32_to_cpu(sg_head->sg_list[i].
9663                                                           bytes);
9664                         }
9665                 } else {
9666                         data_cnt = le32_to_cpu(scsiq->q1.data_cnt);
9667                 }
9668                 if (data_cnt != 0UL) {
9669                         if (data_cnt < 512UL) {
9670                                 disable_syn_offset_one_fix = TRUE;
9671                         } else {
9672                                 for (i = 0; i < ASC_SYN_OFFSET_ONE_DISABLE_LIST;
9673                                      i++) {
9674                                         disable_cmd =
9675                                             _syn_offset_one_disable_cmd[i];
9676                                         if (disable_cmd == 0xFF) {
9677                                                 break;
9678                                         }
9679                                         if (scsi_cmd == disable_cmd) {
9680                                                 disable_syn_offset_one_fix =
9681                                                     TRUE;
9682                                                 break;
9683                                         }
9684                                 }
9685                         }
9686                 }
9687         }
9688         if (disable_syn_offset_one_fix) {
9689                 scsiq->q2.tag_code &= ~MSG_SIMPLE_TAG;
9690                 scsiq->q2.tag_code |= (ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX |
9691                                        ASC_TAG_FLAG_DISABLE_DISCONNECT);
9692         } else {
9693                 scsiq->q2.tag_code &= 0x27;
9694         }
9695         if ((scsiq->q1.cntl & QC_SG_HEAD) != 0) {
9696                 if (asc_dvc->bug_fix_cntl) {
9697                         if (asc_dvc->bug_fix_cntl & ASC_BUG_FIX_IF_NOT_DWB) {
9698                                 if ((scsi_cmd == READ_6) ||
9699                                     (scsi_cmd == READ_10)) {
9700                                         addr =
9701                                             (ADV_PADDR)le32_to_cpu(sg_head->
9702                                                                    sg_list
9703                                                                    [sg_entry_cnt_minus_one].
9704                                                                    addr) +
9705                                             (ADV_DCNT)le32_to_cpu(sg_head->
9706                                                                   sg_list
9707                                                                   [sg_entry_cnt_minus_one].
9708                                                                   bytes);
9709                                         extra_bytes =
9710                                             (uchar)((ushort)addr & 0x0003);
9711                                         if ((extra_bytes != 0)
9712                                             &&
9713                                             ((scsiq->q2.
9714                                               tag_code &
9715                                               ASC_TAG_FLAG_EXTRA_BYTES)
9716                                              == 0)) {
9717                                                 scsiq->q2.tag_code |=
9718                                                     ASC_TAG_FLAG_EXTRA_BYTES;
9719                                                 scsiq->q1.extra_bytes =
9720                                                     extra_bytes;
9721                                                 data_cnt =
9722                                                     le32_to_cpu(sg_head->
9723                                                                 sg_list
9724                                                                 [sg_entry_cnt_minus_one].
9725                                                                 bytes);
9726                                                 data_cnt -=
9727                                                     (ASC_DCNT) extra_bytes;
9728                                                 sg_head->
9729                                                     sg_list
9730                                                     [sg_entry_cnt_minus_one].
9731                                                     bytes =
9732                                                     cpu_to_le32(data_cnt);
9733                                         }
9734                                 }
9735                         }
9736                 }
9737                 sg_head->entry_to_copy = sg_head->entry_cnt;
9738 #if CC_VERY_LONG_SG_LIST
9739                 /*
9740                  * Set the sg_entry_cnt to the maximum possible. The rest of
9741                  * the SG elements will be copied when the RISC completes the
9742                  * SG elements that fit and halts.
9743                  */
9744                 if (sg_entry_cnt > ASC_MAX_SG_LIST) {
9745                         sg_entry_cnt = ASC_MAX_SG_LIST;
9746                 }
9747 #endif /* CC_VERY_LONG_SG_LIST */
9748                 n_q_required = AscSgListToQueue(sg_entry_cnt);
9749                 if ((AscGetNumOfFreeQueue(asc_dvc, target_ix, n_q_required) >=
9750                      (uint) n_q_required)
9751                     || ((scsiq->q1.cntl & QC_URGENT) != 0)) {
9752                         if ((sta =
9753                              AscSendScsiQueue(asc_dvc, scsiq,
9754                                               n_q_required)) == 1) {
9755                                 asc_dvc->in_critical_cnt--;
9756                                 if (asc_exe_callback != 0) {
9757                                         (*asc_exe_callback) (asc_dvc, scsiq);
9758                                 }
9759                                 DvcLeaveCritical(last_int_level);
9760                                 return (sta);
9761                         }
9762                 }
9763         } else {
9764                 if (asc_dvc->bug_fix_cntl) {
9765                         if (asc_dvc->bug_fix_cntl & ASC_BUG_FIX_IF_NOT_DWB) {
9766                                 if ((scsi_cmd == READ_6) ||
9767                                     (scsi_cmd == READ_10)) {
9768                                         addr =
9769                                             le32_to_cpu(scsiq->q1.data_addr) +
9770                                             le32_to_cpu(scsiq->q1.data_cnt);
9771                                         extra_bytes =
9772                                             (uchar)((ushort)addr & 0x0003);
9773                                         if ((extra_bytes != 0)
9774                                             &&
9775                                             ((scsiq->q2.
9776                                               tag_code &
9777                                               ASC_TAG_FLAG_EXTRA_BYTES)
9778                                              == 0)) {
9779                                                 data_cnt =
9780                                                     le32_to_cpu(scsiq->q1.
9781                                                                 data_cnt);
9782                                                 if (((ushort)data_cnt & 0x01FF)
9783                                                     == 0) {
9784                                                         scsiq->q2.tag_code |=
9785                                                             ASC_TAG_FLAG_EXTRA_BYTES;
9786                                                         data_cnt -= (ASC_DCNT)
9787                                                             extra_bytes;
9788                                                         scsiq->q1.data_cnt =
9789                                                             cpu_to_le32
9790                                                             (data_cnt);
9791                                                         scsiq->q1.extra_bytes =
9792                                                             extra_bytes;
9793                                                 }
9794                                         }
9795                                 }
9796                         }
9797                 }
9798                 n_q_required = 1;
9799                 if ((AscGetNumOfFreeQueue(asc_dvc, target_ix, 1) >= 1) ||
9800                     ((scsiq->q1.cntl & QC_URGENT) != 0)) {
9801                         if ((sta = AscSendScsiQueue(asc_dvc, scsiq,
9802                                                     n_q_required)) == 1) {
9803                                 asc_dvc->in_critical_cnt--;
9804                                 if (asc_exe_callback != 0) {
9805                                         (*asc_exe_callback) (asc_dvc, scsiq);
9806                                 }
9807                                 DvcLeaveCritical(last_int_level);
9808                                 return (sta);
9809                         }
9810                 }
9811         }
9812         asc_dvc->in_critical_cnt--;
9813         DvcLeaveCritical(last_int_level);
9814         return (sta);
9815 }
9816
9817 static int
9818 AscSendScsiQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar n_q_required)
9819 {
9820         PortAddr iop_base;
9821         uchar free_q_head;
9822         uchar next_qp;
9823         uchar tid_no;
9824         uchar target_ix;
9825         int sta;
9826
9827         iop_base = asc_dvc->iop_base;
9828         target_ix = scsiq->q2.target_ix;
9829         tid_no = ASC_TIX_TO_TID(target_ix);
9830         sta = 0;
9831         free_q_head = (uchar)AscGetVarFreeQHead(iop_base);
9832         if (n_q_required > 1) {
9833                 if ((next_qp = AscAllocMultipleFreeQueue(iop_base,
9834                                                          free_q_head, (uchar)
9835                                                          (n_q_required)))
9836                     != (uchar)ASC_QLINK_END) {
9837                         asc_dvc->last_q_shortage = 0;
9838                         scsiq->sg_head->queue_cnt = n_q_required - 1;
9839                         scsiq->q1.q_no = free_q_head;
9840                         if ((sta = AscPutReadySgListQueue(asc_dvc, scsiq,
9841                                                           free_q_head)) == 1) {
9842                                 AscPutVarFreeQHead(iop_base, next_qp);
9843                                 asc_dvc->cur_total_qng += (uchar)(n_q_required);
9844                                 asc_dvc->cur_dvc_qng[tid_no]++;
9845                         }
9846                         return (sta);
9847                 }
9848         } else if (n_q_required == 1) {
9849                 if ((next_qp = AscAllocFreeQueue(iop_base,
9850                                                  free_q_head)) !=
9851                     ASC_QLINK_END) {
9852                         scsiq->q1.q_no = free_q_head;
9853                         if ((sta = AscPutReadyQueue(asc_dvc, scsiq,
9854                                                     free_q_head)) == 1) {
9855                                 AscPutVarFreeQHead(iop_base, next_qp);
9856                                 asc_dvc->cur_total_qng++;
9857                                 asc_dvc->cur_dvc_qng[tid_no]++;
9858                         }
9859                         return (sta);
9860                 }
9861         }
9862         return (sta);
9863 }
9864
9865 static int AscSgListToQueue(int sg_list)
9866 {
9867         int n_sg_list_qs;
9868
9869         n_sg_list_qs = ((sg_list - 1) / ASC_SG_LIST_PER_Q);
9870         if (((sg_list - 1) % ASC_SG_LIST_PER_Q) != 0)
9871                 n_sg_list_qs++;
9872         return (n_sg_list_qs + 1);
9873 }
9874
9875 static uint
9876 AscGetNumOfFreeQueue(ASC_DVC_VAR *asc_dvc, uchar target_ix, uchar n_qs)
9877 {
9878         uint cur_used_qs;
9879         uint cur_free_qs;
9880         ASC_SCSI_BIT_ID_TYPE target_id;
9881         uchar tid_no;
9882
9883         target_id = ASC_TIX_TO_TARGET_ID(target_ix);
9884         tid_no = ASC_TIX_TO_TID(target_ix);
9885         if ((asc_dvc->unit_not_ready & target_id) ||
9886             (asc_dvc->queue_full_or_busy & target_id)) {
9887                 return (0);
9888         }
9889         if (n_qs == 1) {
9890                 cur_used_qs = (uint) asc_dvc->cur_total_qng +
9891                     (uint) asc_dvc->last_q_shortage + (uint) ASC_MIN_FREE_Q;
9892         } else {
9893                 cur_used_qs = (uint) asc_dvc->cur_total_qng +
9894                     (uint) ASC_MIN_FREE_Q;
9895         }
9896         if ((uint) (cur_used_qs + n_qs) <= (uint) asc_dvc->max_total_qng) {
9897                 cur_free_qs = (uint) asc_dvc->max_total_qng - cur_used_qs;
9898                 if (asc_dvc->cur_dvc_qng[tid_no] >=
9899                     asc_dvc->max_dvc_qng[tid_no]) {
9900                         return (0);
9901                 }
9902                 return (cur_free_qs);
9903         }
9904         if (n_qs > 1) {
9905                 if ((n_qs > asc_dvc->last_q_shortage)
9906                     && (n_qs <= (asc_dvc->max_total_qng - ASC_MIN_FREE_Q))) {
9907                         asc_dvc->last_q_shortage = n_qs;
9908                 }
9909         }
9910         return (0);
9911 }
9912
9913 static int AscPutReadyQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar q_no)
9914 {
9915         ushort q_addr;
9916         uchar tid_no;
9917         uchar sdtr_data;
9918         uchar syn_period_ix;
9919         uchar syn_offset;
9920         PortAddr iop_base;
9921
9922         iop_base = asc_dvc->iop_base;
9923         if (((asc_dvc->init_sdtr & scsiq->q1.target_id) != 0) &&
9924             ((asc_dvc->sdtr_done & scsiq->q1.target_id) == 0)) {
9925                 tid_no = ASC_TIX_TO_TID(scsiq->q2.target_ix);
9926                 sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
9927                 syn_period_ix =
9928                     (sdtr_data >> 4) & (asc_dvc->max_sdtr_index - 1);
9929                 syn_offset = sdtr_data & ASC_SYN_MAX_OFFSET;
9930                 AscMsgOutSDTR(asc_dvc,
9931                               asc_dvc->sdtr_period_tbl[syn_period_ix],
9932                               syn_offset);
9933                 scsiq->q1.cntl |= QC_MSG_OUT;
9934         }
9935         q_addr = ASC_QNO_TO_QADDR(q_no);
9936         if ((scsiq->q1.target_id & asc_dvc->use_tagged_qng) == 0) {
9937                 scsiq->q2.tag_code &= ~MSG_SIMPLE_TAG;
9938         }
9939         scsiq->q1.status = QS_FREE;
9940         AscMemWordCopyPtrToLram(iop_base,
9941                                 q_addr + ASC_SCSIQ_CDB_BEG,
9942                                 (uchar *)scsiq->cdbptr, scsiq->q2.cdb_len >> 1);
9943
9944         DvcPutScsiQ(iop_base,
9945                     q_addr + ASC_SCSIQ_CPY_BEG,
9946                     (uchar *)&scsiq->q1.cntl,
9947                     ((sizeof(ASC_SCSIQ_1) + sizeof(ASC_SCSIQ_2)) / 2) - 1);
9948         AscWriteLramWord(iop_base,
9949                          (ushort)(q_addr + (ushort)ASC_SCSIQ_B_STATUS),
9950                          (ushort)(((ushort)scsiq->q1.
9951                                    q_no << 8) | (ushort)QS_READY));
9952         return (1);
9953 }
9954
9955 static int
9956 AscPutReadySgListQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar q_no)
9957 {
9958         int sta;
9959         int i;
9960         ASC_SG_HEAD *sg_head;
9961         ASC_SG_LIST_Q scsi_sg_q;
9962         ASC_DCNT saved_data_addr;
9963         ASC_DCNT saved_data_cnt;
9964         PortAddr iop_base;
9965         ushort sg_list_dwords;
9966         ushort sg_index;
9967         ushort sg_entry_cnt;
9968         ushort q_addr;
9969         uchar next_qp;
9970
9971         iop_base = asc_dvc->iop_base;
9972         sg_head = scsiq->sg_head;
9973         saved_data_addr = scsiq->q1.data_addr;
9974         saved_data_cnt = scsiq->q1.data_cnt;
9975         scsiq->q1.data_addr = (ASC_PADDR) sg_head->sg_list[0].addr;
9976         scsiq->q1.data_cnt = (ASC_DCNT) sg_head->sg_list[0].bytes;
9977 #if CC_VERY_LONG_SG_LIST
9978         /*
9979          * If sg_head->entry_cnt is greater than ASC_MAX_SG_LIST
9980          * then not all SG elements will fit in the allocated queues.
9981          * The rest of the SG elements will be copied when the RISC
9982          * completes the SG elements that fit and halts.
9983          */
9984         if (sg_head->entry_cnt > ASC_MAX_SG_LIST) {
9985                 /*
9986                  * Set sg_entry_cnt to be the number of SG elements that
9987                  * will fit in the allocated SG queues. It is minus 1, because
9988                  * the first SG element is handled above. ASC_MAX_SG_LIST is
9989                  * already inflated by 1 to account for this. For example it
9990                  * may be 50 which is 1 + 7 queues * 7 SG elements.
9991                  */
9992                 sg_entry_cnt = ASC_MAX_SG_LIST - 1;
9993
9994                 /*
9995                  * Keep track of remaining number of SG elements that will
9996                  * need to be handled from a_isr.c.
9997                  */
9998                 scsiq->remain_sg_entry_cnt =
9999                     sg_head->entry_cnt - ASC_MAX_SG_LIST;
10000         } else {
10001 #endif /* CC_VERY_LONG_SG_LIST */
10002                 /*
10003                  * Set sg_entry_cnt to be the number of SG elements that
10004                  * will fit in the allocated SG queues. It is minus 1, because
10005                  * the first SG element is handled above.
10006                  */
10007                 sg_entry_cnt = sg_head->entry_cnt - 1;
10008 #if CC_VERY_LONG_SG_LIST
10009         }
10010 #endif /* CC_VERY_LONG_SG_LIST */
10011         if (sg_entry_cnt != 0) {
10012                 scsiq->q1.cntl |= QC_SG_HEAD;
10013                 q_addr = ASC_QNO_TO_QADDR(q_no);
10014                 sg_index = 1;
10015                 scsiq->q1.sg_queue_cnt = sg_head->queue_cnt;
10016                 scsi_sg_q.sg_head_qp = q_no;
10017                 scsi_sg_q.cntl = QCSG_SG_XFER_LIST;
10018                 for (i = 0; i < sg_head->queue_cnt; i++) {
10019                         scsi_sg_q.seq_no = i + 1;
10020                         if (sg_entry_cnt > ASC_SG_LIST_PER_Q) {
10021                                 sg_list_dwords = (uchar)(ASC_SG_LIST_PER_Q * 2);
10022                                 sg_entry_cnt -= ASC_SG_LIST_PER_Q;
10023                                 if (i == 0) {
10024                                         scsi_sg_q.sg_list_cnt =
10025                                             ASC_SG_LIST_PER_Q;
10026                                         scsi_sg_q.sg_cur_list_cnt =
10027                                             ASC_SG_LIST_PER_Q;
10028                                 } else {
10029                                         scsi_sg_q.sg_list_cnt =
10030                                             ASC_SG_LIST_PER_Q - 1;
10031                                         scsi_sg_q.sg_cur_list_cnt =
10032                                             ASC_SG_LIST_PER_Q - 1;
10033                                 }
10034                         } else {
10035 #if CC_VERY_LONG_SG_LIST
10036                                 /*
10037                                  * This is the last SG queue in the list of
10038                                  * allocated SG queues. If there are more
10039                                  * SG elements than will fit in the allocated
10040                                  * queues, then set the QCSG_SG_XFER_MORE flag.
10041                                  */
10042                                 if (sg_head->entry_cnt > ASC_MAX_SG_LIST) {
10043                                         scsi_sg_q.cntl |= QCSG_SG_XFER_MORE;
10044                                 } else {
10045 #endif /* CC_VERY_LONG_SG_LIST */
10046                                         scsi_sg_q.cntl |= QCSG_SG_XFER_END;
10047 #if CC_VERY_LONG_SG_LIST
10048                                 }
10049 #endif /* CC_VERY_LONG_SG_LIST */
10050                                 sg_list_dwords = sg_entry_cnt << 1;
10051                                 if (i == 0) {
10052                                         scsi_sg_q.sg_list_cnt = sg_entry_cnt;
10053                                         scsi_sg_q.sg_cur_list_cnt =
10054                                             sg_entry_cnt;
10055                                 } else {
10056                                         scsi_sg_q.sg_list_cnt =
10057                                             sg_entry_cnt - 1;
10058                                         scsi_sg_q.sg_cur_list_cnt =
10059                                             sg_entry_cnt - 1;
10060                                 }
10061                                 sg_entry_cnt = 0;
10062                         }
10063                         next_qp = AscReadLramByte(iop_base,
10064                                                   (ushort)(q_addr +
10065                                                            ASC_SCSIQ_B_FWD));
10066                         scsi_sg_q.q_no = next_qp;
10067                         q_addr = ASC_QNO_TO_QADDR(next_qp);
10068                         AscMemWordCopyPtrToLram(iop_base,
10069                                                 q_addr + ASC_SCSIQ_SGHD_CPY_BEG,
10070                                                 (uchar *)&scsi_sg_q,
10071                                                 sizeof(ASC_SG_LIST_Q) >> 1);
10072                         AscMemDWordCopyPtrToLram(iop_base,
10073                                                  q_addr + ASC_SGQ_LIST_BEG,
10074                                                  (uchar *)&sg_head->
10075                                                  sg_list[sg_index],
10076                                                  sg_list_dwords);
10077                         sg_index += ASC_SG_LIST_PER_Q;
10078                         scsiq->next_sg_index = sg_index;
10079                 }
10080         } else {
10081                 scsiq->q1.cntl &= ~QC_SG_HEAD;
10082         }
10083         sta = AscPutReadyQueue(asc_dvc, scsiq, q_no);
10084         scsiq->q1.data_addr = saved_data_addr;
10085         scsiq->q1.data_cnt = saved_data_cnt;
10086         return (sta);
10087 }
10088
10089 static int
10090 AscSetRunChipSynRegAtID(PortAddr iop_base, uchar tid_no, uchar sdtr_data)
10091 {
10092         int sta = FALSE;
10093
10094         if (AscHostReqRiscHalt(iop_base)) {
10095                 sta = AscSetChipSynRegAtID(iop_base, tid_no, sdtr_data);
10096                 AscStartChip(iop_base);
10097                 return (sta);
10098         }
10099         return (sta);
10100 }
10101
10102 static int AscSetChipSynRegAtID(PortAddr iop_base, uchar id, uchar sdtr_data)
10103 {
10104         ASC_SCSI_BIT_ID_TYPE org_id;
10105         int i;
10106         int sta = TRUE;
10107
10108         AscSetBank(iop_base, 1);
10109         org_id = AscReadChipDvcID(iop_base);
10110         for (i = 0; i <= ASC_MAX_TID; i++) {
10111                 if (org_id == (0x01 << i))
10112                         break;
10113         }
10114         org_id = (ASC_SCSI_BIT_ID_TYPE) i;
10115         AscWriteChipDvcID(iop_base, id);
10116         if (AscReadChipDvcID(iop_base) == (0x01 << id)) {
10117                 AscSetBank(iop_base, 0);
10118                 AscSetChipSyn(iop_base, sdtr_data);
10119                 if (AscGetChipSyn(iop_base) != sdtr_data) {
10120                         sta = FALSE;
10121                 }
10122         } else {
10123                 sta = FALSE;
10124         }
10125         AscSetBank(iop_base, 1);
10126         AscWriteChipDvcID(iop_base, org_id);
10127         AscSetBank(iop_base, 0);
10128         return (sta);
10129 }
10130
10131 static ushort AscInitLram(ASC_DVC_VAR *asc_dvc)
10132 {
10133         uchar i;
10134         ushort s_addr;
10135         PortAddr iop_base;
10136         ushort warn_code;
10137
10138         iop_base = asc_dvc->iop_base;
10139         warn_code = 0;
10140         AscMemWordSetLram(iop_base, ASC_QADR_BEG, 0,
10141                           (ushort)(((int)(asc_dvc->max_total_qng + 2 + 1) *
10142                                     64) >> 1)
10143             );
10144         i = ASC_MIN_ACTIVE_QNO;
10145         s_addr = ASC_QADR_BEG + ASC_QBLK_SIZE;
10146         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
10147                          (uchar)(i + 1));
10148         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
10149                          (uchar)(asc_dvc->max_total_qng));
10150         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
10151                          (uchar)i);
10152         i++;
10153         s_addr += ASC_QBLK_SIZE;
10154         for (; i < asc_dvc->max_total_qng; i++, s_addr += ASC_QBLK_SIZE) {
10155                 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
10156                                  (uchar)(i + 1));
10157                 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
10158                                  (uchar)(i - 1));
10159                 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
10160                                  (uchar)i);
10161         }
10162         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
10163                          (uchar)ASC_QLINK_END);
10164         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
10165                          (uchar)(asc_dvc->max_total_qng - 1));
10166         AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
10167                          (uchar)asc_dvc->max_total_qng);
10168         i++;
10169         s_addr += ASC_QBLK_SIZE;
10170         for (; i <= (uchar)(asc_dvc->max_total_qng + 3);
10171              i++, s_addr += ASC_QBLK_SIZE) {
10172                 AscWriteLramByte(iop_base,
10173                                  (ushort)(s_addr + (ushort)ASC_SCSIQ_B_FWD), i);
10174                 AscWriteLramByte(iop_base,
10175                                  (ushort)(s_addr + (ushort)ASC_SCSIQ_B_BWD), i);
10176                 AscWriteLramByte(iop_base,
10177                                  (ushort)(s_addr + (ushort)ASC_SCSIQ_B_QNO), i);
10178         }
10179         return (warn_code);
10180 }
10181
10182 static ushort AscInitQLinkVar(ASC_DVC_VAR *asc_dvc)
10183 {
10184         PortAddr iop_base;
10185         int i;
10186         ushort lram_addr;
10187
10188         iop_base = asc_dvc->iop_base;
10189         AscPutRiscVarFreeQHead(iop_base, 1);
10190         AscPutRiscVarDoneQTail(iop_base, asc_dvc->max_total_qng);
10191         AscPutVarFreeQHead(iop_base, 1);
10192         AscPutVarDoneQTail(iop_base, asc_dvc->max_total_qng);
10193         AscWriteLramByte(iop_base, ASCV_BUSY_QHEAD_B,
10194                          (uchar)((int)asc_dvc->max_total_qng + 1));
10195         AscWriteLramByte(iop_base, ASCV_DISC1_QHEAD_B,
10196                          (uchar)((int)asc_dvc->max_total_qng + 2));
10197         AscWriteLramByte(iop_base, (ushort)ASCV_TOTAL_READY_Q_B,
10198                          asc_dvc->max_total_qng);
10199         AscWriteLramWord(iop_base, ASCV_ASCDVC_ERR_CODE_W, 0);
10200         AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
10201         AscWriteLramByte(iop_base, ASCV_STOP_CODE_B, 0);
10202         AscWriteLramByte(iop_base, ASCV_SCSIBUSY_B, 0);
10203         AscWriteLramByte(iop_base, ASCV_WTM_FLAG_B, 0);
10204         AscPutQDoneInProgress(iop_base, 0);
10205         lram_addr = ASC_QADR_BEG;
10206         for (i = 0; i < 32; i++, lram_addr += 2) {
10207                 AscWriteLramWord(iop_base, lram_addr, 0);
10208         }
10209         return (0);
10210 }
10211
10212 static int AscSetLibErrorCode(ASC_DVC_VAR *asc_dvc, ushort err_code)
10213 {
10214         if (asc_dvc->err_code == 0) {
10215                 asc_dvc->err_code = err_code;
10216                 AscWriteLramWord(asc_dvc->iop_base, ASCV_ASCDVC_ERR_CODE_W,
10217                                  err_code);
10218         }
10219         return (err_code);
10220 }
10221
10222 static uchar
10223 AscMsgOutSDTR(ASC_DVC_VAR *asc_dvc, uchar sdtr_period, uchar sdtr_offset)
10224 {
10225         EXT_MSG sdtr_buf;
10226         uchar sdtr_period_index;
10227         PortAddr iop_base;
10228
10229         iop_base = asc_dvc->iop_base;
10230         sdtr_buf.msg_type = MS_EXTEND;
10231         sdtr_buf.msg_len = MS_SDTR_LEN;
10232         sdtr_buf.msg_req = MS_SDTR_CODE;
10233         sdtr_buf.xfer_period = sdtr_period;
10234         sdtr_offset &= ASC_SYN_MAX_OFFSET;
10235         sdtr_buf.req_ack_offset = sdtr_offset;
10236         if ((sdtr_period_index =
10237              AscGetSynPeriodIndex(asc_dvc, sdtr_period)) <=
10238             asc_dvc->max_sdtr_index) {
10239                 AscMemWordCopyPtrToLram(iop_base,
10240                                         ASCV_MSGOUT_BEG,
10241                                         (uchar *)&sdtr_buf,
10242                                         sizeof(EXT_MSG) >> 1);
10243                 return ((sdtr_period_index << 4) | sdtr_offset);
10244         } else {
10245
10246                 sdtr_buf.req_ack_offset = 0;
10247                 AscMemWordCopyPtrToLram(iop_base,
10248                                         ASCV_MSGOUT_BEG,
10249                                         (uchar *)&sdtr_buf,
10250                                         sizeof(EXT_MSG) >> 1);
10251                 return (0);
10252         }
10253 }
10254
10255 static uchar
10256 AscCalSDTRData(ASC_DVC_VAR *asc_dvc, uchar sdtr_period, uchar syn_offset)
10257 {
10258         uchar byte;
10259         uchar sdtr_period_ix;
10260
10261         sdtr_period_ix = AscGetSynPeriodIndex(asc_dvc, sdtr_period);
10262         if ((sdtr_period_ix > asc_dvc->max_sdtr_index)
10263             ) {
10264                 return (0xFF);
10265         }
10266         byte = (sdtr_period_ix << 4) | (syn_offset & ASC_SYN_MAX_OFFSET);
10267         return (byte);
10268 }
10269
10270 static void AscSetChipSDTR(PortAddr iop_base, uchar sdtr_data, uchar tid_no)
10271 {
10272         AscSetChipSynRegAtID(iop_base, tid_no, sdtr_data);
10273         AscPutMCodeSDTRDoneAtID(iop_base, tid_no, sdtr_data);
10274         return;
10275 }
10276
10277 static uchar AscGetSynPeriodIndex(ASC_DVC_VAR *asc_dvc, uchar syn_time)
10278 {
10279         uchar *period_table;
10280         int max_index;
10281         int min_index;
10282         int i;
10283
10284         period_table = asc_dvc->sdtr_period_tbl;
10285         max_index = (int)asc_dvc->max_sdtr_index;
10286         min_index = (int)asc_dvc->host_init_sdtr_index;
10287         if ((syn_time <= period_table[max_index])) {
10288                 for (i = min_index; i < (max_index - 1); i++) {
10289                         if (syn_time <= period_table[i]) {
10290                                 return ((uchar)i);
10291                         }
10292                 }
10293                 return ((uchar)max_index);
10294         } else {
10295                 return ((uchar)(max_index + 1));
10296         }
10297 }
10298
10299 static uchar AscAllocFreeQueue(PortAddr iop_base, uchar free_q_head)
10300 {
10301         ushort q_addr;
10302         uchar next_qp;
10303         uchar q_status;
10304
10305         q_addr = ASC_QNO_TO_QADDR(free_q_head);
10306         q_status = (uchar)AscReadLramByte(iop_base,
10307                                           (ushort)(q_addr +
10308                                                    ASC_SCSIQ_B_STATUS));
10309         next_qp = AscReadLramByte(iop_base, (ushort)(q_addr + ASC_SCSIQ_B_FWD));
10310         if (((q_status & QS_READY) == 0) && (next_qp != ASC_QLINK_END)) {
10311                 return (next_qp);
10312         }
10313         return (ASC_QLINK_END);
10314 }
10315
10316 static uchar
10317 AscAllocMultipleFreeQueue(PortAddr iop_base, uchar free_q_head, uchar n_free_q)
10318 {
10319         uchar i;
10320
10321         for (i = 0; i < n_free_q; i++) {
10322                 if ((free_q_head = AscAllocFreeQueue(iop_base, free_q_head))
10323                     == ASC_QLINK_END) {
10324                         return (ASC_QLINK_END);
10325                 }
10326         }
10327         return (free_q_head);
10328 }
10329
10330 static int AscHostReqRiscHalt(PortAddr iop_base)
10331 {
10332         int count = 0;
10333         int sta = 0;
10334         uchar saved_stop_code;
10335
10336         if (AscIsChipHalted(iop_base))
10337                 return (1);
10338         saved_stop_code = AscReadLramByte(iop_base, ASCV_STOP_CODE_B);
10339         AscWriteLramByte(iop_base, ASCV_STOP_CODE_B,
10340                          ASC_STOP_HOST_REQ_RISC_HALT | ASC_STOP_REQ_RISC_STOP);
10341         do {
10342                 if (AscIsChipHalted(iop_base)) {
10343                         sta = 1;
10344                         break;
10345                 }
10346                 DvcSleepMilliSecond(100);
10347         } while (count++ < 20);
10348         AscWriteLramByte(iop_base, ASCV_STOP_CODE_B, saved_stop_code);
10349         return (sta);
10350 }
10351
10352 static int AscStopQueueExe(PortAddr iop_base)
10353 {
10354         int count = 0;
10355
10356         if (AscReadLramByte(iop_base, ASCV_STOP_CODE_B) == 0) {
10357                 AscWriteLramByte(iop_base, ASCV_STOP_CODE_B,
10358                                  ASC_STOP_REQ_RISC_STOP);
10359                 do {
10360                         if (AscReadLramByte(iop_base, ASCV_STOP_CODE_B) &
10361                             ASC_STOP_ACK_RISC_STOP) {
10362                                 return (1);
10363                         }
10364                         DvcSleepMilliSecond(100);
10365                 } while (count++ < 20);
10366         }
10367         return (0);
10368 }
10369
10370 static void DvcDelayMicroSecond(ADV_DVC_VAR *asc_dvc, ushort micro_sec)
10371 {
10372         udelay(micro_sec);
10373 }
10374
10375 static void DvcDelayNanoSecond(ASC_DVC_VAR *asc_dvc, ASC_DCNT nano_sec)
10376 {
10377         udelay((nano_sec + 999) / 1000);
10378 }
10379
10380 #ifdef CONFIG_ISA
10381 static ASC_DCNT __init AscGetEisaProductID(PortAddr iop_base)
10382 {
10383         PortAddr eisa_iop;
10384         ushort product_id_high, product_id_low;
10385         ASC_DCNT product_id;
10386
10387         eisa_iop = ASC_GET_EISA_SLOT(iop_base) | ASC_EISA_PID_IOP_MASK;
10388         product_id_low = inpw(eisa_iop);
10389         product_id_high = inpw(eisa_iop + 2);
10390         product_id = ((ASC_DCNT) product_id_high << 16) |
10391             (ASC_DCNT) product_id_low;
10392         return (product_id);
10393 }
10394
10395 static PortAddr __init AscSearchIOPortAddrEISA(PortAddr iop_base)
10396 {
10397         ASC_DCNT eisa_product_id;
10398
10399         if (iop_base == 0) {
10400                 iop_base = ASC_EISA_MIN_IOP_ADDR;
10401         } else {
10402                 if (iop_base == ASC_EISA_MAX_IOP_ADDR)
10403                         return (0);
10404                 if ((iop_base & 0x0050) == 0x0050) {
10405                         iop_base += ASC_EISA_BIG_IOP_GAP;
10406                 } else {
10407                         iop_base += ASC_EISA_SMALL_IOP_GAP;
10408                 }
10409         }
10410         while (iop_base <= ASC_EISA_MAX_IOP_ADDR) {
10411                 eisa_product_id = AscGetEisaProductID(iop_base);
10412                 if ((eisa_product_id == ASC_EISA_ID_740) ||
10413                     (eisa_product_id == ASC_EISA_ID_750)) {
10414                         if (AscFindSignature(iop_base)) {
10415                                 inpw(iop_base + 4);
10416                                 return (iop_base);
10417                         }
10418                 }
10419                 if (iop_base == ASC_EISA_MAX_IOP_ADDR)
10420                         return (0);
10421                 if ((iop_base & 0x0050) == 0x0050) {
10422                         iop_base += ASC_EISA_BIG_IOP_GAP;
10423                 } else {
10424                         iop_base += ASC_EISA_SMALL_IOP_GAP;
10425                 }
10426         }
10427         return (0);
10428 }
10429 #endif /* CONFIG_ISA */
10430
10431 static int AscStartChip(PortAddr iop_base)
10432 {
10433         AscSetChipControl(iop_base, 0);
10434         if ((AscGetChipStatus(iop_base) & CSW_HALTED) != 0) {
10435                 return (0);
10436         }
10437         return (1);
10438 }
10439
10440 static int AscStopChip(PortAddr iop_base)
10441 {
10442         uchar cc_val;
10443
10444         cc_val =
10445             AscGetChipControl(iop_base) &
10446             (~(CC_SINGLE_STEP | CC_TEST | CC_DIAG));
10447         AscSetChipControl(iop_base, (uchar)(cc_val | CC_HALT));
10448         AscSetChipIH(iop_base, INS_HALT);
10449         AscSetChipIH(iop_base, INS_RFLAG_WTM);
10450         if ((AscGetChipStatus(iop_base) & CSW_HALTED) == 0) {
10451                 return (0);
10452         }
10453         return (1);
10454 }
10455
10456 static int AscIsChipHalted(PortAddr iop_base)
10457 {
10458         if ((AscGetChipStatus(iop_base) & CSW_HALTED) != 0) {
10459                 if ((AscGetChipControl(iop_base) & CC_HALT) != 0) {
10460                         return (1);
10461                 }
10462         }
10463         return (0);
10464 }
10465
10466 static void AscSetChipIH(PortAddr iop_base, ushort ins_code)
10467 {
10468         AscSetBank(iop_base, 1);
10469         AscWriteChipIH(iop_base, ins_code);
10470         AscSetBank(iop_base, 0);
10471         return;
10472 }
10473
10474 static void AscAckInterrupt(PortAddr iop_base)
10475 {
10476         uchar host_flag;
10477         uchar risc_flag;
10478         ushort loop;
10479
10480         loop = 0;
10481         do {
10482                 risc_flag = AscReadLramByte(iop_base, ASCV_RISC_FLAG_B);
10483                 if (loop++ > 0x7FFF) {
10484                         break;
10485                 }
10486         } while ((risc_flag & ASC_RISC_FLAG_GEN_INT) != 0);
10487         host_flag =
10488             AscReadLramByte(iop_base,
10489                             ASCV_HOST_FLAG_B) & (~ASC_HOST_FLAG_ACK_INT);
10490         AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B,
10491                          (uchar)(host_flag | ASC_HOST_FLAG_ACK_INT));
10492         AscSetChipStatus(iop_base, CIW_INT_ACK);
10493         loop = 0;
10494         while (AscGetChipStatus(iop_base) & CSW_INT_PENDING) {
10495                 AscSetChipStatus(iop_base, CIW_INT_ACK);
10496                 if (loop++ > 3) {
10497                         break;
10498                 }
10499         }
10500         AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B, host_flag);
10501         return;
10502 }
10503
10504 static void AscDisableInterrupt(PortAddr iop_base)
10505 {
10506         ushort cfg;
10507
10508         cfg = AscGetChipCfgLsw(iop_base);
10509         AscSetChipCfgLsw(iop_base, cfg & (~ASC_CFG0_HOST_INT_ON));
10510         return;
10511 }
10512
10513 static void AscEnableInterrupt(PortAddr iop_base)
10514 {
10515         ushort cfg;
10516
10517         cfg = AscGetChipCfgLsw(iop_base);
10518         AscSetChipCfgLsw(iop_base, cfg | ASC_CFG0_HOST_INT_ON);
10519         return;
10520 }
10521
10522 static void AscSetBank(PortAddr iop_base, uchar bank)
10523 {
10524         uchar val;
10525
10526         val = AscGetChipControl(iop_base) &
10527             (~
10528              (CC_SINGLE_STEP | CC_TEST | CC_DIAG | CC_SCSI_RESET |
10529               CC_CHIP_RESET));
10530         if (bank == 1) {
10531                 val |= CC_BANK_ONE;
10532         } else if (bank == 2) {
10533                 val |= CC_DIAG | CC_BANK_ONE;
10534         } else {
10535                 val &= ~CC_BANK_ONE;
10536         }
10537         AscSetChipControl(iop_base, val);
10538         return;
10539 }
10540
10541 static int AscResetChipAndScsiBus(ASC_DVC_VAR *asc_dvc)
10542 {
10543         PortAddr iop_base;
10544         int i = 10;
10545
10546         iop_base = asc_dvc->iop_base;
10547         while ((AscGetChipStatus(iop_base) & CSW_SCSI_RESET_ACTIVE)
10548                && (i-- > 0)) {
10549                 DvcSleepMilliSecond(100);
10550         }
10551         AscStopChip(iop_base);
10552         AscSetChipControl(iop_base, CC_CHIP_RESET | CC_SCSI_RESET | CC_HALT);
10553         DvcDelayNanoSecond(asc_dvc, 60000);
10554         AscSetChipIH(iop_base, INS_RFLAG_WTM);
10555         AscSetChipIH(iop_base, INS_HALT);
10556         AscSetChipControl(iop_base, CC_CHIP_RESET | CC_HALT);
10557         AscSetChipControl(iop_base, CC_HALT);
10558         DvcSleepMilliSecond(200);
10559         AscSetChipStatus(iop_base, CIW_CLR_SCSI_RESET_INT);
10560         AscSetChipStatus(iop_base, 0);
10561         return (AscIsChipHalted(iop_base));
10562 }
10563
10564 static ASC_DCNT __init AscGetMaxDmaCount(ushort bus_type)
10565 {
10566         if (bus_type & ASC_IS_ISA)
10567                 return (ASC_MAX_ISA_DMA_COUNT);
10568         else if (bus_type & (ASC_IS_EISA | ASC_IS_VL))
10569                 return (ASC_MAX_VL_DMA_COUNT);
10570         return (ASC_MAX_PCI_DMA_COUNT);
10571 }
10572
10573 #ifdef CONFIG_ISA
10574 static ushort __init AscGetIsaDmaChannel(PortAddr iop_base)
10575 {
10576         ushort channel;
10577
10578         channel = AscGetChipCfgLsw(iop_base) & 0x0003;
10579         if (channel == 0x03)
10580                 return (0);
10581         else if (channel == 0x00)
10582                 return (7);
10583         return (channel + 4);
10584 }
10585
10586 static ushort __init AscSetIsaDmaChannel(PortAddr iop_base, ushort dma_channel)
10587 {
10588         ushort cfg_lsw;
10589         uchar value;
10590
10591         if ((dma_channel >= 5) && (dma_channel <= 7)) {
10592                 if (dma_channel == 7)
10593                         value = 0x00;
10594                 else
10595                         value = dma_channel - 4;
10596                 cfg_lsw = AscGetChipCfgLsw(iop_base) & 0xFFFC;
10597                 cfg_lsw |= value;
10598                 AscSetChipCfgLsw(iop_base, cfg_lsw);
10599                 return (AscGetIsaDmaChannel(iop_base));
10600         }
10601         return (0);
10602 }
10603
10604 static uchar __init AscSetIsaDmaSpeed(PortAddr iop_base, uchar speed_value)
10605 {
10606         speed_value &= 0x07;
10607         AscSetBank(iop_base, 1);
10608         AscWriteChipDmaSpeed(iop_base, speed_value);
10609         AscSetBank(iop_base, 0);
10610         return (AscGetIsaDmaSpeed(iop_base));
10611 }
10612
10613 static uchar __init AscGetIsaDmaSpeed(PortAddr iop_base)
10614 {
10615         uchar speed_value;
10616
10617         AscSetBank(iop_base, 1);
10618         speed_value = AscReadChipDmaSpeed(iop_base);
10619         speed_value &= 0x07;
10620         AscSetBank(iop_base, 0);
10621         return (speed_value);
10622 }
10623 #endif /* CONFIG_ISA */
10624
10625 static ushort __init
10626 AscReadPCIConfigWord(ASC_DVC_VAR *asc_dvc, ushort pci_config_offset)
10627 {
10628         uchar lsb, msb;
10629
10630         lsb = DvcReadPCIConfigByte(asc_dvc, pci_config_offset);
10631         msb = DvcReadPCIConfigByte(asc_dvc, pci_config_offset + 1);
10632         return ((ushort)((msb << 8) | lsb));
10633 }
10634
10635 static ushort __init AscInitGetConfig(ASC_DVC_VAR *asc_dvc)
10636 {
10637         ushort warn_code;
10638         PortAddr iop_base;
10639         ushort PCIDeviceID;
10640         ushort PCIVendorID;
10641         uchar PCIRevisionID;
10642         uchar prevCmdRegBits;
10643
10644         warn_code = 0;
10645         iop_base = asc_dvc->iop_base;
10646         asc_dvc->init_state = ASC_INIT_STATE_BEG_GET_CFG;
10647         if (asc_dvc->err_code != 0) {
10648                 return (UW_ERR);
10649         }
10650         if (asc_dvc->bus_type == ASC_IS_PCI) {
10651                 PCIVendorID = AscReadPCIConfigWord(asc_dvc,
10652                                                    AscPCIConfigVendorIDRegister);
10653
10654                 PCIDeviceID = AscReadPCIConfigWord(asc_dvc,
10655                                                    AscPCIConfigDeviceIDRegister);
10656
10657                 PCIRevisionID = DvcReadPCIConfigByte(asc_dvc,
10658                                                      AscPCIConfigRevisionIDRegister);
10659
10660                 if (PCIVendorID != PCI_VENDOR_ID_ASP) {
10661                         warn_code |= ASC_WARN_SET_PCI_CONFIG_SPACE;
10662                 }
10663                 prevCmdRegBits = DvcReadPCIConfigByte(asc_dvc,
10664                                                       AscPCIConfigCommandRegister);
10665
10666                 if ((prevCmdRegBits & AscPCICmdRegBits_IOMemBusMaster) !=
10667                     AscPCICmdRegBits_IOMemBusMaster) {
10668                         DvcWritePCIConfigByte(asc_dvc,
10669                                               AscPCIConfigCommandRegister,
10670                                               (prevCmdRegBits |
10671                                                AscPCICmdRegBits_IOMemBusMaster));
10672
10673                         if ((DvcReadPCIConfigByte(asc_dvc,
10674                                                   AscPCIConfigCommandRegister)
10675                              & AscPCICmdRegBits_IOMemBusMaster)
10676                             != AscPCICmdRegBits_IOMemBusMaster) {
10677                                 warn_code |= ASC_WARN_SET_PCI_CONFIG_SPACE;
10678                         }
10679                 }
10680                 if ((PCIDeviceID == PCI_DEVICE_ID_ASP_1200A) ||
10681                     (PCIDeviceID == PCI_DEVICE_ID_ASP_ABP940)) {
10682                         DvcWritePCIConfigByte(asc_dvc,
10683                                               AscPCIConfigLatencyTimer, 0x00);
10684                         if (DvcReadPCIConfigByte
10685                             (asc_dvc, AscPCIConfigLatencyTimer)
10686                             != 0x00) {
10687                                 warn_code |= ASC_WARN_SET_PCI_CONFIG_SPACE;
10688                         }
10689                 } else if (PCIDeviceID == PCI_DEVICE_ID_ASP_ABP940U) {
10690                         if (DvcReadPCIConfigByte(asc_dvc,
10691                                                  AscPCIConfigLatencyTimer) <
10692                             0x20) {
10693                                 DvcWritePCIConfigByte(asc_dvc,
10694                                                       AscPCIConfigLatencyTimer,
10695                                                       0x20);
10696
10697                                 if (DvcReadPCIConfigByte(asc_dvc,
10698                                                          AscPCIConfigLatencyTimer)
10699                                     < 0x20) {
10700                                         warn_code |=
10701                                             ASC_WARN_SET_PCI_CONFIG_SPACE;
10702                                 }
10703                         }
10704                 }
10705         }
10706
10707         if (AscFindSignature(iop_base)) {
10708                 warn_code |= AscInitAscDvcVar(asc_dvc);
10709                 warn_code |= AscInitFromEEP(asc_dvc);
10710                 asc_dvc->init_state |= ASC_INIT_STATE_END_GET_CFG;
10711                 if (asc_dvc->scsi_reset_wait > ASC_MAX_SCSI_RESET_WAIT) {
10712                         asc_dvc->scsi_reset_wait = ASC_MAX_SCSI_RESET_WAIT;
10713                 }
10714         } else {
10715                 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
10716         }
10717         return (warn_code);
10718 }
10719
10720 static ushort __init AscInitSetConfig(ASC_DVC_VAR *asc_dvc)
10721 {
10722         ushort warn_code = 0;
10723
10724         asc_dvc->init_state |= ASC_INIT_STATE_BEG_SET_CFG;
10725         if (asc_dvc->err_code != 0)
10726                 return (UW_ERR);
10727         if (AscFindSignature(asc_dvc->iop_base)) {
10728                 warn_code |= AscInitFromAscDvcVar(asc_dvc);
10729                 asc_dvc->init_state |= ASC_INIT_STATE_END_SET_CFG;
10730         } else {
10731                 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
10732         }
10733         return (warn_code);
10734 }
10735
10736 static ushort __init AscInitFromAscDvcVar(ASC_DVC_VAR *asc_dvc)
10737 {
10738         PortAddr iop_base;
10739         ushort cfg_msw;
10740         ushort warn_code;
10741         ushort pci_device_id = 0;
10742
10743         iop_base = asc_dvc->iop_base;
10744 #ifdef CONFIG_PCI
10745         if (asc_dvc->cfg->dev)
10746                 pci_device_id = to_pci_dev(asc_dvc->cfg->dev)->device;
10747 #endif
10748         warn_code = 0;
10749         cfg_msw = AscGetChipCfgMsw(iop_base);
10750         if ((cfg_msw & ASC_CFG_MSW_CLR_MASK) != 0) {
10751                 cfg_msw &= (~(ASC_CFG_MSW_CLR_MASK));
10752                 warn_code |= ASC_WARN_CFG_MSW_RECOVER;
10753                 AscSetChipCfgMsw(iop_base, cfg_msw);
10754         }
10755         if ((asc_dvc->cfg->cmd_qng_enabled & asc_dvc->cfg->disc_enable) !=
10756             asc_dvc->cfg->cmd_qng_enabled) {
10757                 asc_dvc->cfg->disc_enable = asc_dvc->cfg->cmd_qng_enabled;
10758                 warn_code |= ASC_WARN_CMD_QNG_CONFLICT;
10759         }
10760         if (AscGetChipStatus(iop_base) & CSW_AUTO_CONFIG) {
10761                 warn_code |= ASC_WARN_AUTO_CONFIG;
10762         }
10763         if ((asc_dvc->bus_type & (ASC_IS_ISA | ASC_IS_VL)) != 0) {
10764                 if (AscSetChipIRQ(iop_base, asc_dvc->irq_no, asc_dvc->bus_type)
10765                     != asc_dvc->irq_no) {
10766                         asc_dvc->err_code |= ASC_IERR_SET_IRQ_NO;
10767                 }
10768         }
10769         if (asc_dvc->bus_type & ASC_IS_PCI) {
10770                 cfg_msw &= 0xFFC0;
10771                 AscSetChipCfgMsw(iop_base, cfg_msw);
10772                 if ((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) == ASC_IS_PCI_ULTRA) {
10773                 } else {
10774                         if ((pci_device_id == PCI_DEVICE_ID_ASP_1200A) ||
10775                             (pci_device_id == PCI_DEVICE_ID_ASP_ABP940)) {
10776                                 asc_dvc->bug_fix_cntl |= ASC_BUG_FIX_IF_NOT_DWB;
10777                                 asc_dvc->bug_fix_cntl |=
10778                                     ASC_BUG_FIX_ASYN_USE_SYN;
10779                         }
10780                 }
10781         } else if (asc_dvc->bus_type == ASC_IS_ISAPNP) {
10782                 if (AscGetChipVersion(iop_base, asc_dvc->bus_type)
10783                     == ASC_CHIP_VER_ASYN_BUG) {
10784                         asc_dvc->bug_fix_cntl |= ASC_BUG_FIX_ASYN_USE_SYN;
10785                 }
10786         }
10787         if (AscSetChipScsiID(iop_base, asc_dvc->cfg->chip_scsi_id) !=
10788             asc_dvc->cfg->chip_scsi_id) {
10789                 asc_dvc->err_code |= ASC_IERR_SET_SCSI_ID;
10790         }
10791 #ifdef CONFIG_ISA
10792         if (asc_dvc->bus_type & ASC_IS_ISA) {
10793                 AscSetIsaDmaChannel(iop_base, asc_dvc->cfg->isa_dma_channel);
10794                 AscSetIsaDmaSpeed(iop_base, asc_dvc->cfg->isa_dma_speed);
10795         }
10796 #endif /* CONFIG_ISA */
10797         return (warn_code);
10798 }
10799
10800 static ushort AscInitAsc1000Driver(ASC_DVC_VAR *asc_dvc)
10801 {
10802         ushort warn_code;
10803         PortAddr iop_base;
10804
10805         iop_base = asc_dvc->iop_base;
10806         warn_code = 0;
10807         if ((asc_dvc->dvc_cntl & ASC_CNTL_RESET_SCSI) &&
10808             !(asc_dvc->init_state & ASC_INIT_RESET_SCSI_DONE)) {
10809                 AscResetChipAndScsiBus(asc_dvc);
10810                 DvcSleepMilliSecond((ASC_DCNT)
10811                                     ((ushort)asc_dvc->scsi_reset_wait * 1000));
10812         }
10813         asc_dvc->init_state |= ASC_INIT_STATE_BEG_LOAD_MC;
10814         if (asc_dvc->err_code != 0)
10815                 return (UW_ERR);
10816         if (!AscFindSignature(asc_dvc->iop_base)) {
10817                 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
10818                 return (warn_code);
10819         }
10820         AscDisableInterrupt(iop_base);
10821         warn_code |= AscInitLram(asc_dvc);
10822         if (asc_dvc->err_code != 0)
10823                 return (UW_ERR);
10824         ASC_DBG1(1, "AscInitAsc1000Driver: _asc_mcode_chksum 0x%lx\n",
10825                  (ulong)_asc_mcode_chksum);
10826         if (AscLoadMicroCode(iop_base, 0, _asc_mcode_buf,
10827                              _asc_mcode_size) != _asc_mcode_chksum) {
10828                 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
10829                 return (warn_code);
10830         }
10831         warn_code |= AscInitMicroCodeVar(asc_dvc);
10832         asc_dvc->init_state |= ASC_INIT_STATE_END_LOAD_MC;
10833         AscEnableInterrupt(iop_base);
10834         return (warn_code);
10835 }
10836
10837 static ushort __init AscInitAscDvcVar(ASC_DVC_VAR *asc_dvc)
10838 {
10839         int i;
10840         PortAddr iop_base;
10841         ushort warn_code;
10842         uchar chip_version;
10843
10844         iop_base = asc_dvc->iop_base;
10845         warn_code = 0;
10846         asc_dvc->err_code = 0;
10847         if ((asc_dvc->bus_type &
10848              (ASC_IS_ISA | ASC_IS_PCI | ASC_IS_EISA | ASC_IS_VL)) == 0) {
10849                 asc_dvc->err_code |= ASC_IERR_NO_BUS_TYPE;
10850         }
10851         AscSetChipControl(iop_base, CC_HALT);
10852         AscSetChipStatus(iop_base, 0);
10853         asc_dvc->bug_fix_cntl = 0;
10854         asc_dvc->pci_fix_asyn_xfer = 0;
10855         asc_dvc->pci_fix_asyn_xfer_always = 0;
10856         /* asc_dvc->init_state initalized in AscInitGetConfig(). */
10857         asc_dvc->sdtr_done = 0;
10858         asc_dvc->cur_total_qng = 0;
10859         asc_dvc->is_in_int = 0;
10860         asc_dvc->in_critical_cnt = 0;
10861         asc_dvc->last_q_shortage = 0;
10862         asc_dvc->use_tagged_qng = 0;
10863         asc_dvc->no_scam = 0;
10864         asc_dvc->unit_not_ready = 0;
10865         asc_dvc->queue_full_or_busy = 0;
10866         asc_dvc->redo_scam = 0;
10867         asc_dvc->res2 = 0;
10868         asc_dvc->host_init_sdtr_index = 0;
10869         asc_dvc->cfg->can_tagged_qng = 0;
10870         asc_dvc->cfg->cmd_qng_enabled = 0;
10871         asc_dvc->dvc_cntl = ASC_DEF_DVC_CNTL;
10872         asc_dvc->init_sdtr = 0;
10873         asc_dvc->max_total_qng = ASC_DEF_MAX_TOTAL_QNG;
10874         asc_dvc->scsi_reset_wait = 3;
10875         asc_dvc->start_motor = ASC_SCSI_WIDTH_BIT_SET;
10876         asc_dvc->max_dma_count = AscGetMaxDmaCount(asc_dvc->bus_type);
10877         asc_dvc->cfg->sdtr_enable = ASC_SCSI_WIDTH_BIT_SET;
10878         asc_dvc->cfg->disc_enable = ASC_SCSI_WIDTH_BIT_SET;
10879         asc_dvc->cfg->chip_scsi_id = ASC_DEF_CHIP_SCSI_ID;
10880         asc_dvc->cfg->lib_serial_no = ASC_LIB_SERIAL_NUMBER;
10881         asc_dvc->cfg->lib_version = (ASC_LIB_VERSION_MAJOR << 8) |
10882             ASC_LIB_VERSION_MINOR;
10883         chip_version = AscGetChipVersion(iop_base, asc_dvc->bus_type);
10884         asc_dvc->cfg->chip_version = chip_version;
10885         asc_dvc->sdtr_period_tbl[0] = SYN_XFER_NS_0;
10886         asc_dvc->sdtr_period_tbl[1] = SYN_XFER_NS_1;
10887         asc_dvc->sdtr_period_tbl[2] = SYN_XFER_NS_2;
10888         asc_dvc->sdtr_period_tbl[3] = SYN_XFER_NS_3;
10889         asc_dvc->sdtr_period_tbl[4] = SYN_XFER_NS_4;
10890         asc_dvc->sdtr_period_tbl[5] = SYN_XFER_NS_5;
10891         asc_dvc->sdtr_period_tbl[6] = SYN_XFER_NS_6;
10892         asc_dvc->sdtr_period_tbl[7] = SYN_XFER_NS_7;
10893         asc_dvc->max_sdtr_index = 7;
10894         if ((asc_dvc->bus_type & ASC_IS_PCI) &&
10895             (chip_version >= ASC_CHIP_VER_PCI_ULTRA_3150)) {
10896                 asc_dvc->bus_type = ASC_IS_PCI_ULTRA;
10897                 asc_dvc->sdtr_period_tbl[0] = SYN_ULTRA_XFER_NS_0;
10898                 asc_dvc->sdtr_period_tbl[1] = SYN_ULTRA_XFER_NS_1;
10899                 asc_dvc->sdtr_period_tbl[2] = SYN_ULTRA_XFER_NS_2;
10900                 asc_dvc->sdtr_period_tbl[3] = SYN_ULTRA_XFER_NS_3;
10901                 asc_dvc->sdtr_period_tbl[4] = SYN_ULTRA_XFER_NS_4;
10902                 asc_dvc->sdtr_period_tbl[5] = SYN_ULTRA_XFER_NS_5;
10903                 asc_dvc->sdtr_period_tbl[6] = SYN_ULTRA_XFER_NS_6;
10904                 asc_dvc->sdtr_period_tbl[7] = SYN_ULTRA_XFER_NS_7;
10905                 asc_dvc->sdtr_period_tbl[8] = SYN_ULTRA_XFER_NS_8;
10906                 asc_dvc->sdtr_period_tbl[9] = SYN_ULTRA_XFER_NS_9;
10907                 asc_dvc->sdtr_period_tbl[10] = SYN_ULTRA_XFER_NS_10;
10908                 asc_dvc->sdtr_period_tbl[11] = SYN_ULTRA_XFER_NS_11;
10909                 asc_dvc->sdtr_period_tbl[12] = SYN_ULTRA_XFER_NS_12;
10910                 asc_dvc->sdtr_period_tbl[13] = SYN_ULTRA_XFER_NS_13;
10911                 asc_dvc->sdtr_period_tbl[14] = SYN_ULTRA_XFER_NS_14;
10912                 asc_dvc->sdtr_period_tbl[15] = SYN_ULTRA_XFER_NS_15;
10913                 asc_dvc->max_sdtr_index = 15;
10914                 if (chip_version == ASC_CHIP_VER_PCI_ULTRA_3150) {
10915                         AscSetExtraControl(iop_base,
10916                                            (SEC_ACTIVE_NEGATE | SEC_SLEW_RATE));
10917                 } else if (chip_version >= ASC_CHIP_VER_PCI_ULTRA_3050) {
10918                         AscSetExtraControl(iop_base,
10919                                            (SEC_ACTIVE_NEGATE |
10920                                             SEC_ENABLE_FILTER));
10921                 }
10922         }
10923         if (asc_dvc->bus_type == ASC_IS_PCI) {
10924                 AscSetExtraControl(iop_base,
10925                                    (SEC_ACTIVE_NEGATE | SEC_SLEW_RATE));
10926         }
10927
10928         asc_dvc->cfg->isa_dma_speed = ASC_DEF_ISA_DMA_SPEED;
10929         if (AscGetChipBusType(iop_base) == ASC_IS_ISAPNP) {
10930                 AscSetChipIFC(iop_base, IFC_INIT_DEFAULT);
10931                 asc_dvc->bus_type = ASC_IS_ISAPNP;
10932         }
10933 #ifdef CONFIG_ISA
10934         if ((asc_dvc->bus_type & ASC_IS_ISA) != 0) {
10935                 asc_dvc->cfg->isa_dma_channel =
10936                     (uchar)AscGetIsaDmaChannel(iop_base);
10937         }
10938 #endif /* CONFIG_ISA */
10939         for (i = 0; i <= ASC_MAX_TID; i++) {
10940                 asc_dvc->cur_dvc_qng[i] = 0;
10941                 asc_dvc->max_dvc_qng[i] = ASC_MAX_SCSI1_QNG;
10942                 asc_dvc->scsiq_busy_head[i] = (ASC_SCSI_Q *)0L;
10943                 asc_dvc->scsiq_busy_tail[i] = (ASC_SCSI_Q *)0L;
10944                 asc_dvc->cfg->max_tag_qng[i] = ASC_MAX_INRAM_TAG_QNG;
10945         }
10946         return (warn_code);
10947 }
10948
10949 static ushort __init AscInitFromEEP(ASC_DVC_VAR *asc_dvc)
10950 {
10951         ASCEEP_CONFIG eep_config_buf;
10952         ASCEEP_CONFIG *eep_config;
10953         PortAddr iop_base;
10954         ushort chksum;
10955         ushort warn_code;
10956         ushort cfg_msw, cfg_lsw;
10957         int i;
10958         int write_eep = 0;
10959
10960         iop_base = asc_dvc->iop_base;
10961         warn_code = 0;
10962         AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0x00FE);
10963         AscStopQueueExe(iop_base);
10964         if ((AscStopChip(iop_base) == FALSE) ||
10965             (AscGetChipScsiCtrl(iop_base) != 0)) {
10966                 asc_dvc->init_state |= ASC_INIT_RESET_SCSI_DONE;
10967                 AscResetChipAndScsiBus(asc_dvc);
10968                 DvcSleepMilliSecond((ASC_DCNT)
10969                                     ((ushort)asc_dvc->scsi_reset_wait * 1000));
10970         }
10971         if (AscIsChipHalted(iop_base) == FALSE) {
10972                 asc_dvc->err_code |= ASC_IERR_START_STOP_CHIP;
10973                 return (warn_code);
10974         }
10975         AscSetPCAddr(iop_base, ASC_MCODE_START_ADDR);
10976         if (AscGetPCAddr(iop_base) != ASC_MCODE_START_ADDR) {
10977                 asc_dvc->err_code |= ASC_IERR_SET_PC_ADDR;
10978                 return (warn_code);
10979         }
10980         eep_config = (ASCEEP_CONFIG *)&eep_config_buf;
10981         cfg_msw = AscGetChipCfgMsw(iop_base);
10982         cfg_lsw = AscGetChipCfgLsw(iop_base);
10983         if ((cfg_msw & ASC_CFG_MSW_CLR_MASK) != 0) {
10984                 cfg_msw &= (~(ASC_CFG_MSW_CLR_MASK));
10985                 warn_code |= ASC_WARN_CFG_MSW_RECOVER;
10986                 AscSetChipCfgMsw(iop_base, cfg_msw);
10987         }
10988         chksum = AscGetEEPConfig(iop_base, eep_config, asc_dvc->bus_type);
10989         ASC_DBG1(1, "AscInitFromEEP: chksum 0x%x\n", chksum);
10990         if (chksum == 0) {
10991                 chksum = 0xaa55;
10992         }
10993         if (AscGetChipStatus(iop_base) & CSW_AUTO_CONFIG) {
10994                 warn_code |= ASC_WARN_AUTO_CONFIG;
10995                 if (asc_dvc->cfg->chip_version == 3) {
10996                         if (eep_config->cfg_lsw != cfg_lsw) {
10997                                 warn_code |= ASC_WARN_EEPROM_RECOVER;
10998                                 eep_config->cfg_lsw =
10999                                     AscGetChipCfgLsw(iop_base);
11000                         }
11001                         if (eep_config->cfg_msw != cfg_msw) {
11002                                 warn_code |= ASC_WARN_EEPROM_RECOVER;
11003                                 eep_config->cfg_msw =
11004                                     AscGetChipCfgMsw(iop_base);
11005                         }
11006                 }
11007         }
11008         eep_config->cfg_msw &= ~ASC_CFG_MSW_CLR_MASK;
11009         eep_config->cfg_lsw |= ASC_CFG0_HOST_INT_ON;
11010         ASC_DBG1(1, "AscInitFromEEP: eep_config->chksum 0x%x\n",
11011                  eep_config->chksum);
11012         if (chksum != eep_config->chksum) {
11013                 if (AscGetChipVersion(iop_base, asc_dvc->bus_type) ==
11014                     ASC_CHIP_VER_PCI_ULTRA_3050) {
11015                         ASC_DBG(1,
11016                                 "AscInitFromEEP: chksum error ignored; EEPROM-less board\n");
11017                         eep_config->init_sdtr = 0xFF;
11018                         eep_config->disc_enable = 0xFF;
11019                         eep_config->start_motor = 0xFF;
11020                         eep_config->use_cmd_qng = 0;
11021                         eep_config->max_total_qng = 0xF0;
11022                         eep_config->max_tag_qng = 0x20;
11023                         eep_config->cntl = 0xBFFF;
11024                         ASC_EEP_SET_CHIP_ID(eep_config, 7);
11025                         eep_config->no_scam = 0;
11026                         eep_config->adapter_info[0] = 0;
11027                         eep_config->adapter_info[1] = 0;
11028                         eep_config->adapter_info[2] = 0;
11029                         eep_config->adapter_info[3] = 0;
11030                         eep_config->adapter_info[4] = 0;
11031                         /* Indicate EEPROM-less board. */
11032                         eep_config->adapter_info[5] = 0xBB;
11033                 } else {
11034                         ASC_PRINT
11035                             ("AscInitFromEEP: EEPROM checksum error; Will try to re-write EEPROM.\n");
11036                         write_eep = 1;
11037                         warn_code |= ASC_WARN_EEPROM_CHKSUM;
11038                 }
11039         }
11040         asc_dvc->cfg->sdtr_enable = eep_config->init_sdtr;
11041         asc_dvc->cfg->disc_enable = eep_config->disc_enable;
11042         asc_dvc->cfg->cmd_qng_enabled = eep_config->use_cmd_qng;
11043         asc_dvc->cfg->isa_dma_speed = ASC_EEP_GET_DMA_SPD(eep_config);
11044         asc_dvc->start_motor = eep_config->start_motor;
11045         asc_dvc->dvc_cntl = eep_config->cntl;
11046         asc_dvc->no_scam = eep_config->no_scam;
11047         asc_dvc->cfg->adapter_info[0] = eep_config->adapter_info[0];
11048         asc_dvc->cfg->adapter_info[1] = eep_config->adapter_info[1];
11049         asc_dvc->cfg->adapter_info[2] = eep_config->adapter_info[2];
11050         asc_dvc->cfg->adapter_info[3] = eep_config->adapter_info[3];
11051         asc_dvc->cfg->adapter_info[4] = eep_config->adapter_info[4];
11052         asc_dvc->cfg->adapter_info[5] = eep_config->adapter_info[5];
11053         if (!AscTestExternalLram(asc_dvc)) {
11054                 if (((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) ==
11055                      ASC_IS_PCI_ULTRA)) {
11056                         eep_config->max_total_qng =
11057                             ASC_MAX_PCI_ULTRA_INRAM_TOTAL_QNG;
11058                         eep_config->max_tag_qng =
11059                             ASC_MAX_PCI_ULTRA_INRAM_TAG_QNG;
11060                 } else {
11061                         eep_config->cfg_msw |= 0x0800;
11062                         cfg_msw |= 0x0800;
11063                         AscSetChipCfgMsw(iop_base, cfg_msw);
11064                         eep_config->max_total_qng = ASC_MAX_PCI_INRAM_TOTAL_QNG;
11065                         eep_config->max_tag_qng = ASC_MAX_INRAM_TAG_QNG;
11066                 }
11067         } else {
11068         }
11069         if (eep_config->max_total_qng < ASC_MIN_TOTAL_QNG) {
11070                 eep_config->max_total_qng = ASC_MIN_TOTAL_QNG;
11071         }
11072         if (eep_config->max_total_qng > ASC_MAX_TOTAL_QNG) {
11073                 eep_config->max_total_qng = ASC_MAX_TOTAL_QNG;
11074         }
11075         if (eep_config->max_tag_qng > eep_config->max_total_qng) {
11076                 eep_config->max_tag_qng = eep_config->max_total_qng;
11077         }
11078         if (eep_config->max_tag_qng < ASC_MIN_TAG_Q_PER_DVC) {
11079                 eep_config->max_tag_qng = ASC_MIN_TAG_Q_PER_DVC;
11080         }
11081         asc_dvc->max_total_qng = eep_config->max_total_qng;
11082         if ((eep_config->use_cmd_qng & eep_config->disc_enable) !=
11083             eep_config->use_cmd_qng) {
11084                 eep_config->disc_enable = eep_config->use_cmd_qng;
11085                 warn_code |= ASC_WARN_CMD_QNG_CONFLICT;
11086         }
11087         if (asc_dvc->bus_type & (ASC_IS_ISA | ASC_IS_VL | ASC_IS_EISA)) {
11088                 asc_dvc->irq_no = AscGetChipIRQ(iop_base, asc_dvc->bus_type);
11089         }
11090         ASC_EEP_SET_CHIP_ID(eep_config,
11091                             ASC_EEP_GET_CHIP_ID(eep_config) & ASC_MAX_TID);
11092         asc_dvc->cfg->chip_scsi_id = ASC_EEP_GET_CHIP_ID(eep_config);
11093         if (((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) == ASC_IS_PCI_ULTRA) &&
11094             !(asc_dvc->dvc_cntl & ASC_CNTL_SDTR_ENABLE_ULTRA)) {
11095                 asc_dvc->host_init_sdtr_index = ASC_SDTR_ULTRA_PCI_10MB_INDEX;
11096         }
11097
11098         for (i = 0; i <= ASC_MAX_TID; i++) {
11099                 asc_dvc->dos_int13_table[i] = eep_config->dos_int13_table[i];
11100                 asc_dvc->cfg->max_tag_qng[i] = eep_config->max_tag_qng;
11101                 asc_dvc->cfg->sdtr_period_offset[i] =
11102                     (uchar)(ASC_DEF_SDTR_OFFSET |
11103                             (asc_dvc->host_init_sdtr_index << 4));
11104         }
11105         eep_config->cfg_msw = AscGetChipCfgMsw(iop_base);
11106         if (write_eep) {
11107                 if ((i =
11108                      AscSetEEPConfig(iop_base, eep_config,
11109                                      asc_dvc->bus_type)) != 0) {
11110                         ASC_PRINT1
11111                             ("AscInitFromEEP: Failed to re-write EEPROM with %d errors.\n",
11112                              i);
11113                 } else {
11114                         ASC_PRINT
11115                             ("AscInitFromEEP: Successfully re-wrote EEPROM.\n");
11116                 }
11117         }
11118         return (warn_code);
11119 }
11120
11121 static ushort AscInitMicroCodeVar(ASC_DVC_VAR *asc_dvc)
11122 {
11123         int i;
11124         ushort warn_code;
11125         PortAddr iop_base;
11126         ASC_PADDR phy_addr;
11127         ASC_DCNT phy_size;
11128
11129         iop_base = asc_dvc->iop_base;
11130         warn_code = 0;
11131         for (i = 0; i <= ASC_MAX_TID; i++) {
11132                 AscPutMCodeInitSDTRAtID(iop_base, i,
11133                                         asc_dvc->cfg->sdtr_period_offset[i]
11134                     );
11135         }
11136
11137         AscInitQLinkVar(asc_dvc);
11138         AscWriteLramByte(iop_base, ASCV_DISC_ENABLE_B,
11139                          asc_dvc->cfg->disc_enable);
11140         AscWriteLramByte(iop_base, ASCV_HOSTSCSI_ID_B,
11141                          ASC_TID_TO_TARGET_ID(asc_dvc->cfg->chip_scsi_id));
11142
11143         /* Align overrun buffer on an 8 byte boundary. */
11144         phy_addr = virt_to_bus(asc_dvc->cfg->overrun_buf);
11145         phy_addr = cpu_to_le32((phy_addr + 7) & ~0x7);
11146         AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_PADDR_D,
11147                                  (uchar *)&phy_addr, 1);
11148         phy_size = cpu_to_le32(ASC_OVERRUN_BSIZE - 8);
11149         AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_BSIZE_D,
11150                                  (uchar *)&phy_size, 1);
11151
11152         asc_dvc->cfg->mcode_date =
11153             AscReadLramWord(iop_base, (ushort)ASCV_MC_DATE_W);
11154         asc_dvc->cfg->mcode_version =
11155             AscReadLramWord(iop_base, (ushort)ASCV_MC_VER_W);
11156
11157         AscSetPCAddr(iop_base, ASC_MCODE_START_ADDR);
11158         if (AscGetPCAddr(iop_base) != ASC_MCODE_START_ADDR) {
11159                 asc_dvc->err_code |= ASC_IERR_SET_PC_ADDR;
11160                 return (warn_code);
11161         }
11162         if (AscStartChip(iop_base) != 1) {
11163                 asc_dvc->err_code |= ASC_IERR_START_STOP_CHIP;
11164                 return (warn_code);
11165         }
11166
11167         return (warn_code);
11168 }
11169
11170 static int __init AscTestExternalLram(ASC_DVC_VAR *asc_dvc)
11171 {
11172         PortAddr iop_base;
11173         ushort q_addr;
11174         ushort saved_word;
11175         int sta;
11176
11177         iop_base = asc_dvc->iop_base;
11178         sta = 0;
11179         q_addr = ASC_QNO_TO_QADDR(241);
11180         saved_word = AscReadLramWord(iop_base, q_addr);
11181         AscSetChipLramAddr(iop_base, q_addr);
11182         AscSetChipLramData(iop_base, 0x55AA);
11183         DvcSleepMilliSecond(10);
11184         AscSetChipLramAddr(iop_base, q_addr);
11185         if (AscGetChipLramData(iop_base) == 0x55AA) {
11186                 sta = 1;
11187                 AscWriteLramWord(iop_base, q_addr, saved_word);
11188         }
11189         return (sta);
11190 }
11191
11192 static int __init AscWriteEEPCmdReg(PortAddr iop_base, uchar cmd_reg)
11193 {
11194         uchar read_back;
11195         int retry;
11196
11197         retry = 0;
11198         while (TRUE) {
11199                 AscSetChipEEPCmd(iop_base, cmd_reg);
11200                 DvcSleepMilliSecond(1);
11201                 read_back = AscGetChipEEPCmd(iop_base);
11202                 if (read_back == cmd_reg) {
11203                         return (1);
11204                 }
11205                 if (retry++ > ASC_EEP_MAX_RETRY) {
11206                         return (0);
11207                 }
11208         }
11209 }
11210
11211 static int __init AscWriteEEPDataReg(PortAddr iop_base, ushort data_reg)
11212 {
11213         ushort read_back;
11214         int retry;
11215
11216         retry = 0;
11217         while (TRUE) {
11218                 AscSetChipEEPData(iop_base, data_reg);
11219                 DvcSleepMilliSecond(1);
11220                 read_back = AscGetChipEEPData(iop_base);
11221                 if (read_back == data_reg) {
11222                         return (1);
11223                 }
11224                 if (retry++ > ASC_EEP_MAX_RETRY) {
11225                         return (0);
11226                 }
11227         }
11228 }
11229
11230 static void __init AscWaitEEPRead(void)
11231 {
11232         DvcSleepMilliSecond(1);
11233         return;
11234 }
11235
11236 static void __init AscWaitEEPWrite(void)
11237 {
11238         DvcSleepMilliSecond(20);
11239         return;
11240 }
11241
11242 static ushort __init AscReadEEPWord(PortAddr iop_base, uchar addr)
11243 {
11244         ushort read_wval;
11245         uchar cmd_reg;
11246
11247         AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_DISABLE);
11248         AscWaitEEPRead();
11249         cmd_reg = addr | ASC_EEP_CMD_READ;
11250         AscWriteEEPCmdReg(iop_base, cmd_reg);
11251         AscWaitEEPRead();
11252         read_wval = AscGetChipEEPData(iop_base);
11253         AscWaitEEPRead();
11254         return (read_wval);
11255 }
11256
11257 static ushort __init
11258 AscWriteEEPWord(PortAddr iop_base, uchar addr, ushort word_val)
11259 {
11260         ushort read_wval;
11261
11262         read_wval = AscReadEEPWord(iop_base, addr);
11263         if (read_wval != word_val) {
11264                 AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_ABLE);
11265                 AscWaitEEPRead();
11266                 AscWriteEEPDataReg(iop_base, word_val);
11267                 AscWaitEEPRead();
11268                 AscWriteEEPCmdReg(iop_base,
11269                                   (uchar)((uchar)ASC_EEP_CMD_WRITE | addr));
11270                 AscWaitEEPWrite();
11271                 AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_DISABLE);
11272                 AscWaitEEPRead();
11273                 return (AscReadEEPWord(iop_base, addr));
11274         }
11275         return (read_wval);
11276 }
11277
11278 static ushort __init
11279 AscGetEEPConfig(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
11280 {
11281         ushort wval;
11282         ushort sum;
11283         ushort *wbuf;
11284         int cfg_beg;
11285         int cfg_end;
11286         int uchar_end_in_config = ASC_EEP_MAX_DVC_ADDR - 2;
11287         int s_addr;
11288
11289         wbuf = (ushort *)cfg_buf;
11290         sum = 0;
11291         /* Read two config words; Byte-swapping done by AscReadEEPWord(). */
11292         for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
11293                 *wbuf = AscReadEEPWord(iop_base, (uchar)s_addr);
11294                 sum += *wbuf;
11295         }
11296         if (bus_type & ASC_IS_VL) {
11297                 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
11298                 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
11299         } else {
11300                 cfg_beg = ASC_EEP_DVC_CFG_BEG;
11301                 cfg_end = ASC_EEP_MAX_DVC_ADDR;
11302         }
11303         for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
11304                 wval = AscReadEEPWord(iop_base, (uchar)s_addr);
11305                 if (s_addr <= uchar_end_in_config) {
11306                         /*
11307                          * Swap all char fields - must unswap bytes already swapped
11308                          * by AscReadEEPWord().
11309                          */
11310                         *wbuf = le16_to_cpu(wval);
11311                 } else {
11312                         /* Don't swap word field at the end - cntl field. */
11313                         *wbuf = wval;
11314                 }
11315                 sum += wval;    /* Checksum treats all EEPROM data as words. */
11316         }
11317         /*
11318          * Read the checksum word which will be compared against 'sum'
11319          * by the caller. Word field already swapped.
11320          */
11321         *wbuf = AscReadEEPWord(iop_base, (uchar)s_addr);
11322         return (sum);
11323 }
11324
11325 static int __init
11326 AscSetEEPConfigOnce(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
11327 {
11328         int n_error;
11329         ushort *wbuf;
11330         ushort word;
11331         ushort sum;
11332         int s_addr;
11333         int cfg_beg;
11334         int cfg_end;
11335         int uchar_end_in_config = ASC_EEP_MAX_DVC_ADDR - 2;
11336
11337         wbuf = (ushort *)cfg_buf;
11338         n_error = 0;
11339         sum = 0;
11340         /* Write two config words; AscWriteEEPWord() will swap bytes. */
11341         for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
11342                 sum += *wbuf;
11343                 if (*wbuf != AscWriteEEPWord(iop_base, (uchar)s_addr, *wbuf)) {
11344                         n_error++;
11345                 }
11346         }
11347         if (bus_type & ASC_IS_VL) {
11348                 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
11349                 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
11350         } else {
11351                 cfg_beg = ASC_EEP_DVC_CFG_BEG;
11352                 cfg_end = ASC_EEP_MAX_DVC_ADDR;
11353         }
11354         for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
11355                 if (s_addr <= uchar_end_in_config) {
11356                         /*
11357                          * This is a char field. Swap char fields before they are
11358                          * swapped again by AscWriteEEPWord().
11359                          */
11360                         word = cpu_to_le16(*wbuf);
11361                         if (word !=
11362                             AscWriteEEPWord(iop_base, (uchar)s_addr, word)) {
11363                                 n_error++;
11364                         }
11365                 } else {
11366                         /* Don't swap word field at the end - cntl field. */
11367                         if (*wbuf !=
11368                             AscWriteEEPWord(iop_base, (uchar)s_addr, *wbuf)) {
11369                                 n_error++;
11370                         }
11371                 }
11372                 sum += *wbuf;   /* Checksum calculated from word values. */
11373         }
11374         /* Write checksum word. It will be swapped by AscWriteEEPWord(). */
11375         *wbuf = sum;
11376         if (sum != AscWriteEEPWord(iop_base, (uchar)s_addr, sum)) {
11377                 n_error++;
11378         }
11379
11380         /* Read EEPROM back again. */
11381         wbuf = (ushort *)cfg_buf;
11382         /*
11383          * Read two config words; Byte-swapping done by AscReadEEPWord().
11384          */
11385         for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
11386                 if (*wbuf != AscReadEEPWord(iop_base, (uchar)s_addr)) {
11387                         n_error++;
11388                 }
11389         }
11390         if (bus_type & ASC_IS_VL) {
11391                 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
11392                 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
11393         } else {
11394                 cfg_beg = ASC_EEP_DVC_CFG_BEG;
11395                 cfg_end = ASC_EEP_MAX_DVC_ADDR;
11396         }
11397         for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
11398                 if (s_addr <= uchar_end_in_config) {
11399                         /*
11400                          * Swap all char fields. Must unswap bytes already swapped
11401                          * by AscReadEEPWord().
11402                          */
11403                         word =
11404                             le16_to_cpu(AscReadEEPWord
11405                                         (iop_base, (uchar)s_addr));
11406                 } else {
11407                         /* Don't swap word field at the end - cntl field. */
11408                         word = AscReadEEPWord(iop_base, (uchar)s_addr);
11409                 }
11410                 if (*wbuf != word) {
11411                         n_error++;
11412                 }
11413         }
11414         /* Read checksum; Byte swapping not needed. */
11415         if (AscReadEEPWord(iop_base, (uchar)s_addr) != sum) {
11416                 n_error++;
11417         }
11418         return (n_error);
11419 }
11420
11421 static int __init
11422 AscSetEEPConfig(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
11423 {
11424         int retry;
11425         int n_error;
11426
11427         retry = 0;
11428         while (TRUE) {
11429                 if ((n_error = AscSetEEPConfigOnce(iop_base, cfg_buf,
11430                                                    bus_type)) == 0) {
11431                         break;
11432                 }
11433                 if (++retry > ASC_EEP_MAX_RETRY) {
11434                         break;
11435                 }
11436         }
11437         return (n_error);
11438 }
11439
11440 static void
11441 AscAsyncFix(ASC_DVC_VAR *asc_dvc, uchar tid_no, ASC_SCSI_INQUIRY *inq)
11442 {
11443         uchar dvc_type;
11444         ASC_SCSI_BIT_ID_TYPE tid_bits;
11445
11446         dvc_type = ASC_INQ_DVC_TYPE(inq);
11447         tid_bits = ASC_TIX_TO_TARGET_ID(tid_no);
11448
11449         if (asc_dvc->bug_fix_cntl & ASC_BUG_FIX_ASYN_USE_SYN) {
11450                 if (!(asc_dvc->init_sdtr & tid_bits)) {
11451                         if ((dvc_type == TYPE_ROM) &&
11452                             (AscCompareString((uchar *)inq->vendor_id,
11453                                               (uchar *)"HP ", 3) == 0)) {
11454                                 asc_dvc->pci_fix_asyn_xfer_always |= tid_bits;
11455                         }
11456                         asc_dvc->pci_fix_asyn_xfer |= tid_bits;
11457                         if ((dvc_type == TYPE_PROCESSOR) ||
11458                             (dvc_type == TYPE_SCANNER) ||
11459                             (dvc_type == TYPE_ROM) || (dvc_type == TYPE_TAPE)) {
11460                                 asc_dvc->pci_fix_asyn_xfer &= ~tid_bits;
11461                         }
11462
11463                         if (asc_dvc->pci_fix_asyn_xfer & tid_bits) {
11464                                 AscSetRunChipSynRegAtID(asc_dvc->iop_base,
11465                                                         tid_no,
11466                                                         ASYN_SDTR_DATA_FIX_PCI_REV_AB);
11467                         }
11468                 }
11469         }
11470         return;
11471 }
11472
11473 static int AscTagQueuingSafe(ASC_SCSI_INQUIRY *inq)
11474 {
11475         if ((inq->add_len >= 32) &&
11476             (AscCompareString((uchar *)inq->vendor_id,
11477                               (uchar *)"QUANTUM XP34301", 15) == 0) &&
11478             (AscCompareString((uchar *)inq->product_rev_level,
11479                               (uchar *)"1071", 4) == 0)) {
11480                 return 0;
11481         }
11482         return 1;
11483 }
11484
11485 static void
11486 AscInquiryHandling(ASC_DVC_VAR *asc_dvc, uchar tid_no, ASC_SCSI_INQUIRY *inq)
11487 {
11488         ASC_SCSI_BIT_ID_TYPE tid_bit = ASC_TIX_TO_TARGET_ID(tid_no);
11489         ASC_SCSI_BIT_ID_TYPE orig_init_sdtr, orig_use_tagged_qng;
11490
11491         orig_init_sdtr = asc_dvc->init_sdtr;
11492         orig_use_tagged_qng = asc_dvc->use_tagged_qng;
11493
11494         asc_dvc->init_sdtr &= ~tid_bit;
11495         asc_dvc->cfg->can_tagged_qng &= ~tid_bit;
11496         asc_dvc->use_tagged_qng &= ~tid_bit;
11497
11498         if (ASC_INQ_RESPONSE_FMT(inq) >= 2 || ASC_INQ_ANSI_VER(inq) >= 2) {
11499                 if ((asc_dvc->cfg->sdtr_enable & tid_bit) && ASC_INQ_SYNC(inq)) {
11500                         asc_dvc->init_sdtr |= tid_bit;
11501                 }
11502                 if ((asc_dvc->cfg->cmd_qng_enabled & tid_bit) &&
11503                     ASC_INQ_CMD_QUEUE(inq)) {
11504                         if (AscTagQueuingSafe(inq)) {
11505                                 asc_dvc->use_tagged_qng |= tid_bit;
11506                                 asc_dvc->cfg->can_tagged_qng |= tid_bit;
11507                         }
11508                 }
11509         }
11510         if (orig_use_tagged_qng != asc_dvc->use_tagged_qng) {
11511                 AscWriteLramByte(asc_dvc->iop_base, ASCV_DISC_ENABLE_B,
11512                                  asc_dvc->cfg->disc_enable);
11513                 AscWriteLramByte(asc_dvc->iop_base, ASCV_USE_TAGGED_QNG_B,
11514                                  asc_dvc->use_tagged_qng);
11515                 AscWriteLramByte(asc_dvc->iop_base, ASCV_CAN_TAGGED_QNG_B,
11516                                  asc_dvc->cfg->can_tagged_qng);
11517
11518                 asc_dvc->max_dvc_qng[tid_no] =
11519                     asc_dvc->cfg->max_tag_qng[tid_no];
11520                 AscWriteLramByte(asc_dvc->iop_base,
11521                                  (ushort)(ASCV_MAX_DVC_QNG_BEG + tid_no),
11522                                  asc_dvc->max_dvc_qng[tid_no]);
11523         }
11524         if (orig_init_sdtr != asc_dvc->init_sdtr) {
11525                 AscAsyncFix(asc_dvc, tid_no, inq);
11526         }
11527         return;
11528 }
11529
11530 static int AscCompareString(uchar *str1, uchar *str2, int len)
11531 {
11532         int i;
11533         int diff;
11534
11535         for (i = 0; i < len; i++) {
11536                 diff = (int)(str1[i] - str2[i]);
11537                 if (diff != 0)
11538                         return (diff);
11539         }
11540         return (0);
11541 }
11542
11543 static uchar AscReadLramByte(PortAddr iop_base, ushort addr)
11544 {
11545         uchar byte_data;
11546         ushort word_data;
11547
11548         if (isodd_word(addr)) {
11549                 AscSetChipLramAddr(iop_base, addr - 1);
11550                 word_data = AscGetChipLramData(iop_base);
11551                 byte_data = (uchar)((word_data >> 8) & 0xFF);
11552         } else {
11553                 AscSetChipLramAddr(iop_base, addr);
11554                 word_data = AscGetChipLramData(iop_base);
11555                 byte_data = (uchar)(word_data & 0xFF);
11556         }
11557         return (byte_data);
11558 }
11559
11560 static ushort AscReadLramWord(PortAddr iop_base, ushort addr)
11561 {
11562         ushort word_data;
11563
11564         AscSetChipLramAddr(iop_base, addr);
11565         word_data = AscGetChipLramData(iop_base);
11566         return (word_data);
11567 }
11568
11569 #if CC_VERY_LONG_SG_LIST
11570 static ASC_DCNT AscReadLramDWord(PortAddr iop_base, ushort addr)
11571 {
11572         ushort val_low, val_high;
11573         ASC_DCNT dword_data;
11574
11575         AscSetChipLramAddr(iop_base, addr);
11576         val_low = AscGetChipLramData(iop_base);
11577         val_high = AscGetChipLramData(iop_base);
11578         dword_data = ((ASC_DCNT) val_high << 16) | (ASC_DCNT) val_low;
11579         return (dword_data);
11580 }
11581 #endif /* CC_VERY_LONG_SG_LIST */
11582
11583 static void AscWriteLramWord(PortAddr iop_base, ushort addr, ushort word_val)
11584 {
11585         AscSetChipLramAddr(iop_base, addr);
11586         AscSetChipLramData(iop_base, word_val);
11587         return;
11588 }
11589
11590 static void AscWriteLramByte(PortAddr iop_base, ushort addr, uchar byte_val)
11591 {
11592         ushort word_data;
11593
11594         if (isodd_word(addr)) {
11595                 addr--;
11596                 word_data = AscReadLramWord(iop_base, addr);
11597                 word_data &= 0x00FF;
11598                 word_data |= (((ushort)byte_val << 8) & 0xFF00);
11599         } else {
11600                 word_data = AscReadLramWord(iop_base, addr);
11601                 word_data &= 0xFF00;
11602                 word_data |= ((ushort)byte_val & 0x00FF);
11603         }
11604         AscWriteLramWord(iop_base, addr, word_data);
11605         return;
11606 }
11607
11608 /*
11609  * Copy 2 bytes to LRAM.
11610  *
11611  * The source data is assumed to be in little-endian order in memory
11612  * and is maintained in little-endian order when written to LRAM.
11613  */
11614 static void
11615 AscMemWordCopyPtrToLram(PortAddr iop_base,
11616                         ushort s_addr, uchar *s_buffer, int words)
11617 {
11618         int i;
11619
11620         AscSetChipLramAddr(iop_base, s_addr);
11621         for (i = 0; i < 2 * words; i += 2) {
11622                 /*
11623                  * On a little-endian system the second argument below
11624                  * produces a little-endian ushort which is written to
11625                  * LRAM in little-endian order. On a big-endian system
11626                  * the second argument produces a big-endian ushort which
11627                  * is "transparently" byte-swapped by outpw() and written
11628                  * in little-endian order to LRAM.
11629                  */
11630                 outpw(iop_base + IOP_RAM_DATA,
11631                       ((ushort)s_buffer[i + 1] << 8) | s_buffer[i]);
11632         }
11633         return;
11634 }
11635
11636 /*
11637  * Copy 4 bytes to LRAM.
11638  *
11639  * The source data is assumed to be in little-endian order in memory
11640  * and is maintained in little-endian order when writen to LRAM.
11641  */
11642 static void
11643 AscMemDWordCopyPtrToLram(PortAddr iop_base,
11644                          ushort s_addr, uchar *s_buffer, int dwords)
11645 {
11646         int i;
11647
11648         AscSetChipLramAddr(iop_base, s_addr);
11649         for (i = 0; i < 4 * dwords; i += 4) {
11650                 outpw(iop_base + IOP_RAM_DATA, ((ushort)s_buffer[i + 1] << 8) | s_buffer[i]);   /* LSW */
11651                 outpw(iop_base + IOP_RAM_DATA, ((ushort)s_buffer[i + 3] << 8) | s_buffer[i + 2]);       /* MSW */
11652         }
11653         return;
11654 }
11655
11656 /*
11657  * Copy 2 bytes from LRAM.
11658  *
11659  * The source data is assumed to be in little-endian order in LRAM
11660  * and is maintained in little-endian order when written to memory.
11661  */
11662 static void
11663 AscMemWordCopyPtrFromLram(PortAddr iop_base,
11664                           ushort s_addr, uchar *d_buffer, int words)
11665 {
11666         int i;
11667         ushort word;
11668
11669         AscSetChipLramAddr(iop_base, s_addr);
11670         for (i = 0; i < 2 * words; i += 2) {
11671                 word = inpw(iop_base + IOP_RAM_DATA);
11672                 d_buffer[i] = word & 0xff;
11673                 d_buffer[i + 1] = (word >> 8) & 0xff;
11674         }
11675         return;
11676 }
11677
11678 static ASC_DCNT AscMemSumLramWord(PortAddr iop_base, ushort s_addr, int words)
11679 {
11680         ASC_DCNT sum;
11681         int i;
11682
11683         sum = 0L;
11684         for (i = 0; i < words; i++, s_addr += 2) {
11685                 sum += AscReadLramWord(iop_base, s_addr);
11686         }
11687         return (sum);
11688 }
11689
11690 static void
11691 AscMemWordSetLram(PortAddr iop_base, ushort s_addr, ushort set_wval, int words)
11692 {
11693         int i;
11694
11695         AscSetChipLramAddr(iop_base, s_addr);
11696         for (i = 0; i < words; i++) {
11697                 AscSetChipLramData(iop_base, set_wval);
11698         }
11699         return;
11700 }
11701
11702 /*
11703  * --- Adv Library Functions
11704  */
11705
11706 /* a_mcode.h */
11707
11708 /* Microcode buffer is kept after initialization for error recovery. */
11709 static unsigned char _adv_asc3550_buf[] = {
11710         0x00, 0x00, 0x00, 0xf2, 0x00, 0xf0, 0x00, 0x16, 0x18, 0xe4, 0x00, 0xfc,
11711         0x01, 0x00, 0x48, 0xe4,
11712         0xbe, 0x18, 0x18, 0x80, 0x03, 0xf6, 0x02, 0x00, 0x00, 0xfa, 0xff, 0xff,
11713         0x28, 0x0e, 0x9e, 0xe7,
11714         0xff, 0x00, 0x82, 0xe7, 0x00, 0xea, 0x00, 0xf6, 0x01, 0xe6, 0x09, 0xe7,
11715         0x55, 0xf0, 0x01, 0xf6,
11716         0x01, 0xfa, 0x08, 0x00, 0x03, 0x00, 0x04, 0x00, 0x18, 0xf4, 0x10, 0x00,
11717         0x00, 0xec, 0x85, 0xf0,
11718         0xbc, 0x00, 0xd5, 0xf0, 0x8e, 0x0c, 0x38, 0x54, 0x00, 0xe6, 0x1e, 0xf0,
11719         0x86, 0xf0, 0xb4, 0x00,
11720         0x98, 0x57, 0xd0, 0x01, 0x0c, 0x1c, 0x3e, 0x1c, 0x0c, 0x00, 0xbb, 0x00,
11721         0xaa, 0x18, 0x02, 0x80,
11722         0x32, 0xf0, 0x01, 0xfc, 0x88, 0x0c, 0xc6, 0x12, 0x02, 0x13, 0x18, 0x40,
11723         0x00, 0x57, 0x01, 0xea,
11724         0x3c, 0x00, 0x6c, 0x01, 0x6e, 0x01, 0x04, 0x12, 0x3e, 0x57, 0x00, 0x80,
11725         0x03, 0xe6, 0xb6, 0x00,
11726         0xc0, 0x00, 0x01, 0x01, 0x3e, 0x01, 0xda, 0x0f, 0x22, 0x10, 0x08, 0x12,
11727         0x02, 0x4a, 0xb9, 0x54,
11728         0x03, 0x58, 0x1b, 0x80, 0x30, 0xe4, 0x4b, 0xe4, 0x20, 0x00, 0x32, 0x00,
11729         0x3e, 0x00, 0x80, 0x00,
11730         0x24, 0x01, 0x3c, 0x01, 0x68, 0x01, 0x6a, 0x01, 0x70, 0x01, 0x72, 0x01,
11731         0x74, 0x01, 0x76, 0x01,
11732         0x78, 0x01, 0x62, 0x0a, 0x92, 0x0c, 0x2c, 0x10, 0x2e, 0x10, 0x06, 0x13,
11733         0x4c, 0x1c, 0xbb, 0x55,
11734         0x3c, 0x56, 0x04, 0x80, 0x4a, 0xe4, 0x02, 0xee, 0x5b, 0xf0, 0xb1, 0xf0,
11735         0x03, 0xf7, 0x06, 0xf7,
11736         0x03, 0xfc, 0x0f, 0x00, 0x40, 0x00, 0xbe, 0x00, 0x00, 0x01, 0xb0, 0x08,
11737         0x30, 0x13, 0x64, 0x15,
11738         0x32, 0x1c, 0x38, 0x1c, 0x4e, 0x1c, 0x10, 0x44, 0x02, 0x48, 0x00, 0x4c,
11739         0x04, 0xea, 0x5d, 0xf0,
11740         0x04, 0xf6, 0x02, 0xfc, 0x05, 0x00, 0x34, 0x00, 0x36, 0x00, 0x98, 0x00,
11741         0xcc, 0x00, 0x20, 0x01,
11742         0x4e, 0x01, 0x4e, 0x0b, 0x1e, 0x0e, 0x0c, 0x10, 0x0a, 0x12, 0x04, 0x13,
11743         0x40, 0x13, 0x30, 0x1c,
11744         0x00, 0x4e, 0xbd, 0x56, 0x06, 0x83, 0x00, 0xdc, 0x05, 0xf0, 0x09, 0xf0,
11745         0x59, 0xf0, 0xa7, 0xf0,
11746         0xb8, 0xf0, 0x0e, 0xf7, 0x06, 0x00, 0x19, 0x00, 0x33, 0x00, 0x9b, 0x00,
11747         0xa4, 0x00, 0xb5, 0x00,
11748         0xba, 0x00, 0xd0, 0x00, 0xe1, 0x00, 0xe7, 0x00, 0xde, 0x03, 0x56, 0x0a,
11749         0x14, 0x0e, 0x02, 0x10,
11750         0x04, 0x10, 0x0a, 0x10, 0x36, 0x10, 0x0a, 0x13, 0x12, 0x13, 0x52, 0x13,
11751         0x10, 0x15, 0x14, 0x15,
11752         0xac, 0x16, 0x20, 0x1c, 0x34, 0x1c, 0x36, 0x1c, 0x08, 0x44, 0x38, 0x44,
11753         0x91, 0x44, 0x0a, 0x45,
11754         0x48, 0x46, 0x01, 0x48, 0x68, 0x54, 0x83, 0x55, 0xb0, 0x57, 0x01, 0x58,
11755         0x83, 0x59, 0x05, 0xe6,
11756         0x0b, 0xf0, 0x0c, 0xf0, 0x5c, 0xf0, 0x4b, 0xf4, 0x04, 0xf8, 0x05, 0xf8,
11757         0x02, 0xfa, 0x03, 0xfa,
11758         0x04, 0xfc, 0x05, 0xfc, 0x07, 0x00, 0x0a, 0x00, 0x0d, 0x00, 0x1c, 0x00,
11759         0x9e, 0x00, 0xa8, 0x00,
11760         0xaa, 0x00, 0xb9, 0x00, 0xe0, 0x00, 0x22, 0x01, 0x26, 0x01, 0x79, 0x01,
11761         0x7a, 0x01, 0xc0, 0x01,
11762         0xc2, 0x01, 0x7c, 0x02, 0x5a, 0x03, 0xea, 0x04, 0xe8, 0x07, 0x68, 0x08,
11763         0x69, 0x08, 0xba, 0x08,
11764         0xe9, 0x09, 0x06, 0x0b, 0x3a, 0x0e, 0x00, 0x10, 0x1a, 0x10, 0xed, 0x10,
11765         0xf1, 0x10, 0x06, 0x12,
11766         0x0c, 0x13, 0x16, 0x13, 0x1e, 0x13, 0x82, 0x13, 0x42, 0x14, 0xd6, 0x14,
11767         0x8a, 0x15, 0xc6, 0x17,
11768         0xd2, 0x17, 0x6b, 0x18, 0x12, 0x1c, 0x46, 0x1c, 0x9c, 0x32, 0x00, 0x40,
11769         0x0e, 0x47, 0x48, 0x47,
11770         0x41, 0x48, 0x89, 0x48, 0x80, 0x4c, 0x00, 0x54, 0x44, 0x55, 0xe5, 0x55,
11771         0x14, 0x56, 0x77, 0x57,
11772         0xbf, 0x57, 0x40, 0x5c, 0x06, 0x80, 0x08, 0x90, 0x03, 0xa1, 0xfe, 0x9c,
11773         0xf0, 0x29, 0x02, 0xfe,
11774         0xb8, 0x0c, 0xff, 0x10, 0x00, 0x00, 0xd0, 0xfe, 0xcc, 0x18, 0x00, 0xcf,
11775         0xfe, 0x80, 0x01, 0xff,
11776         0x03, 0x00, 0x00, 0xfe, 0x93, 0x15, 0xfe, 0x0f, 0x05, 0xff, 0x38, 0x00,
11777         0x00, 0xfe, 0x57, 0x24,
11778         0x00, 0xfe, 0x48, 0x00, 0x4f, 0xff, 0x04, 0x00, 0x00, 0x10, 0xff, 0x09,
11779         0x00, 0x00, 0xff, 0x08,
11780         0x01, 0x01, 0xff, 0x08, 0xff, 0xff, 0xff, 0x27, 0x00, 0x00, 0xff, 0x10,
11781         0xff, 0xff, 0xff, 0x0f,
11782         0x00, 0x00, 0xfe, 0x78, 0x56, 0xfe, 0x34, 0x12, 0xff, 0x21, 0x00, 0x00,
11783         0xfe, 0x04, 0xf7, 0xcf,
11784         0x2a, 0x67, 0x0b, 0x01, 0xfe, 0xce, 0x0e, 0xfe, 0x04, 0xf7, 0xcf, 0x67,
11785         0x0b, 0x3c, 0x2a, 0xfe,
11786         0x3d, 0xf0, 0xfe, 0x02, 0x02, 0xfe, 0x20, 0xf0, 0x9c, 0xfe, 0x91, 0xf0,
11787         0xfe, 0xf0, 0x01, 0xfe,
11788         0x90, 0xf0, 0xfe, 0xf0, 0x01, 0xfe, 0x8f, 0xf0, 0x9c, 0x05, 0x51, 0x3b,
11789         0x02, 0xfe, 0xd4, 0x0c,
11790         0x01, 0xfe, 0x44, 0x0d, 0xfe, 0xdd, 0x12, 0xfe, 0xfc, 0x10, 0xfe, 0x28,
11791         0x1c, 0x05, 0xfe, 0xa6,
11792         0x00, 0xfe, 0xd3, 0x12, 0x47, 0x18, 0xfe, 0xa6, 0x00, 0xb5, 0xfe, 0x48,
11793         0xf0, 0xfe, 0x86, 0x02,
11794         0xfe, 0x49, 0xf0, 0xfe, 0xa0, 0x02, 0xfe, 0x4a, 0xf0, 0xfe, 0xbe, 0x02,
11795         0xfe, 0x46, 0xf0, 0xfe,
11796         0x50, 0x02, 0xfe, 0x47, 0xf0, 0xfe, 0x56, 0x02, 0xfe, 0x43, 0xf0, 0xfe,
11797         0x44, 0x02, 0xfe, 0x44,
11798         0xf0, 0xfe, 0x48, 0x02, 0xfe, 0x45, 0xf0, 0xfe, 0x4c, 0x02, 0x17, 0x0b,
11799         0xa0, 0x17, 0x06, 0x18,
11800         0x96, 0x02, 0x29, 0xfe, 0x00, 0x1c, 0xde, 0xfe, 0x02, 0x1c, 0xdd, 0xfe,
11801         0x1e, 0x1c, 0xfe, 0xe9,
11802         0x10, 0x01, 0xfe, 0x20, 0x17, 0xfe, 0xe7, 0x10, 0xfe, 0x06, 0xfc, 0xc7,
11803         0x0a, 0x6b, 0x01, 0x9e,
11804         0x02, 0x29, 0x14, 0x4d, 0x37, 0x97, 0x01, 0xfe, 0x64, 0x0f, 0x0a, 0x6b,
11805         0x01, 0x82, 0xfe, 0xbd,
11806         0x10, 0x0a, 0x6b, 0x01, 0x82, 0xfe, 0xad, 0x10, 0xfe, 0x16, 0x1c, 0xfe,
11807         0x58, 0x1c, 0x17, 0x06,
11808         0x18, 0x96, 0x2a, 0x25, 0x29, 0xfe, 0x3d, 0xf0, 0xfe, 0x02, 0x02, 0x21,
11809         0xfe, 0x94, 0x02, 0xfe,
11810         0x5a, 0x1c, 0xea, 0xfe, 0x14, 0x1c, 0x14, 0xfe, 0x30, 0x00, 0x37, 0x97,
11811         0x01, 0xfe, 0x54, 0x0f,
11812         0x17, 0x06, 0x18, 0x96, 0x02, 0xd0, 0x1e, 0x20, 0x07, 0x10, 0x34, 0xfe,
11813         0x69, 0x10, 0x17, 0x06,
11814         0x18, 0x96, 0xfe, 0x04, 0xec, 0x20, 0x46, 0x3d, 0x12, 0x20, 0xfe, 0x05,
11815         0xf6, 0xc7, 0x01, 0xfe,
11816         0x52, 0x16, 0x09, 0x4a, 0x4c, 0x35, 0x11, 0x2d, 0x3c, 0x8a, 0x01, 0xe6,
11817         0x02, 0x29, 0x0a, 0x40,
11818         0x01, 0x0e, 0x07, 0x00, 0x5d, 0x01, 0x6f, 0xfe, 0x18, 0x10, 0xfe, 0x41,
11819         0x58, 0x0a, 0x99, 0x01,
11820         0x0e, 0xfe, 0xc8, 0x54, 0x64, 0xfe, 0x0c, 0x03, 0x01, 0xe6, 0x02, 0x29,
11821         0x2a, 0x46, 0xfe, 0x02,
11822         0xe8, 0x27, 0xf8, 0xfe, 0x9e, 0x43, 0xf7, 0xfe, 0x27, 0xf0, 0xfe, 0xdc,
11823         0x01, 0xfe, 0x07, 0x4b,
11824         0xfe, 0x20, 0xf0, 0x9c, 0xfe, 0x40, 0x1c, 0x25, 0xd2, 0xfe, 0x26, 0xf0,
11825         0xfe, 0x56, 0x03, 0xfe,
11826         0xa0, 0xf0, 0xfe, 0x44, 0x03, 0xfe, 0x11, 0xf0, 0x9c, 0xfe, 0xef, 0x10,
11827         0xfe, 0x9f, 0xf0, 0xfe,
11828         0x64, 0x03, 0xeb, 0x0f, 0xfe, 0x11, 0x00, 0x02, 0x5a, 0x2a, 0xfe, 0x48,
11829         0x1c, 0xeb, 0x09, 0x04,
11830         0x1d, 0xfe, 0x18, 0x13, 0x23, 0x1e, 0x98, 0xac, 0x12, 0x98, 0x0a, 0x40,
11831         0x01, 0x0e, 0xac, 0x75,
11832         0x01, 0xfe, 0xbc, 0x15, 0x11, 0xca, 0x25, 0xd2, 0xfe, 0x01, 0xf0, 0xd2,
11833         0xfe, 0x82, 0xf0, 0xfe,
11834         0x92, 0x03, 0xec, 0x11, 0xfe, 0xe4, 0x00, 0x65, 0xfe, 0xa4, 0x03, 0x25,
11835         0x32, 0x1f, 0xfe, 0xb4,
11836         0x03, 0x01, 0x43, 0xfe, 0x06, 0xf0, 0xfe, 0xc4, 0x03, 0x8d, 0x81, 0xfe,
11837         0x0a, 0xf0, 0xfe, 0x7a,
11838         0x06, 0x02, 0x22, 0x05, 0x6b, 0x28, 0x16, 0xfe, 0xf6, 0x04, 0x14, 0x2c,
11839         0x01, 0x33, 0x8f, 0xfe,
11840         0x66, 0x02, 0x02, 0xd1, 0xeb, 0x2a, 0x67, 0x1a, 0xfe, 0x67, 0x1b, 0xf8,
11841         0xf7, 0xfe, 0x48, 0x1c,
11842         0x70, 0x01, 0x6e, 0x87, 0x0a, 0x40, 0x01, 0x0e, 0x07, 0x00, 0x16, 0xd3,
11843         0x0a, 0xca, 0x01, 0x0e,
11844         0x74, 0x60, 0x59, 0x76, 0x27, 0x05, 0x6b, 0x28, 0xfe, 0x10, 0x12, 0x14,
11845         0x2c, 0x01, 0x33, 0x8f,
11846         0xfe, 0x66, 0x02, 0x02, 0xd1, 0xbc, 0x7d, 0xbd, 0x7f, 0x25, 0x22, 0x65,
11847         0xfe, 0x3c, 0x04, 0x1f,
11848         0xfe, 0x38, 0x04, 0x68, 0xfe, 0xa0, 0x00, 0xfe, 0x9b, 0x57, 0xfe, 0x4e,
11849         0x12, 0x2b, 0xff, 0x02,
11850         0x00, 0x10, 0x01, 0x08, 0x1f, 0xfe, 0xe0, 0x04, 0x2b, 0x01, 0x08, 0x1f,
11851         0x22, 0x30, 0x2e, 0xd5,
11852         0xfe, 0x4c, 0x44, 0xfe, 0x4c, 0x12, 0x60, 0xfe, 0x44, 0x48, 0x13, 0x2c,
11853         0xfe, 0x4c, 0x54, 0x64,
11854         0xd3, 0x46, 0x76, 0x27, 0xfa, 0xef, 0xfe, 0x62, 0x13, 0x09, 0x04, 0x1d,
11855         0xfe, 0x2a, 0x13, 0x2f,
11856         0x07, 0x7e, 0xa5, 0xfe, 0x20, 0x10, 0x13, 0x2c, 0xfe, 0x4c, 0x54, 0x64,
11857         0xd3, 0xfa, 0xef, 0x86,
11858         0x09, 0x04, 0x1d, 0xfe, 0x08, 0x13, 0x2f, 0x07, 0x7e, 0x6e, 0x09, 0x04,
11859         0x1d, 0xfe, 0x1c, 0x12,
11860         0x14, 0x92, 0x09, 0x04, 0x06, 0x3b, 0x14, 0xc4, 0x01, 0x33, 0x8f, 0xfe,
11861         0x70, 0x0c, 0x02, 0x22,
11862         0x2b, 0x11, 0xfe, 0xe6, 0x00, 0xfe, 0x1c, 0x90, 0xf9, 0x03, 0x14, 0x92,
11863         0x01, 0x33, 0x02, 0x29,
11864         0xfe, 0x42, 0x5b, 0x67, 0x1a, 0xfe, 0x46, 0x59, 0xf8, 0xf7, 0xfe, 0x87,
11865         0x80, 0xfe, 0x31, 0xe4,
11866         0x4f, 0x09, 0x04, 0x0b, 0xfe, 0x78, 0x13, 0xfe, 0x20, 0x80, 0x07, 0x1a,
11867         0xfe, 0x70, 0x12, 0x49,
11868         0x04, 0x06, 0xfe, 0x60, 0x13, 0x05, 0xfe, 0xa2, 0x00, 0x28, 0x16, 0xfe,
11869         0x80, 0x05, 0xfe, 0x31,
11870         0xe4, 0x6a, 0x49, 0x04, 0x0b, 0xfe, 0x4a, 0x13, 0x05, 0xfe, 0xa0, 0x00,
11871         0x28, 0xfe, 0x42, 0x12,
11872         0x5e, 0x01, 0x08, 0x25, 0x32, 0xf1, 0x01, 0x08, 0x26, 0xfe, 0x98, 0x05,
11873         0x11, 0xfe, 0xe3, 0x00,
11874         0x23, 0x49, 0xfe, 0x4a, 0xf0, 0xfe, 0x6a, 0x05, 0xfe, 0x49, 0xf0, 0xfe,
11875         0x64, 0x05, 0x83, 0x24,
11876         0xfe, 0x21, 0x00, 0xa1, 0x24, 0xfe, 0x22, 0x00, 0xa0, 0x24, 0x4c, 0xfe,
11877         0x09, 0x48, 0x01, 0x08,
11878         0x26, 0xfe, 0x98, 0x05, 0xfe, 0xe2, 0x08, 0x49, 0x04, 0xc5, 0x3b, 0x01,
11879         0x86, 0x24, 0x06, 0x12,
11880         0xcc, 0x37, 0xfe, 0x27, 0x01, 0x09, 0x04, 0x1d, 0xfe, 0x22, 0x12, 0x47,
11881         0x01, 0xa7, 0x14, 0x92,
11882         0x09, 0x04, 0x06, 0x3b, 0x14, 0xc4, 0x01, 0x33, 0x8f, 0xfe, 0x70, 0x0c,
11883         0x02, 0x22, 0x05, 0xfe,
11884         0x9c, 0x00, 0x28, 0xfe, 0x3e, 0x12, 0x05, 0x50, 0x28, 0xfe, 0x36, 0x13,
11885         0x47, 0x01, 0xa7, 0x26,
11886         0xfe, 0x08, 0x06, 0x0a, 0x06, 0x49, 0x04, 0x19, 0xfe, 0x02, 0x12, 0x5f,
11887         0x01, 0xfe, 0xaa, 0x14,
11888         0x1f, 0xfe, 0xfe, 0x05, 0x11, 0x9a, 0x01, 0x43, 0x11, 0xfe, 0xe5, 0x00,
11889         0x05, 0x50, 0xb4, 0x0c,
11890         0x50, 0x05, 0xc6, 0x28, 0xfe, 0x62, 0x12, 0x05, 0x3f, 0x28, 0xfe, 0x5a,
11891         0x13, 0x01, 0xfe, 0x14,
11892         0x18, 0x01, 0xfe, 0x66, 0x18, 0xfe, 0x43, 0x48, 0xb7, 0x19, 0x13, 0x6c,
11893         0xff, 0x02, 0x00, 0x57,
11894         0x48, 0x8b, 0x1c, 0x3d, 0x85, 0xb7, 0x69, 0x47, 0x01, 0xa7, 0x26, 0xfe,
11895         0x72, 0x06, 0x49, 0x04,
11896         0x1b, 0xdf, 0x89, 0x0a, 0x4d, 0x01, 0xfe, 0xd8, 0x14, 0x1f, 0xfe, 0x68,
11897         0x06, 0x11, 0x9a, 0x01,
11898         0x43, 0x11, 0xfe, 0xe5, 0x00, 0x05, 0x3f, 0xb4, 0x0c, 0x3f, 0x17, 0x06,
11899         0x01, 0xa7, 0xec, 0x72,
11900         0x70, 0x01, 0x6e, 0x87, 0x11, 0xfe, 0xe2, 0x00, 0x01, 0x08, 0x25, 0x32,
11901         0xfe, 0x0a, 0xf0, 0xfe,
11902         0xa6, 0x06, 0x8c, 0xfe, 0x5c, 0x07, 0xfe, 0x06, 0xf0, 0xfe, 0x64, 0x07,
11903         0x8d, 0x81, 0x02, 0x22,
11904         0x09, 0x04, 0x0b, 0xfe, 0x2e, 0x12, 0x15, 0x1a, 0x01, 0x08, 0x15, 0x00,
11905         0x01, 0x08, 0x15, 0x00,
11906         0x01, 0x08, 0x15, 0x00, 0x01, 0x08, 0xfe, 0x99, 0xa4, 0x01, 0x08, 0x15,
11907         0x00, 0x02, 0xfe, 0x32,
11908         0x08, 0x61, 0x04, 0x1b, 0xfe, 0x38, 0x12, 0x09, 0x04, 0x1b, 0x6e, 0x15,
11909         0xfe, 0x1b, 0x00, 0x01,
11910         0x08, 0x15, 0x00, 0x01, 0x08, 0x15, 0x00, 0x01, 0x08, 0x15, 0x00, 0x01,
11911         0x08, 0x15, 0x06, 0x01,
11912         0x08, 0x15, 0x00, 0x02, 0xd9, 0x66, 0x4c, 0xfe, 0x3a, 0x55, 0x5f, 0xfe,
11913         0x9a, 0x81, 0x4b, 0x1d,
11914         0xba, 0xfe, 0x32, 0x07, 0x0a, 0x1d, 0xfe, 0x09, 0x6f, 0xaf, 0xfe, 0xca,
11915         0x45, 0xfe, 0x32, 0x12,
11916         0x62, 0x2c, 0x85, 0x66, 0x7b, 0x01, 0x08, 0x25, 0x32, 0xfe, 0x0a, 0xf0,
11917         0xfe, 0x32, 0x07, 0x8d,
11918         0x81, 0x8c, 0xfe, 0x5c, 0x07, 0x02, 0x22, 0x01, 0x43, 0x02, 0xfe, 0x8a,
11919         0x06, 0x15, 0x19, 0x02,
11920         0xfe, 0x8a, 0x06, 0xfe, 0x9c, 0xf7, 0xd4, 0xfe, 0x2c, 0x90, 0xfe, 0xae,
11921         0x90, 0x77, 0xfe, 0xca,
11922         0x07, 0x0c, 0x54, 0x18, 0x55, 0x09, 0x4a, 0x6a, 0x35, 0x1e, 0x20, 0x07,
11923         0x10, 0xfe, 0x0e, 0x12,
11924         0x74, 0xfe, 0x80, 0x80, 0x37, 0x20, 0x63, 0x27, 0xfe, 0x06, 0x10, 0xfe,
11925         0x83, 0xe7, 0xc4, 0xa1,
11926         0xfe, 0x03, 0x40, 0x09, 0x4a, 0x4f, 0x35, 0x01, 0xa8, 0xad, 0xfe, 0x1f,
11927         0x40, 0x12, 0x58, 0x01,
11928         0xa5, 0xfe, 0x08, 0x50, 0xfe, 0x8a, 0x50, 0xfe, 0x44, 0x51, 0xfe, 0xc6,
11929         0x51, 0x83, 0xfb, 0xfe,
11930         0x8a, 0x90, 0x0c, 0x52, 0x18, 0x53, 0xfe, 0x0c, 0x90, 0xfe, 0x8e, 0x90,
11931         0xfe, 0x40, 0x50, 0xfe,
11932         0xc2, 0x50, 0x0c, 0x39, 0x18, 0x3a, 0xfe, 0x4a, 0x10, 0x09, 0x04, 0x6a,
11933         0xfe, 0x2a, 0x12, 0xfe,
11934         0x2c, 0x90, 0xfe, 0xae, 0x90, 0x0c, 0x54, 0x18, 0x55, 0x09, 0x04, 0x4f,
11935         0x85, 0x01, 0xa8, 0xfe,
11936         0x1f, 0x80, 0x12, 0x58, 0xfe, 0x44, 0x90, 0xfe, 0xc6, 0x90, 0x0c, 0x56,
11937         0x18, 0x57, 0xfb, 0xfe,
11938         0x8a, 0x90, 0x0c, 0x52, 0x18, 0x53, 0xfe, 0x40, 0x90, 0xfe, 0xc2, 0x90,
11939         0x0c, 0x39, 0x18, 0x3a,
11940         0x0c, 0x38, 0x18, 0x4e, 0x09, 0x4a, 0x19, 0x35, 0x2a, 0x13, 0xfe, 0x4e,
11941         0x11, 0x65, 0xfe, 0x48,
11942         0x08, 0xfe, 0x9e, 0xf0, 0xfe, 0x5c, 0x08, 0xb1, 0x16, 0x32, 0x2a, 0x73,
11943         0xdd, 0xb8, 0xfe, 0x80,
11944         0x08, 0xb9, 0xfe, 0x9e, 0x08, 0x8c, 0xfe, 0x74, 0x08, 0xfe, 0x06, 0xf0,
11945         0xfe, 0x7a, 0x08, 0x8d,
11946         0x81, 0x02, 0x22, 0x01, 0x43, 0xfe, 0xc9, 0x10, 0x15, 0x19, 0xfe, 0xc9,
11947         0x10, 0x61, 0x04, 0x06,
11948         0xfe, 0x10, 0x12, 0x61, 0x04, 0x0b, 0x45, 0x09, 0x04, 0x0b, 0xfe, 0x68,
11949         0x12, 0xfe, 0x2e, 0x1c,
11950         0x02, 0xfe, 0x24, 0x0a, 0x61, 0x04, 0x06, 0x45, 0x61, 0x04, 0x0b, 0xfe,
11951         0x52, 0x12, 0xfe, 0x2c,
11952         0x1c, 0xfe, 0xaa, 0xf0, 0xfe, 0x1e, 0x09, 0xfe, 0xac, 0xf0, 0xfe, 0xbe,
11953         0x08, 0xfe, 0x8a, 0x10,
11954         0xaa, 0xfe, 0xf3, 0x10, 0xfe, 0xad, 0xf0, 0xfe, 0xca, 0x08, 0x02, 0xfe,
11955         0x24, 0x0a, 0xab, 0xfe,
11956         0xe7, 0x10, 0xfe, 0x2b, 0xf0, 0x9d, 0xe9, 0x1c, 0xfe, 0x00, 0xfe, 0xfe,
11957         0x1c, 0x12, 0xb5, 0xfe,
11958         0xd2, 0xf0, 0x9d, 0xfe, 0x76, 0x18, 0x1c, 0x1a, 0x16, 0x9d, 0x05, 0xcb,
11959         0x1c, 0x06, 0x16, 0x9d,
11960         0xb8, 0x6d, 0xb9, 0x6d, 0xaa, 0xab, 0xfe, 0xb1, 0x10, 0x70, 0x5e, 0x2b,
11961         0x14, 0x92, 0x01, 0x33,
11962         0x0f, 0xfe, 0x35, 0x00, 0xfe, 0x01, 0xf0, 0x5a, 0x0f, 0x7c, 0x02, 0x5a,
11963         0xfe, 0x74, 0x18, 0x1c,
11964         0xfe, 0x00, 0xf8, 0x16, 0x6d, 0x67, 0x1b, 0x01, 0xfe, 0x44, 0x0d, 0x3b,
11965         0x01, 0xe6, 0x1e, 0x27,
11966         0x74, 0x67, 0x1a, 0x02, 0x6d, 0x09, 0x04, 0x0b, 0x21, 0xfe, 0x06, 0x0a,
11967         0x09, 0x04, 0x6a, 0xfe,
11968         0x82, 0x12, 0x09, 0x04, 0x19, 0xfe, 0x66, 0x13, 0x1e, 0x58, 0xac, 0xfc,
11969         0xfe, 0x83, 0x80, 0xfe,
11970         0xc8, 0x44, 0xfe, 0x2e, 0x13, 0xfe, 0x04, 0x91, 0xfe, 0x86, 0x91, 0x63,
11971         0x27, 0xfe, 0x40, 0x59,
11972         0xfe, 0xc1, 0x59, 0x77, 0xd7, 0x05, 0x54, 0x31, 0x55, 0x0c, 0x7b, 0x18,
11973         0x7c, 0xbe, 0x54, 0xbf,
11974         0x55, 0x01, 0xa8, 0xad, 0x63, 0x27, 0x12, 0x58, 0xc0, 0x38, 0xc1, 0x4e,
11975         0x79, 0x56, 0x68, 0x57,
11976         0xf4, 0xf5, 0xfe, 0x04, 0xfa, 0x38, 0xfe, 0x05, 0xfa, 0x4e, 0x01, 0xa5,
11977         0xa2, 0x23, 0x0c, 0x7b,
11978         0x0c, 0x7c, 0x79, 0x56, 0x68, 0x57, 0xfe, 0x12, 0x10, 0x09, 0x04, 0x19,
11979         0x16, 0xd7, 0x79, 0x39,
11980         0x68, 0x3a, 0x09, 0x04, 0xfe, 0xf7, 0x00, 0x35, 0x05, 0x52, 0x31, 0x53,
11981         0xfe, 0x10, 0x58, 0xfe,
11982         0x91, 0x58, 0xfe, 0x14, 0x59, 0xfe, 0x95, 0x59, 0x02, 0x6d, 0x09, 0x04,
11983         0x19, 0x16, 0xd7, 0x09,
11984         0x04, 0xfe, 0xf7, 0x00, 0x35, 0xfe, 0x3a, 0x55, 0xfe, 0x19, 0x81, 0x5f,
11985         0xfe, 0x10, 0x90, 0xfe,
11986         0x92, 0x90, 0xfe, 0xd7, 0x10, 0x2f, 0x07, 0x9b, 0x16, 0xfe, 0xc6, 0x08,
11987         0x11, 0x9b, 0x09, 0x04,
11988         0x0b, 0xfe, 0x14, 0x13, 0x05, 0x39, 0x31, 0x3a, 0x77, 0xfe, 0xc6, 0x08,
11989         0xfe, 0x0c, 0x58, 0xfe,
11990         0x8d, 0x58, 0x02, 0x6d, 0x23, 0x47, 0xfe, 0x19, 0x80, 0xde, 0x09, 0x04,
11991         0x0b, 0xfe, 0x1a, 0x12,
11992         0xfe, 0x6c, 0x19, 0xfe, 0x19, 0x41, 0xe9, 0xb5, 0xfe, 0xd1, 0xf0, 0xd9,
11993         0x14, 0x7a, 0x01, 0x33,
11994         0x0f, 0xfe, 0x44, 0x00, 0xfe, 0x8e, 0x10, 0xfe, 0x6c, 0x19, 0xbe, 0x39,
11995         0xfe, 0xed, 0x19, 0xbf,
11996         0x3a, 0xfe, 0x0c, 0x51, 0xfe, 0x8e, 0x51, 0xe9, 0x1c, 0xfe, 0x00, 0xff,
11997         0x34, 0xfe, 0x74, 0x10,
11998         0xb5, 0xfe, 0xd2, 0xf0, 0xfe, 0xb2, 0x0a, 0xfe, 0x76, 0x18, 0x1c, 0x1a,
11999         0x84, 0x05, 0xcb, 0x1c,
12000         0x06, 0xfe, 0x08, 0x13, 0x0f, 0xfe, 0x16, 0x00, 0x02, 0x5a, 0xfe, 0xd1,
12001         0xf0, 0xfe, 0xc4, 0x0a,
12002         0x14, 0x7a, 0x01, 0x33, 0x0f, 0xfe, 0x17, 0x00, 0xfe, 0x42, 0x10, 0xfe,
12003         0xce, 0xf0, 0xfe, 0xca,
12004         0x0a, 0xfe, 0x3c, 0x10, 0xfe, 0xcd, 0xf0, 0xfe, 0xd6, 0x0a, 0x0f, 0xfe,
12005         0x22, 0x00, 0x02, 0x5a,
12006         0xfe, 0xcb, 0xf0, 0xfe, 0xe2, 0x0a, 0x0f, 0xfe, 0x24, 0x00, 0x02, 0x5a,
12007         0xfe, 0xd0, 0xf0, 0xfe,
12008         0xec, 0x0a, 0x0f, 0x93, 0xdc, 0xfe, 0xcf, 0xf0, 0xfe, 0xf6, 0x0a, 0x0f,
12009         0x4c, 0xfe, 0x10, 0x10,
12010         0xfe, 0xcc, 0xf0, 0xd9, 0x61, 0x04, 0x19, 0x3b, 0x0f, 0xfe, 0x12, 0x00,
12011         0x2a, 0x13, 0xfe, 0x4e,
12012         0x11, 0x65, 0xfe, 0x0c, 0x0b, 0xfe, 0x9e, 0xf0, 0xfe, 0x20, 0x0b, 0xb1,
12013         0x16, 0x32, 0x2a, 0x73,
12014         0xdd, 0xb8, 0x22, 0xb9, 0x22, 0x2a, 0xec, 0x65, 0xfe, 0x2c, 0x0b, 0x25,
12015         0x32, 0x8c, 0xfe, 0x48,
12016         0x0b, 0x8d, 0x81, 0xb8, 0xd4, 0xb9, 0xd4, 0x02, 0x22, 0x01, 0x43, 0xfe,
12017         0xdb, 0x10, 0x11, 0xfe,
12018         0xe8, 0x00, 0xaa, 0xab, 0x70, 0xbc, 0x7d, 0xbd, 0x7f, 0xfe, 0x89, 0xf0,
12019         0x22, 0x30, 0x2e, 0xd8,
12020         0xbc, 0x7d, 0xbd, 0x7f, 0x01, 0x08, 0x1f, 0x22, 0x30, 0x2e, 0xd6, 0xb1,
12021         0x45, 0x0f, 0xfe, 0x42,
12022         0x00, 0x02, 0x5a, 0x78, 0x06, 0xfe, 0x81, 0x49, 0x16, 0xfe, 0x38, 0x0c,
12023         0x09, 0x04, 0x0b, 0xfe,
12024         0x44, 0x13, 0x0f, 0x00, 0x4b, 0x0b, 0xfe, 0x54, 0x12, 0x4b, 0xfe, 0x28,
12025         0x00, 0x21, 0xfe, 0xa6,
12026         0x0c, 0x0a, 0x40, 0x01, 0x0e, 0x07, 0x00, 0x5d, 0x3e, 0xfe, 0x28, 0x00,
12027         0xfe, 0xe2, 0x10, 0x01,
12028         0xe7, 0x01, 0xe8, 0x0a, 0x99, 0x01, 0xfe, 0x32, 0x0e, 0x59, 0x11, 0x2d,
12029         0x01, 0x6f, 0x02, 0x29,
12030         0x0f, 0xfe, 0x44, 0x00, 0x4b, 0x0b, 0xdf, 0x3e, 0x0b, 0xfe, 0xb4, 0x10,
12031         0x01, 0x86, 0x3e, 0x0b,
12032         0xfe, 0xaa, 0x10, 0x01, 0x86, 0xfe, 0x19, 0x82, 0xfe, 0x34, 0x46, 0xa3,
12033         0x3e, 0x0b, 0x0f, 0xfe,
12034         0x43, 0x00, 0xfe, 0x96, 0x10, 0x09, 0x4a, 0x0b, 0x35, 0x01, 0xe7, 0x01,
12035         0xe8, 0x59, 0x11, 0x2d,
12036         0x01, 0x6f, 0x67, 0x0b, 0x59, 0x3c, 0x8a, 0x02, 0xfe, 0x2a, 0x03, 0x09,
12037         0x04, 0x0b, 0x84, 0x3e,
12038         0x0b, 0x0f, 0x00, 0xfe, 0x5c, 0x10, 0x61, 0x04, 0x1b, 0xfe, 0x58, 0x12,
12039         0x09, 0x04, 0x1b, 0xfe,
12040         0x50, 0x13, 0xfe, 0x1c, 0x1c, 0xfe, 0x9d, 0xf0, 0xfe, 0x5c, 0x0c, 0xfe,
12041         0x1c, 0x1c, 0xfe, 0x9d,
12042         0xf0, 0xfe, 0x62, 0x0c, 0x09, 0x4a, 0x1b, 0x35, 0xfe, 0xa9, 0x10, 0x0f,
12043         0xfe, 0x15, 0x00, 0xfe,
12044         0x04, 0xe6, 0x0b, 0x5f, 0x5c, 0x0f, 0xfe, 0x13, 0x00, 0xfe, 0x10, 0x10,
12045         0x0f, 0xfe, 0x47, 0x00,
12046         0xa1, 0x0f, 0xfe, 0x41, 0x00, 0xa0, 0x0f, 0xfe, 0x24, 0x00, 0x87, 0xaa,
12047         0xab, 0x70, 0x05, 0x6b,
12048         0x28, 0x21, 0xd1, 0x5f, 0xfe, 0x04, 0xe6, 0x1b, 0xfe, 0x9d, 0x41, 0xfe,
12049         0x1c, 0x42, 0x59, 0x01,
12050         0xda, 0x02, 0x29, 0xea, 0x14, 0x0b, 0x37, 0x95, 0xa9, 0x14, 0xfe, 0x31,
12051         0x00, 0x37, 0x97, 0x01,
12052         0xfe, 0x54, 0x0f, 0x02, 0xd0, 0x3c, 0xfe, 0x06, 0xec, 0xc9, 0xee, 0x3e,
12053         0x1d, 0xfe, 0xce, 0x45,
12054         0x34, 0x3c, 0xfe, 0x06, 0xea, 0xc9, 0xfe, 0x47, 0x4b, 0x89, 0xfe, 0x75,
12055         0x57, 0x05, 0x51, 0xfe,
12056         0x98, 0x56, 0xfe, 0x38, 0x12, 0x0a, 0x42, 0x01, 0x0e, 0xfe, 0x44, 0x48,
12057         0x46, 0x09, 0x04, 0x1d,
12058         0xfe, 0x1a, 0x13, 0x0a, 0x40, 0x01, 0x0e, 0x47, 0xfe, 0x41, 0x58, 0x0a,
12059         0x99, 0x01, 0x0e, 0xfe,
12060         0x49, 0x54, 0x8e, 0xfe, 0x2a, 0x0d, 0x02, 0xfe, 0x2a, 0x03, 0x0a, 0x51,
12061         0xfe, 0xee, 0x14, 0xee,
12062         0x3e, 0x1d, 0xfe, 0xce, 0x45, 0x34, 0x3c, 0xfe, 0xce, 0x47, 0xfe, 0xad,
12063         0x13, 0x02, 0x29, 0x1e,
12064         0x20, 0x07, 0x10, 0xfe, 0x9e, 0x12, 0x23, 0x12, 0x4d, 0x12, 0x94, 0x12,
12065         0xce, 0x1e, 0x2d, 0x47,
12066         0x37, 0x2d, 0xb1, 0xe0, 0xfe, 0xbc, 0xf0, 0xfe, 0xec, 0x0d, 0x13, 0x06,
12067         0x12, 0x4d, 0x01, 0xfe,
12068         0xe2, 0x15, 0x05, 0xfe, 0x38, 0x01, 0x31, 0xfe, 0x3a, 0x01, 0x77, 0xfe,
12069         0xf0, 0x0d, 0xfe, 0x02,
12070         0xec, 0xce, 0x62, 0x00, 0x5d, 0xfe, 0x04, 0xec, 0x20, 0x46, 0xfe, 0x05,
12071         0xf6, 0xfe, 0x34, 0x01,
12072         0x01, 0xfe, 0x52, 0x16, 0xfb, 0xfe, 0x48, 0xf4, 0x0d, 0xfe, 0x18, 0x13,
12073         0xaf, 0xfe, 0x02, 0xea,
12074         0xce, 0x62, 0x7a, 0xfe, 0xc5, 0x13, 0x14, 0x1b, 0x37, 0x95, 0xa9, 0x5c,
12075         0x05, 0xfe, 0x38, 0x01,
12076         0x1c, 0xfe, 0xf0, 0xff, 0x0c, 0xfe, 0x60, 0x01, 0x05, 0xfe, 0x3a, 0x01,
12077         0x0c, 0xfe, 0x62, 0x01,
12078         0x3d, 0x12, 0x20, 0x24, 0x06, 0x12, 0x2d, 0x11, 0x2d, 0x8a, 0x13, 0x06,
12079         0x03, 0x23, 0x03, 0x1e,
12080         0x4d, 0xfe, 0xf7, 0x12, 0x1e, 0x94, 0xac, 0x12, 0x94, 0x07, 0x7a, 0xfe,
12081         0x71, 0x13, 0xfe, 0x24,
12082         0x1c, 0x14, 0x1a, 0x37, 0x95, 0xa9, 0xfe, 0xd9, 0x10, 0xb6, 0xfe, 0x03,
12083         0xdc, 0xfe, 0x73, 0x57,
12084         0xfe, 0x80, 0x5d, 0x03, 0xb6, 0xfe, 0x03, 0xdc, 0xfe, 0x5b, 0x57, 0xfe,
12085         0x80, 0x5d, 0x03, 0xfe,
12086         0x03, 0x57, 0xb6, 0x23, 0xfe, 0x00, 0xcc, 0x03, 0xfe, 0x03, 0x57, 0xb6,
12087         0x75, 0x03, 0x09, 0x04,
12088         0x4c, 0xfe, 0x22, 0x13, 0xfe, 0x1c, 0x80, 0x07, 0x06, 0xfe, 0x1a, 0x13,
12089         0xfe, 0x1e, 0x80, 0xe1,
12090         0xfe, 0x1d, 0x80, 0xa4, 0xfe, 0x0c, 0x90, 0xfe, 0x0e, 0x13, 0xfe, 0x0e,
12091         0x90, 0xa3, 0xfe, 0x3c,
12092         0x90, 0xfe, 0x30, 0xf4, 0x0b, 0xfe, 0x3c, 0x50, 0xa0, 0x01, 0xfe, 0x82,
12093         0x16, 0x2f, 0x07, 0x2d,
12094         0xe0, 0x01, 0xfe, 0xbc, 0x15, 0x09, 0x04, 0x1d, 0x45, 0x01, 0xe7, 0x01,
12095         0xe8, 0x11, 0xfe, 0xe9,
12096         0x00, 0x09, 0x04, 0x4c, 0xfe, 0x2c, 0x13, 0x01, 0xfe, 0x14, 0x16, 0xfe,
12097         0x1e, 0x1c, 0xfe, 0x14,
12098         0x90, 0xfe, 0x96, 0x90, 0x0c, 0xfe, 0x64, 0x01, 0x18, 0xfe, 0x66, 0x01,
12099         0x09, 0x04, 0x4f, 0xfe,
12100         0x12, 0x12, 0xfe, 0x03, 0x80, 0x74, 0xfe, 0x01, 0xec, 0x20, 0xfe, 0x80,
12101         0x40, 0x12, 0x20, 0x63,
12102         0x27, 0x11, 0xc8, 0x59, 0x1e, 0x20, 0xed, 0x76, 0x20, 0x03, 0xfe, 0x08,
12103         0x1c, 0x05, 0xfe, 0xac,
12104         0x00, 0xfe, 0x06, 0x58, 0x05, 0xfe, 0xae, 0x00, 0xfe, 0x07, 0x58, 0x05,
12105         0xfe, 0xb0, 0x00, 0xfe,
12106         0x08, 0x58, 0x05, 0xfe, 0xb2, 0x00, 0xfe, 0x09, 0x58, 0xfe, 0x0a, 0x1c,
12107         0x24, 0x69, 0x12, 0xc9,
12108         0x23, 0x0c, 0x50, 0x0c, 0x3f, 0x13, 0x40, 0x48, 0x5f, 0x17, 0x1d, 0xfe,
12109         0x90, 0x4d, 0xfe, 0x91,
12110         0x54, 0x21, 0xfe, 0x08, 0x0f, 0x3e, 0x10, 0x13, 0x42, 0x48, 0x17, 0x4c,
12111         0xfe, 0x90, 0x4d, 0xfe,
12112         0x91, 0x54, 0x21, 0xfe, 0x1e, 0x0f, 0x24, 0x10, 0x12, 0x20, 0x78, 0x2c,
12113         0x46, 0x1e, 0x20, 0xed,
12114         0x76, 0x20, 0x11, 0xc8, 0xf6, 0xfe, 0xd6, 0xf0, 0xfe, 0x32, 0x0f, 0xea,
12115         0x70, 0xfe, 0x14, 0x1c,
12116         0xfe, 0x10, 0x1c, 0xfe, 0x18, 0x1c, 0x03, 0x3c, 0xfe, 0x0c, 0x14, 0xee,
12117         0xfe, 0x07, 0xe6, 0x1d,
12118         0xfe, 0xce, 0x47, 0xfe, 0xf5, 0x13, 0x03, 0x01, 0x86, 0x78, 0x2c, 0x46,
12119         0xfa, 0xef, 0xfe, 0x42,
12120         0x13, 0x2f, 0x07, 0x2d, 0xfe, 0x34, 0x13, 0x0a, 0x42, 0x01, 0x0e, 0xb0,
12121         0xfe, 0x36, 0x12, 0xf0,
12122         0xfe, 0x45, 0x48, 0x01, 0xe3, 0xfe, 0x00, 0xcc, 0xb0, 0xfe, 0xf3, 0x13,
12123         0x3d, 0x75, 0x07, 0x10,
12124         0xa3, 0x0a, 0x80, 0x01, 0x0e, 0xfe, 0x80, 0x5c, 0x01, 0x6f, 0xfe, 0x0e,
12125         0x10, 0x07, 0x7e, 0x45,
12126         0xf6, 0xfe, 0xd6, 0xf0, 0xfe, 0x6c, 0x0f, 0x03, 0xfe, 0x44, 0x58, 0x74,
12127         0xfe, 0x01, 0xec, 0x97,
12128         0xfe, 0x9e, 0x40, 0xfe, 0x9d, 0xe7, 0x00, 0xfe, 0x9c, 0xe7, 0x1b, 0x76,
12129         0x27, 0x01, 0xda, 0xfe,
12130         0xdd, 0x10, 0x2a, 0xbc, 0x7d, 0xbd, 0x7f, 0x30, 0x2e, 0xd5, 0x07, 0x1b,
12131         0xfe, 0x48, 0x12, 0x07,
12132         0x0b, 0xfe, 0x56, 0x12, 0x07, 0x1a, 0xfe, 0x30, 0x12, 0x07, 0xc2, 0x16,
12133         0xfe, 0x3e, 0x11, 0x07,
12134         0xfe, 0x23, 0x00, 0x16, 0xfe, 0x4a, 0x11, 0x07, 0x06, 0x16, 0xfe, 0xa8,
12135         0x11, 0x07, 0x19, 0xfe,
12136         0x12, 0x12, 0x07, 0x00, 0x16, 0x22, 0x14, 0xc2, 0x01, 0x33, 0x9f, 0x2b,
12137         0x01, 0x08, 0x8c, 0x43,
12138         0x03, 0x2b, 0xfe, 0x62, 0x08, 0x0a, 0xca, 0x01, 0xfe, 0x32, 0x0e, 0x11,
12139         0x7e, 0x02, 0x29, 0x2b,
12140         0x2f, 0x07, 0x9b, 0xfe, 0xd9, 0x13, 0x79, 0x39, 0x68, 0x3a, 0x77, 0xfe,
12141         0xfc, 0x10, 0x09, 0x04,
12142         0x6a, 0xfe, 0x72, 0x12, 0xc0, 0x38, 0xc1, 0x4e, 0xf4, 0xf5, 0x8e, 0xfe,
12143         0xc6, 0x10, 0x1e, 0x58,
12144         0xfe, 0x26, 0x13, 0x05, 0x7b, 0x31, 0x7c, 0x77, 0xfe, 0x82, 0x0c, 0x0c,
12145         0x54, 0x18, 0x55, 0x23,
12146         0x0c, 0x7b, 0x0c, 0x7c, 0x01, 0xa8, 0x24, 0x69, 0x73, 0x12, 0x58, 0x01,
12147         0xa5, 0xc0, 0x38, 0xc1,
12148         0x4e, 0xfe, 0x04, 0x55, 0xfe, 0xa5, 0x55, 0xfe, 0x04, 0xfa, 0x38, 0xfe,
12149         0x05, 0xfa, 0x4e, 0xfe,
12150         0x91, 0x10, 0x05, 0x56, 0x31, 0x57, 0xfe, 0x40, 0x56, 0xfe, 0xe1, 0x56,
12151         0x0c, 0x56, 0x18, 0x57,
12152         0x83, 0xc0, 0x38, 0xc1, 0x4e, 0xf4, 0xf5, 0x05, 0x52, 0x31, 0x53, 0xfe,
12153         0x00, 0x56, 0xfe, 0xa1,
12154         0x56, 0x0c, 0x52, 0x18, 0x53, 0x09, 0x04, 0x6a, 0xfe, 0x1e, 0x12, 0x1e,
12155         0x58, 0xfe, 0x1f, 0x40,
12156         0x05, 0x54, 0x31, 0x55, 0xfe, 0x2c, 0x50, 0xfe, 0xae, 0x50, 0x05, 0x56,
12157         0x31, 0x57, 0xfe, 0x44,
12158         0x50, 0xfe, 0xc6, 0x50, 0x05, 0x52, 0x31, 0x53, 0xfe, 0x08, 0x50, 0xfe,
12159         0x8a, 0x50, 0x05, 0x39,
12160         0x31, 0x3a, 0xfe, 0x40, 0x50, 0xfe, 0xc2, 0x50, 0x02, 0x5c, 0x24, 0x06,
12161         0x12, 0xcd, 0x02, 0x5b,
12162         0x2b, 0x01, 0x08, 0x1f, 0x44, 0x30, 0x2e, 0xd5, 0x07, 0x06, 0x21, 0x44,
12163         0x2f, 0x07, 0x9b, 0x21,
12164         0x5b, 0x01, 0x6e, 0x1c, 0x3d, 0x16, 0x44, 0x09, 0x04, 0x0b, 0xe2, 0x79,
12165         0x39, 0x68, 0x3a, 0xfe,
12166         0x0a, 0x55, 0x34, 0xfe, 0x8b, 0x55, 0xbe, 0x39, 0xbf, 0x3a, 0xfe, 0x0c,
12167         0x51, 0xfe, 0x8e, 0x51,
12168         0x02, 0x5b, 0xfe, 0x19, 0x81, 0xaf, 0xfe, 0x19, 0x41, 0x02, 0x5b, 0x2b,
12169         0x01, 0x08, 0x25, 0x32,
12170         0x1f, 0xa2, 0x30, 0x2e, 0xd8, 0x4b, 0x1a, 0xfe, 0xa6, 0x12, 0x4b, 0x0b,
12171         0x3b, 0x02, 0x44, 0x01,
12172         0x08, 0x25, 0x32, 0x1f, 0xa2, 0x30, 0x2e, 0xd6, 0x07, 0x1a, 0x21, 0x44,
12173         0x01, 0x08, 0x1f, 0xa2,
12174         0x30, 0x2e, 0xfe, 0xe8, 0x09, 0xfe, 0xc2, 0x49, 0x60, 0x05, 0xfe, 0x9c,
12175         0x00, 0x28, 0x84, 0x49,
12176         0x04, 0x19, 0x34, 0x9f, 0xfe, 0xbb, 0x45, 0x4b, 0x00, 0x45, 0x3e, 0x06,
12177         0x78, 0x3d, 0xfe, 0xda,
12178         0x14, 0x01, 0x6e, 0x87, 0xfe, 0x4b, 0x45, 0xe2, 0x2f, 0x07, 0x9a, 0xe1,
12179         0x05, 0xc6, 0x28, 0x84,
12180         0x05, 0x3f, 0x28, 0x34, 0x5e, 0x02, 0x5b, 0xfe, 0xc0, 0x5d, 0xfe, 0xf8,
12181         0x14, 0xfe, 0x03, 0x17,
12182         0x05, 0x50, 0xb4, 0x0c, 0x50, 0x5e, 0x2b, 0x01, 0x08, 0x26, 0x5c, 0x01,
12183         0xfe, 0xaa, 0x14, 0x02,
12184         0x5c, 0x01, 0x08, 0x25, 0x32, 0x1f, 0x44, 0x30, 0x2e, 0xd6, 0x07, 0x06,
12185         0x21, 0x44, 0x01, 0xfe,
12186         0x8e, 0x13, 0xfe, 0x42, 0x58, 0xfe, 0x82, 0x14, 0xfe, 0xa4, 0x14, 0x87,
12187         0xfe, 0x4a, 0xf4, 0x0b,
12188         0x16, 0x44, 0xfe, 0x4a, 0xf4, 0x06, 0xfe, 0x0c, 0x12, 0x2f, 0x07, 0x9a,
12189         0x85, 0x02, 0x5b, 0x05,
12190         0x3f, 0xb4, 0x0c, 0x3f, 0x5e, 0x2b, 0x01, 0x08, 0x26, 0x5c, 0x01, 0xfe,
12191         0xd8, 0x14, 0x02, 0x5c,
12192         0x13, 0x06, 0x65, 0xfe, 0xca, 0x12, 0x26, 0xfe, 0xe0, 0x12, 0x72, 0xf1,
12193         0x01, 0x08, 0x23, 0x72,
12194         0x03, 0x8f, 0xfe, 0xdc, 0x12, 0x25, 0xfe, 0xdc, 0x12, 0x1f, 0xfe, 0xca,
12195         0x12, 0x5e, 0x2b, 0x01,
12196         0x08, 0xfe, 0xd5, 0x10, 0x13, 0x6c, 0xff, 0x02, 0x00, 0x57, 0x48, 0x8b,
12197         0x1c, 0xfe, 0xff, 0x7f,
12198         0xfe, 0x30, 0x56, 0xfe, 0x00, 0x5c, 0x03, 0x13, 0x6c, 0xff, 0x02, 0x00,
12199         0x57, 0x48, 0x8b, 0x1c,
12200         0x3d, 0xfe, 0x30, 0x56, 0xfe, 0x00, 0x5c, 0x03, 0x13, 0x6c, 0xff, 0x02,
12201         0x00, 0x57, 0x48, 0x8b,
12202         0x03, 0x13, 0x6c, 0xff, 0x02, 0x00, 0x57, 0x48, 0x8b, 0xfe, 0x0b, 0x58,
12203         0x03, 0x0a, 0x50, 0x01,
12204         0x82, 0x0a, 0x3f, 0x01, 0x82, 0x03, 0xfc, 0x1c, 0x10, 0xff, 0x03, 0x00,
12205         0x54, 0xfe, 0x00, 0xf4,
12206         0x19, 0x48, 0xfe, 0x00, 0x7d, 0xfe, 0x01, 0x7d, 0xfe, 0x02, 0x7d, 0xfe,
12207         0x03, 0x7c, 0x63, 0x27,
12208         0x0c, 0x52, 0x18, 0x53, 0xbe, 0x56, 0xbf, 0x57, 0x03, 0xfe, 0x62, 0x08,
12209         0xfe, 0x82, 0x4a, 0xfe,
12210         0xe1, 0x1a, 0xfe, 0x83, 0x5a, 0x74, 0x03, 0x01, 0xfe, 0x14, 0x18, 0xfe,
12211         0x42, 0x48, 0x5f, 0x60,
12212         0x89, 0x01, 0x08, 0x1f, 0xfe, 0xa2, 0x14, 0x30, 0x2e, 0xd8, 0x01, 0x08,
12213         0x1f, 0xfe, 0xa2, 0x14,
12214         0x30, 0x2e, 0xfe, 0xe8, 0x0a, 0xfe, 0xc1, 0x59, 0x05, 0xc6, 0x28, 0xfe,
12215         0xcc, 0x12, 0x49, 0x04,
12216         0x1b, 0xfe, 0xc4, 0x13, 0x23, 0x62, 0x1b, 0xe2, 0x4b, 0xc3, 0x64, 0xfe,
12217         0xe8, 0x13, 0x3b, 0x13,
12218         0x06, 0x17, 0xc3, 0x78, 0xdb, 0xfe, 0x78, 0x10, 0xff, 0x02, 0x83, 0x55,
12219         0xa1, 0xff, 0x02, 0x83,
12220         0x55, 0x62, 0x1a, 0xa4, 0xbb, 0xfe, 0x30, 0x00, 0x8e, 0xe4, 0x17, 0x2c,
12221         0x13, 0x06, 0xfe, 0x56,
12222         0x10, 0x62, 0x0b, 0xe1, 0xbb, 0xfe, 0x64, 0x00, 0x8e, 0xe4, 0x0a, 0xfe,
12223         0x64, 0x00, 0x17, 0x93,
12224         0x13, 0x06, 0xfe, 0x28, 0x10, 0x62, 0x06, 0xfe, 0x60, 0x13, 0xbb, 0xfe,
12225         0xc8, 0x00, 0x8e, 0xe4,
12226         0x0a, 0xfe, 0xc8, 0x00, 0x17, 0x4d, 0x13, 0x06, 0x83, 0xbb, 0xfe, 0x90,
12227         0x01, 0xba, 0xfe, 0x4e,
12228         0x14, 0x89, 0xfe, 0x12, 0x10, 0xfe, 0x43, 0xf4, 0x94, 0xfe, 0x56, 0xf0,
12229         0xfe, 0x60, 0x14, 0xfe,
12230         0x04, 0xf4, 0x6c, 0xfe, 0x43, 0xf4, 0x93, 0xfe, 0xf3, 0x10, 0xf9, 0x01,
12231         0xfe, 0x22, 0x13, 0x1c,
12232         0x3d, 0xfe, 0x10, 0x13, 0xfe, 0x00, 0x17, 0xfe, 0x4d, 0xe4, 0x69, 0xba,
12233         0xfe, 0x9c, 0x14, 0xb7,
12234         0x69, 0xfe, 0x1c, 0x10, 0xfe, 0x00, 0x17, 0xfe, 0x4d, 0xe4, 0x19, 0xba,
12235         0xfe, 0x9c, 0x14, 0xb7,
12236         0x19, 0x83, 0x60, 0x23, 0xfe, 0x4d, 0xf4, 0x00, 0xdf, 0x89, 0x13, 0x06,
12237         0xfe, 0xb4, 0x56, 0xfe,
12238         0xc3, 0x58, 0x03, 0x60, 0x13, 0x0b, 0x03, 0x15, 0x06, 0x01, 0x08, 0x26,
12239         0xe5, 0x15, 0x0b, 0x01,
12240         0x08, 0x26, 0xe5, 0x15, 0x1a, 0x01, 0x08, 0x26, 0xe5, 0x72, 0xfe, 0x89,
12241         0x49, 0x01, 0x08, 0x03,
12242         0x15, 0x06, 0x01, 0x08, 0x26, 0xa6, 0x15, 0x1a, 0x01, 0x08, 0x26, 0xa6,
12243         0x15, 0x06, 0x01, 0x08,
12244         0x26, 0xa6, 0xfe, 0x89, 0x49, 0x01, 0x08, 0x26, 0xa6, 0x72, 0xfe, 0x89,
12245         0x4a, 0x01, 0x08, 0x03,
12246         0x60, 0x03, 0x1e, 0xcc, 0x07, 0x06, 0xfe, 0x44, 0x13, 0xad, 0x12, 0xcc,
12247         0xfe, 0x49, 0xf4, 0x00,
12248         0x3b, 0x72, 0x9f, 0x5e, 0xfe, 0x01, 0xec, 0xfe, 0x27, 0x01, 0xf1, 0x01,
12249         0x08, 0x2f, 0x07, 0xfe,
12250         0xe3, 0x00, 0xfe, 0x20, 0x13, 0x1f, 0xfe, 0x5a, 0x15, 0x23, 0x12, 0xcd,
12251         0x01, 0x43, 0x1e, 0xcd,
12252         0x07, 0x06, 0x45, 0x09, 0x4a, 0x06, 0x35, 0x03, 0x0a, 0x42, 0x01, 0x0e,
12253         0xed, 0x88, 0x07, 0x10,
12254         0xa4, 0x0a, 0x80, 0x01, 0x0e, 0x88, 0x0a, 0x51, 0x01, 0x9e, 0x03, 0x0a,
12255         0x80, 0x01, 0x0e, 0x88,
12256         0xfe, 0x80, 0xe7, 0x10, 0x07, 0x10, 0x84, 0xfe, 0x45, 0x58, 0x01, 0xe3,
12257         0x88, 0x03, 0x0a, 0x42,
12258         0x01, 0x0e, 0x88, 0x0a, 0x51, 0x01, 0x9e, 0x03, 0x0a, 0x42, 0x01, 0x0e,
12259         0xfe, 0x80, 0x80, 0xf2,
12260         0xfe, 0x49, 0xe4, 0x10, 0xa4, 0x0a, 0x80, 0x01, 0x0e, 0xf2, 0x0a, 0x51,
12261         0x01, 0x82, 0x03, 0x17,
12262         0x10, 0x71, 0x66, 0xfe, 0x60, 0x01, 0xfe, 0x18, 0xdf, 0xfe, 0x19, 0xde,
12263         0xfe, 0x24, 0x1c, 0xfe,
12264         0x1d, 0xf7, 0x1d, 0x90, 0xfe, 0xf6, 0x15, 0x01, 0xfe, 0xfc, 0x16, 0xe0,
12265         0x91, 0x1d, 0x66, 0xfe,
12266         0x2c, 0x01, 0xfe, 0x2f, 0x19, 0x03, 0xae, 0x21, 0xfe, 0xe6, 0x15, 0xfe,
12267         0xda, 0x10, 0x17, 0x10,
12268         0x71, 0x05, 0xfe, 0x64, 0x01, 0xfe, 0x00, 0xf4, 0x19, 0xfe, 0x18, 0x58,
12269         0x05, 0xfe, 0x66, 0x01,
12270         0xfe, 0x19, 0x58, 0x91, 0x19, 0xfe, 0x3c, 0x90, 0xfe, 0x30, 0xf4, 0x06,
12271         0xfe, 0x3c, 0x50, 0x66,
12272         0xfe, 0x38, 0x00, 0xfe, 0x0f, 0x79, 0xfe, 0x1c, 0xf7, 0x19, 0x90, 0xfe,
12273         0x40, 0x16, 0xfe, 0xb6,
12274         0x14, 0x34, 0x03, 0xae, 0x21, 0xfe, 0x18, 0x16, 0xfe, 0x9c, 0x10, 0x17,
12275         0x10, 0x71, 0xfe, 0x83,
12276         0x5a, 0xfe, 0x18, 0xdf, 0xfe, 0x19, 0xde, 0xfe, 0x1d, 0xf7, 0x38, 0x90,
12277         0xfe, 0x62, 0x16, 0xfe,
12278         0x94, 0x14, 0xfe, 0x10, 0x13, 0x91, 0x38, 0x66, 0x1b, 0xfe, 0xaf, 0x19,
12279         0xfe, 0x98, 0xe7, 0x00,
12280         0x03, 0xae, 0x21, 0xfe, 0x56, 0x16, 0xfe, 0x6c, 0x10, 0x17, 0x10, 0x71,
12281         0xfe, 0x30, 0xbc, 0xfe,
12282         0xb2, 0xbc, 0x91, 0xc5, 0x66, 0x1b, 0xfe, 0x0f, 0x79, 0xfe, 0x1c, 0xf7,
12283         0xc5, 0x90, 0xfe, 0x9a,
12284         0x16, 0xfe, 0x5c, 0x14, 0x34, 0x03, 0xae, 0x21, 0xfe, 0x86, 0x16, 0xfe,
12285         0x42, 0x10, 0xfe, 0x02,
12286         0xf6, 0x10, 0x71, 0xfe, 0x18, 0xfe, 0x54, 0xfe, 0x19, 0xfe, 0x55, 0xfc,
12287         0xfe, 0x1d, 0xf7, 0x4f,
12288         0x90, 0xfe, 0xc0, 0x16, 0xfe, 0x36, 0x14, 0xfe, 0x1c, 0x13, 0x91, 0x4f,
12289         0x47, 0xfe, 0x83, 0x58,
12290         0xfe, 0xaf, 0x19, 0xfe, 0x80, 0xe7, 0x10, 0xfe, 0x81, 0xe7, 0x10, 0x11,
12291         0xfe, 0xdd, 0x00, 0x63,
12292         0x27, 0x03, 0x63, 0x27, 0xfe, 0x12, 0x45, 0x21, 0xfe, 0xb0, 0x16, 0x14,
12293         0x06, 0x37, 0x95, 0xa9,
12294         0x02, 0x29, 0xfe, 0x39, 0xf0, 0xfe, 0x04, 0x17, 0x23, 0x03, 0xfe, 0x7e,
12295         0x18, 0x1c, 0x1a, 0x5d,
12296         0x13, 0x0d, 0x03, 0x71, 0x05, 0xcb, 0x1c, 0x06, 0xfe, 0xef, 0x12, 0xfe,
12297         0xe1, 0x10, 0x78, 0x2c,
12298         0x46, 0x2f, 0x07, 0x2d, 0xfe, 0x3c, 0x13, 0xfe, 0x82, 0x14, 0xfe, 0x42,
12299         0x13, 0x3c, 0x8a, 0x0a,
12300         0x42, 0x01, 0x0e, 0xb0, 0xfe, 0x3e, 0x12, 0xf0, 0xfe, 0x45, 0x48, 0x01,
12301         0xe3, 0xfe, 0x00, 0xcc,
12302         0xb0, 0xfe, 0xf3, 0x13, 0x3d, 0x75, 0x07, 0x10, 0xa3, 0x0a, 0x80, 0x01,
12303         0x0e, 0xf2, 0x01, 0x6f,
12304         0xfe, 0x16, 0x10, 0x07, 0x7e, 0x85, 0xfe, 0x40, 0x14, 0xfe, 0x24, 0x12,
12305         0xf6, 0xfe, 0xd6, 0xf0,
12306         0xfe, 0x24, 0x17, 0x17, 0x0b, 0x03, 0xfe, 0x9c, 0xe7, 0x0b, 0x0f, 0xfe,
12307         0x15, 0x00, 0x59, 0x76,
12308         0x27, 0x01, 0xda, 0x17, 0x06, 0x03, 0x3c, 0x8a, 0x09, 0x4a, 0x1d, 0x35,
12309         0x11, 0x2d, 0x01, 0x6f,
12310         0x17, 0x06, 0x03, 0xfe, 0x38, 0x90, 0xfe, 0xba, 0x90, 0x79, 0xc7, 0x68,
12311         0xc8, 0xfe, 0x48, 0x55,
12312         0x34, 0xfe, 0xc9, 0x55, 0x03, 0x1e, 0x98, 0x73, 0x12, 0x98, 0x03, 0x0a,
12313         0x99, 0x01, 0x0e, 0xf0,
12314         0x0a, 0x40, 0x01, 0x0e, 0xfe, 0x49, 0x44, 0x16, 0xfe, 0xf0, 0x17, 0x73,
12315         0x75, 0x03, 0x0a, 0x42,
12316         0x01, 0x0e, 0x07, 0x10, 0x45, 0x0a, 0x51, 0x01, 0x9e, 0x0a, 0x40, 0x01,
12317         0x0e, 0x73, 0x75, 0x03,
12318         0xfe, 0x4e, 0xe4, 0x1a, 0x64, 0xfe, 0x24, 0x18, 0x05, 0xfe, 0x90, 0x00,
12319         0xfe, 0x3a, 0x45, 0x5b,
12320         0xfe, 0x4e, 0xe4, 0xc2, 0x64, 0xfe, 0x36, 0x18, 0x05, 0xfe, 0x92, 0x00,
12321         0xfe, 0x02, 0xe6, 0x1b,
12322         0xdc, 0xfe, 0x4e, 0xe4, 0xfe, 0x0b, 0x00, 0x64, 0xfe, 0x48, 0x18, 0x05,
12323         0xfe, 0x94, 0x00, 0xfe,
12324         0x02, 0xe6, 0x19, 0xfe, 0x08, 0x10, 0x05, 0xfe, 0x96, 0x00, 0xfe, 0x02,
12325         0xe6, 0x2c, 0xfe, 0x4e,
12326         0x45, 0xfe, 0x0c, 0x12, 0xaf, 0xff, 0x04, 0x68, 0x54, 0xde, 0x1c, 0x69,
12327         0x03, 0x07, 0x7a, 0xfe,
12328         0x5a, 0xf0, 0xfe, 0x74, 0x18, 0x24, 0xfe, 0x09, 0x00, 0xfe, 0x34, 0x10,
12329         0x07, 0x1b, 0xfe, 0x5a,
12330         0xf0, 0xfe, 0x82, 0x18, 0x24, 0xc3, 0xfe, 0x26, 0x10, 0x07, 0x1a, 0x5d,
12331         0x24, 0x2c, 0xdc, 0x07,
12332         0x0b, 0x5d, 0x24, 0x93, 0xfe, 0x0e, 0x10, 0x07, 0x06, 0x5d, 0x24, 0x4d,
12333         0x9f, 0xad, 0x03, 0x14,
12334         0xfe, 0x09, 0x00, 0x01, 0x33, 0xfe, 0x04, 0xfe, 0x7d, 0x05, 0x7f, 0xf9,
12335         0x03, 0x25, 0xfe, 0xca,
12336         0x18, 0xfe, 0x14, 0xf0, 0x08, 0x65, 0xfe, 0xc6, 0x18, 0x03, 0xff, 0x1a,
12337         0x00, 0x00,
12338 };
12339
12340 static unsigned short _adv_asc3550_size = sizeof(_adv_asc3550_buf);     /* 0x13AD */
12341 static ADV_DCNT _adv_asc3550_chksum = 0x04D52DDDUL;     /* Expanded little-endian checksum. */
12342
12343 /* Microcode buffer is kept after initialization for error recovery. */
12344 static unsigned char _adv_asc38C0800_buf[] = {
12345         0x00, 0x00, 0x00, 0xf2, 0x00, 0xf0, 0x00, 0xfc, 0x00, 0x16, 0x18, 0xe4,
12346         0x01, 0x00, 0x48, 0xe4,
12347         0x18, 0x80, 0x03, 0xf6, 0x02, 0x00, 0xce, 0x19, 0x00, 0xfa, 0xff, 0xff,
12348         0x1c, 0x0f, 0x00, 0xf6,
12349         0x9e, 0xe7, 0xff, 0x00, 0x82, 0xe7, 0x00, 0xea, 0x01, 0xfa, 0x01, 0xe6,
12350         0x09, 0xe7, 0x55, 0xf0,
12351         0x01, 0xf6, 0x03, 0x00, 0x04, 0x00, 0x10, 0x00, 0x1e, 0xf0, 0x85, 0xf0,
12352         0x18, 0xf4, 0x08, 0x00,
12353         0xbc, 0x00, 0x38, 0x54, 0x00, 0xec, 0xd5, 0xf0, 0x82, 0x0d, 0x00, 0xe6,
12354         0x86, 0xf0, 0xb1, 0xf0,
12355         0x98, 0x57, 0x01, 0xfc, 0xb4, 0x00, 0xd4, 0x01, 0x0c, 0x1c, 0x3e, 0x1c,
12356         0x3c, 0x00, 0xbb, 0x00,
12357         0x00, 0x10, 0xba, 0x19, 0x02, 0x80, 0x32, 0xf0, 0x7c, 0x0d, 0x02, 0x13,
12358         0xba, 0x13, 0x18, 0x40,
12359         0x00, 0x57, 0x01, 0xea, 0x02, 0xfc, 0x03, 0xfc, 0x3e, 0x00, 0x6c, 0x01,
12360         0x6e, 0x01, 0x74, 0x01,
12361         0x76, 0x01, 0xb9, 0x54, 0x3e, 0x57, 0x00, 0x80, 0x03, 0xe6, 0xb6, 0x00,
12362         0xc0, 0x00, 0x01, 0x01,
12363         0x3e, 0x01, 0x7a, 0x01, 0xca, 0x08, 0xce, 0x10, 0x16, 0x11, 0x04, 0x12,
12364         0x08, 0x12, 0x02, 0x4a,
12365         0xbb, 0x55, 0x3c, 0x56, 0x03, 0x58, 0x1b, 0x80, 0x30, 0xe4, 0x4b, 0xe4,
12366         0x5d, 0xf0, 0x02, 0xfa,
12367         0x20, 0x00, 0x32, 0x00, 0x40, 0x00, 0x80, 0x00, 0x24, 0x01, 0x3c, 0x01,
12368         0x68, 0x01, 0x6a, 0x01,
12369         0x70, 0x01, 0x72, 0x01, 0x78, 0x01, 0x7c, 0x01, 0x62, 0x0a, 0x86, 0x0d,
12370         0x06, 0x13, 0x4c, 0x1c,
12371         0x04, 0x80, 0x4a, 0xe4, 0x02, 0xee, 0x5b, 0xf0, 0x03, 0xf7, 0x0c, 0x00,
12372         0x0f, 0x00, 0x47, 0x00,
12373         0xbe, 0x00, 0x00, 0x01, 0x20, 0x11, 0x5c, 0x16, 0x32, 0x1c, 0x38, 0x1c,
12374         0x4e, 0x1c, 0x10, 0x44,
12375         0x00, 0x4c, 0x04, 0xea, 0x5c, 0xf0, 0xa7, 0xf0, 0x04, 0xf6, 0x03, 0xfa,
12376         0x05, 0x00, 0x34, 0x00,
12377         0x36, 0x00, 0x98, 0x00, 0xcc, 0x00, 0x20, 0x01, 0x4e, 0x01, 0x4a, 0x0b,
12378         0x42, 0x0c, 0x12, 0x0f,
12379         0x0c, 0x10, 0x22, 0x11, 0x0a, 0x12, 0x04, 0x13, 0x30, 0x1c, 0x02, 0x48,
12380         0x00, 0x4e, 0x42, 0x54,
12381         0x44, 0x55, 0xbd, 0x56, 0x06, 0x83, 0x00, 0xdc, 0x05, 0xf0, 0x09, 0xf0,
12382         0x59, 0xf0, 0xb8, 0xf0,
12383         0x4b, 0xf4, 0x06, 0xf7, 0x0e, 0xf7, 0x04, 0xfc, 0x05, 0xfc, 0x06, 0x00,
12384         0x19, 0x00, 0x33, 0x00,
12385         0x9b, 0x00, 0xa4, 0x00, 0xb5, 0x00, 0xba, 0x00, 0xd0, 0x00, 0xe1, 0x00,
12386         0xe7, 0x00, 0xe2, 0x03,
12387         0x08, 0x0f, 0x02, 0x10, 0x04, 0x10, 0x0a, 0x10, 0x0a, 0x13, 0x0c, 0x13,
12388         0x12, 0x13, 0x24, 0x14,
12389         0x34, 0x14, 0x04, 0x16, 0x08, 0x16, 0xa4, 0x17, 0x20, 0x1c, 0x34, 0x1c,
12390         0x36, 0x1c, 0x08, 0x44,
12391         0x38, 0x44, 0x91, 0x44, 0x0a, 0x45, 0x48, 0x46, 0x01, 0x48, 0x68, 0x54,
12392         0x3a, 0x55, 0x83, 0x55,
12393         0xe5, 0x55, 0xb0, 0x57, 0x01, 0x58, 0x83, 0x59, 0x05, 0xe6, 0x0b, 0xf0,
12394         0x0c, 0xf0, 0x04, 0xf8,
12395         0x05, 0xf8, 0x07, 0x00, 0x0a, 0x00, 0x1c, 0x00, 0x1e, 0x00, 0x9e, 0x00,
12396         0xa8, 0x00, 0xaa, 0x00,
12397         0xb9, 0x00, 0xe0, 0x00, 0x22, 0x01, 0x26, 0x01, 0x79, 0x01, 0x7e, 0x01,
12398         0xc4, 0x01, 0xc6, 0x01,
12399         0x80, 0x02, 0x5e, 0x03, 0xee, 0x04, 0x9a, 0x06, 0xf8, 0x07, 0x62, 0x08,
12400         0x68, 0x08, 0x69, 0x08,
12401         0xd6, 0x08, 0xe9, 0x09, 0xfa, 0x0b, 0x2e, 0x0f, 0x12, 0x10, 0x1a, 0x10,
12402         0xed, 0x10, 0xf1, 0x10,
12403         0x2a, 0x11, 0x06, 0x12, 0x0c, 0x12, 0x3e, 0x12, 0x10, 0x13, 0x16, 0x13,
12404         0x1e, 0x13, 0x46, 0x14,
12405         0x76, 0x14, 0x82, 0x14, 0x36, 0x15, 0xca, 0x15, 0x6b, 0x18, 0xbe, 0x18,
12406         0xca, 0x18, 0xe6, 0x19,
12407         0x12, 0x1c, 0x46, 0x1c, 0x9c, 0x32, 0x00, 0x40, 0x0e, 0x47, 0xfe, 0x9c,
12408         0xf0, 0x2b, 0x02, 0xfe,
12409         0xac, 0x0d, 0xff, 0x10, 0x00, 0x00, 0xd7, 0xfe, 0xe8, 0x19, 0x00, 0xd6,
12410         0xfe, 0x84, 0x01, 0xff,
12411         0x03, 0x00, 0x00, 0xfe, 0x93, 0x15, 0xfe, 0x0f, 0x05, 0xff, 0x38, 0x00,
12412         0x00, 0xfe, 0x57, 0x24,
12413         0x00, 0xfe, 0x4c, 0x00, 0x5b, 0xff, 0x04, 0x00, 0x00, 0x11, 0xff, 0x09,
12414         0x00, 0x00, 0xff, 0x08,
12415         0x01, 0x01, 0xff, 0x08, 0xff, 0xff, 0xff, 0x27, 0x00, 0x00, 0xff, 0x10,
12416         0xff, 0xff, 0xff, 0x11,
12417         0x00, 0x00, 0xfe, 0x78, 0x56, 0xfe, 0x34, 0x12, 0xff, 0x21, 0x00, 0x00,
12418         0xfe, 0x04, 0xf7, 0xd6,
12419         0x2c, 0x99, 0x0a, 0x01, 0xfe, 0xc2, 0x0f, 0xfe, 0x04, 0xf7, 0xd6, 0x99,
12420         0x0a, 0x42, 0x2c, 0xfe,
12421         0x3d, 0xf0, 0xfe, 0x06, 0x02, 0xfe, 0x20, 0xf0, 0xa7, 0xfe, 0x91, 0xf0,
12422         0xfe, 0xf4, 0x01, 0xfe,
12423         0x90, 0xf0, 0xfe, 0xf4, 0x01, 0xfe, 0x8f, 0xf0, 0xa7, 0x03, 0x5d, 0x4d,
12424         0x02, 0xfe, 0xc8, 0x0d,
12425         0x01, 0xfe, 0x38, 0x0e, 0xfe, 0xdd, 0x12, 0xfe, 0xfc, 0x10, 0xfe, 0x28,
12426         0x1c, 0x03, 0xfe, 0xa6,
12427         0x00, 0xfe, 0xd3, 0x12, 0x41, 0x14, 0xfe, 0xa6, 0x00, 0xc2, 0xfe, 0x48,
12428         0xf0, 0xfe, 0x8a, 0x02,
12429         0xfe, 0x49, 0xf0, 0xfe, 0xa4, 0x02, 0xfe, 0x4a, 0xf0, 0xfe, 0xc2, 0x02,
12430         0xfe, 0x46, 0xf0, 0xfe,
12431         0x54, 0x02, 0xfe, 0x47, 0xf0, 0xfe, 0x5a, 0x02, 0xfe, 0x43, 0xf0, 0xfe,
12432         0x48, 0x02, 0xfe, 0x44,
12433         0xf0, 0xfe, 0x4c, 0x02, 0xfe, 0x45, 0xf0, 0xfe, 0x50, 0x02, 0x18, 0x0a,
12434         0xaa, 0x18, 0x06, 0x14,
12435         0xa1, 0x02, 0x2b, 0xfe, 0x00, 0x1c, 0xe7, 0xfe, 0x02, 0x1c, 0xe6, 0xfe,
12436         0x1e, 0x1c, 0xfe, 0xe9,
12437         0x10, 0x01, 0xfe, 0x18, 0x18, 0xfe, 0xe7, 0x10, 0xfe, 0x06, 0xfc, 0xce,
12438         0x09, 0x70, 0x01, 0xa8,
12439         0x02, 0x2b, 0x15, 0x59, 0x39, 0xa2, 0x01, 0xfe, 0x58, 0x10, 0x09, 0x70,
12440         0x01, 0x87, 0xfe, 0xbd,
12441         0x10, 0x09, 0x70, 0x01, 0x87, 0xfe, 0xad, 0x10, 0xfe, 0x16, 0x1c, 0xfe,
12442         0x58, 0x1c, 0x18, 0x06,
12443         0x14, 0xa1, 0x2c, 0x1c, 0x2b, 0xfe, 0x3d, 0xf0, 0xfe, 0x06, 0x02, 0x23,
12444         0xfe, 0x98, 0x02, 0xfe,
12445         0x5a, 0x1c, 0xf8, 0xfe, 0x14, 0x1c, 0x15, 0xfe, 0x30, 0x00, 0x39, 0xa2,
12446         0x01, 0xfe, 0x48, 0x10,
12447         0x18, 0x06, 0x14, 0xa1, 0x02, 0xd7, 0x22, 0x20, 0x07, 0x11, 0x35, 0xfe,
12448         0x69, 0x10, 0x18, 0x06,
12449         0x14, 0xa1, 0xfe, 0x04, 0xec, 0x20, 0x4f, 0x43, 0x13, 0x20, 0xfe, 0x05,
12450         0xf6, 0xce, 0x01, 0xfe,
12451         0x4a, 0x17, 0x08, 0x54, 0x58, 0x37, 0x12, 0x2f, 0x42, 0x92, 0x01, 0xfe,
12452         0x82, 0x16, 0x02, 0x2b,
12453         0x09, 0x46, 0x01, 0x0e, 0x07, 0x00, 0x66, 0x01, 0x73, 0xfe, 0x18, 0x10,
12454         0xfe, 0x41, 0x58, 0x09,
12455         0xa4, 0x01, 0x0e, 0xfe, 0xc8, 0x54, 0x6b, 0xfe, 0x10, 0x03, 0x01, 0xfe,
12456         0x82, 0x16, 0x02, 0x2b,
12457         0x2c, 0x4f, 0xfe, 0x02, 0xe8, 0x2a, 0xfe, 0xbf, 0x57, 0xfe, 0x9e, 0x43,
12458         0xfe, 0x77, 0x57, 0xfe,
12459         0x27, 0xf0, 0xfe, 0xe0, 0x01, 0xfe, 0x07, 0x4b, 0xfe, 0x20, 0xf0, 0xa7,
12460         0xfe, 0x40, 0x1c, 0x1c,
12461         0xd9, 0xfe, 0x26, 0xf0, 0xfe, 0x5a, 0x03, 0xfe, 0xa0, 0xf0, 0xfe, 0x48,
12462         0x03, 0xfe, 0x11, 0xf0,
12463         0xa7, 0xfe, 0xef, 0x10, 0xfe, 0x9f, 0xf0, 0xfe, 0x68, 0x03, 0xf9, 0x10,
12464         0xfe, 0x11, 0x00, 0x02,
12465         0x65, 0x2c, 0xfe, 0x48, 0x1c, 0xf9, 0x08, 0x05, 0x1b, 0xfe, 0x18, 0x13,
12466         0x21, 0x22, 0xa3, 0xb7,
12467         0x13, 0xa3, 0x09, 0x46, 0x01, 0x0e, 0xb7, 0x78, 0x01, 0xfe, 0xb4, 0x16,
12468         0x12, 0xd1, 0x1c, 0xd9,
12469         0xfe, 0x01, 0xf0, 0xd9, 0xfe, 0x82, 0xf0, 0xfe, 0x96, 0x03, 0xfa, 0x12,
12470         0xfe, 0xe4, 0x00, 0x27,
12471         0xfe, 0xa8, 0x03, 0x1c, 0x34, 0x1d, 0xfe, 0xb8, 0x03, 0x01, 0x4b, 0xfe,
12472         0x06, 0xf0, 0xfe, 0xc8,
12473         0x03, 0x95, 0x86, 0xfe, 0x0a, 0xf0, 0xfe, 0x8a, 0x06, 0x02, 0x24, 0x03,
12474         0x70, 0x28, 0x17, 0xfe,
12475         0xfa, 0x04, 0x15, 0x6d, 0x01, 0x36, 0x7b, 0xfe, 0x6a, 0x02, 0x02, 0xd8,
12476         0xf9, 0x2c, 0x99, 0x19,
12477         0xfe, 0x67, 0x1b, 0xfe, 0xbf, 0x57, 0xfe, 0x77, 0x57, 0xfe, 0x48, 0x1c,
12478         0x74, 0x01, 0xaf, 0x8c,
12479         0x09, 0x46, 0x01, 0x0e, 0x07, 0x00, 0x17, 0xda, 0x09, 0xd1, 0x01, 0x0e,
12480         0x8d, 0x51, 0x64, 0x79,
12481         0x2a, 0x03, 0x70, 0x28, 0xfe, 0x10, 0x12, 0x15, 0x6d, 0x01, 0x36, 0x7b,
12482         0xfe, 0x6a, 0x02, 0x02,
12483         0xd8, 0xc7, 0x81, 0xc8, 0x83, 0x1c, 0x24, 0x27, 0xfe, 0x40, 0x04, 0x1d,
12484         0xfe, 0x3c, 0x04, 0x3b,
12485         0xfe, 0xa0, 0x00, 0xfe, 0x9b, 0x57, 0xfe, 0x4e, 0x12, 0x2d, 0xff, 0x02,
12486         0x00, 0x10, 0x01, 0x0b,
12487         0x1d, 0xfe, 0xe4, 0x04, 0x2d, 0x01, 0x0b, 0x1d, 0x24, 0x33, 0x31, 0xde,
12488         0xfe, 0x4c, 0x44, 0xfe,
12489         0x4c, 0x12, 0x51, 0xfe, 0x44, 0x48, 0x0f, 0x6f, 0xfe, 0x4c, 0x54, 0x6b,
12490         0xda, 0x4f, 0x79, 0x2a,
12491         0xfe, 0x06, 0x80, 0xfe, 0x48, 0x47, 0xfe, 0x62, 0x13, 0x08, 0x05, 0x1b,
12492         0xfe, 0x2a, 0x13, 0x32,
12493         0x07, 0x82, 0xfe, 0x52, 0x13, 0xfe, 0x20, 0x10, 0x0f, 0x6f, 0xfe, 0x4c,
12494         0x54, 0x6b, 0xda, 0xfe,
12495         0x06, 0x80, 0xfe, 0x48, 0x47, 0xfe, 0x40, 0x13, 0x08, 0x05, 0x1b, 0xfe,
12496         0x08, 0x13, 0x32, 0x07,
12497         0x82, 0xfe, 0x30, 0x13, 0x08, 0x05, 0x1b, 0xfe, 0x1c, 0x12, 0x15, 0x9d,
12498         0x08, 0x05, 0x06, 0x4d,
12499         0x15, 0xfe, 0x0d, 0x00, 0x01, 0x36, 0x7b, 0xfe, 0x64, 0x0d, 0x02, 0x24,
12500         0x2d, 0x12, 0xfe, 0xe6,
12501         0x00, 0xfe, 0x1c, 0x90, 0xfe, 0x40, 0x5c, 0x04, 0x15, 0x9d, 0x01, 0x36,
12502         0x02, 0x2b, 0xfe, 0x42,
12503         0x5b, 0x99, 0x19, 0xfe, 0x46, 0x59, 0xfe, 0xbf, 0x57, 0xfe, 0x77, 0x57,
12504         0xfe, 0x87, 0x80, 0xfe,
12505         0x31, 0xe4, 0x5b, 0x08, 0x05, 0x0a, 0xfe, 0x84, 0x13, 0xfe, 0x20, 0x80,
12506         0x07, 0x19, 0xfe, 0x7c,
12507         0x12, 0x53, 0x05, 0x06, 0xfe, 0x6c, 0x13, 0x03, 0xfe, 0xa2, 0x00, 0x28,
12508         0x17, 0xfe, 0x90, 0x05,
12509         0xfe, 0x31, 0xe4, 0x5a, 0x53, 0x05, 0x0a, 0xfe, 0x56, 0x13, 0x03, 0xfe,
12510         0xa0, 0x00, 0x28, 0xfe,
12511         0x4e, 0x12, 0x67, 0xff, 0x02, 0x00, 0x10, 0x27, 0xfe, 0x48, 0x05, 0x1c,
12512         0x34, 0xfe, 0x89, 0x48,
12513         0xff, 0x02, 0x00, 0x10, 0x27, 0xfe, 0x56, 0x05, 0x26, 0xfe, 0xa8, 0x05,
12514         0x12, 0xfe, 0xe3, 0x00,
12515         0x21, 0x53, 0xfe, 0x4a, 0xf0, 0xfe, 0x76, 0x05, 0xfe, 0x49, 0xf0, 0xfe,
12516         0x70, 0x05, 0x88, 0x25,
12517         0xfe, 0x21, 0x00, 0xab, 0x25, 0xfe, 0x22, 0x00, 0xaa, 0x25, 0x58, 0xfe,
12518         0x09, 0x48, 0xff, 0x02,
12519         0x00, 0x10, 0x27, 0xfe, 0x86, 0x05, 0x26, 0xfe, 0xa8, 0x05, 0xfe, 0xe2,
12520         0x08, 0x53, 0x05, 0xcb,
12521         0x4d, 0x01, 0xb0, 0x25, 0x06, 0x13, 0xd3, 0x39, 0xfe, 0x27, 0x01, 0x08,
12522         0x05, 0x1b, 0xfe, 0x22,
12523         0x12, 0x41, 0x01, 0xb2, 0x15, 0x9d, 0x08, 0x05, 0x06, 0x4d, 0x15, 0xfe,
12524         0x0d, 0x00, 0x01, 0x36,
12525         0x7b, 0xfe, 0x64, 0x0d, 0x02, 0x24, 0x03, 0xfe, 0x9c, 0x00, 0x28, 0xeb,
12526         0x03, 0x5c, 0x28, 0xfe,
12527         0x36, 0x13, 0x41, 0x01, 0xb2, 0x26, 0xfe, 0x18, 0x06, 0x09, 0x06, 0x53,
12528         0x05, 0x1f, 0xfe, 0x02,
12529         0x12, 0x50, 0x01, 0xfe, 0x9e, 0x15, 0x1d, 0xfe, 0x0e, 0x06, 0x12, 0xa5,
12530         0x01, 0x4b, 0x12, 0xfe,
12531         0xe5, 0x00, 0x03, 0x5c, 0xc1, 0x0c, 0x5c, 0x03, 0xcd, 0x28, 0xfe, 0x62,
12532         0x12, 0x03, 0x45, 0x28,
12533         0xfe, 0x5a, 0x13, 0x01, 0xfe, 0x0c, 0x19, 0x01, 0xfe, 0x76, 0x19, 0xfe,
12534         0x43, 0x48, 0xc4, 0xcc,
12535         0x0f, 0x71, 0xff, 0x02, 0x00, 0x57, 0x52, 0x93, 0x1e, 0x43, 0x8b, 0xc4,
12536         0x6e, 0x41, 0x01, 0xb2,
12537         0x26, 0xfe, 0x82, 0x06, 0x53, 0x05, 0x1a, 0xe9, 0x91, 0x09, 0x59, 0x01,
12538         0xfe, 0xcc, 0x15, 0x1d,
12539         0xfe, 0x78, 0x06, 0x12, 0xa5, 0x01, 0x4b, 0x12, 0xfe, 0xe5, 0x00, 0x03,
12540         0x45, 0xc1, 0x0c, 0x45,
12541         0x18, 0x06, 0x01, 0xb2, 0xfa, 0x76, 0x74, 0x01, 0xaf, 0x8c, 0x12, 0xfe,
12542         0xe2, 0x00, 0x27, 0xdb,
12543         0x1c, 0x34, 0xfe, 0x0a, 0xf0, 0xfe, 0xb6, 0x06, 0x94, 0xfe, 0x6c, 0x07,
12544         0xfe, 0x06, 0xf0, 0xfe,
12545         0x74, 0x07, 0x95, 0x86, 0x02, 0x24, 0x08, 0x05, 0x0a, 0xfe, 0x2e, 0x12,
12546         0x16, 0x19, 0x01, 0x0b,
12547         0x16, 0x00, 0x01, 0x0b, 0x16, 0x00, 0x01, 0x0b, 0x16, 0x00, 0x01, 0x0b,
12548         0xfe, 0x99, 0xa4, 0x01,
12549         0x0b, 0x16, 0x00, 0x02, 0xfe, 0x42, 0x08, 0x68, 0x05, 0x1a, 0xfe, 0x38,
12550         0x12, 0x08, 0x05, 0x1a,
12551         0xfe, 0x30, 0x13, 0x16, 0xfe, 0x1b, 0x00, 0x01, 0x0b, 0x16, 0x00, 0x01,
12552         0x0b, 0x16, 0x00, 0x01,
12553         0x0b, 0x16, 0x00, 0x01, 0x0b, 0x16, 0x06, 0x01, 0x0b, 0x16, 0x00, 0x02,
12554         0xe2, 0x6c, 0x58, 0xbe,
12555         0x50, 0xfe, 0x9a, 0x81, 0x55, 0x1b, 0x7a, 0xfe, 0x42, 0x07, 0x09, 0x1b,
12556         0xfe, 0x09, 0x6f, 0xba,
12557         0xfe, 0xca, 0x45, 0xfe, 0x32, 0x12, 0x69, 0x6d, 0x8b, 0x6c, 0x7f, 0x27,
12558         0xfe, 0x54, 0x07, 0x1c,
12559         0x34, 0xfe, 0x0a, 0xf0, 0xfe, 0x42, 0x07, 0x95, 0x86, 0x94, 0xfe, 0x6c,
12560         0x07, 0x02, 0x24, 0x01,
12561         0x4b, 0x02, 0xdb, 0x16, 0x1f, 0x02, 0xdb, 0xfe, 0x9c, 0xf7, 0xdc, 0xfe,
12562         0x2c, 0x90, 0xfe, 0xae,
12563         0x90, 0x56, 0xfe, 0xda, 0x07, 0x0c, 0x60, 0x14, 0x61, 0x08, 0x54, 0x5a,
12564         0x37, 0x22, 0x20, 0x07,
12565         0x11, 0xfe, 0x0e, 0x12, 0x8d, 0xfe, 0x80, 0x80, 0x39, 0x20, 0x6a, 0x2a,
12566         0xfe, 0x06, 0x10, 0xfe,
12567         0x83, 0xe7, 0xfe, 0x48, 0x00, 0xab, 0xfe, 0x03, 0x40, 0x08, 0x54, 0x5b,
12568         0x37, 0x01, 0xb3, 0xb8,
12569         0xfe, 0x1f, 0x40, 0x13, 0x62, 0x01, 0xef, 0xfe, 0x08, 0x50, 0xfe, 0x8a,
12570         0x50, 0xfe, 0x44, 0x51,
12571         0xfe, 0xc6, 0x51, 0x88, 0xfe, 0x08, 0x90, 0xfe, 0x8a, 0x90, 0x0c, 0x5e,
12572         0x14, 0x5f, 0xfe, 0x0c,
12573         0x90, 0xfe, 0x8e, 0x90, 0xfe, 0x40, 0x50, 0xfe, 0xc2, 0x50, 0x0c, 0x3d,
12574         0x14, 0x3e, 0xfe, 0x4a,
12575         0x10, 0x08, 0x05, 0x5a, 0xfe, 0x2a, 0x12, 0xfe, 0x2c, 0x90, 0xfe, 0xae,
12576         0x90, 0x0c, 0x60, 0x14,
12577         0x61, 0x08, 0x05, 0x5b, 0x8b, 0x01, 0xb3, 0xfe, 0x1f, 0x80, 0x13, 0x62,
12578         0xfe, 0x44, 0x90, 0xfe,
12579         0xc6, 0x90, 0x0c, 0x3f, 0x14, 0x40, 0xfe, 0x08, 0x90, 0xfe, 0x8a, 0x90,
12580         0x0c, 0x5e, 0x14, 0x5f,
12581         0xfe, 0x40, 0x90, 0xfe, 0xc2, 0x90, 0x0c, 0x3d, 0x14, 0x3e, 0x0c, 0x2e,
12582         0x14, 0x3c, 0x21, 0x0c,
12583         0x49, 0x0c, 0x63, 0x08, 0x54, 0x1f, 0x37, 0x2c, 0x0f, 0xfe, 0x4e, 0x11,
12584         0x27, 0xdd, 0xfe, 0x9e,
12585         0xf0, 0xfe, 0x76, 0x08, 0xbc, 0x17, 0x34, 0x2c, 0x77, 0xe6, 0xc5, 0xfe,
12586         0x9a, 0x08, 0xc6, 0xfe,
12587         0xb8, 0x08, 0x94, 0xfe, 0x8e, 0x08, 0xfe, 0x06, 0xf0, 0xfe, 0x94, 0x08,
12588         0x95, 0x86, 0x02, 0x24,
12589         0x01, 0x4b, 0xfe, 0xc9, 0x10, 0x16, 0x1f, 0xfe, 0xc9, 0x10, 0x68, 0x05,
12590         0x06, 0xfe, 0x10, 0x12,
12591         0x68, 0x05, 0x0a, 0x4e, 0x08, 0x05, 0x0a, 0xfe, 0x90, 0x12, 0xfe, 0x2e,
12592         0x1c, 0x02, 0xfe, 0x18,
12593         0x0b, 0x68, 0x05, 0x06, 0x4e, 0x68, 0x05, 0x0a, 0xfe, 0x7a, 0x12, 0xfe,
12594         0x2c, 0x1c, 0xfe, 0xaa,
12595         0xf0, 0xfe, 0xd2, 0x09, 0xfe, 0xac, 0xf0, 0xfe, 0x00, 0x09, 0x02, 0xfe,
12596         0xde, 0x09, 0xfe, 0xb7,
12597         0xf0, 0xfe, 0xfc, 0x08, 0xfe, 0x02, 0xf6, 0x1a, 0x50, 0xfe, 0x70, 0x18,
12598         0xfe, 0xf1, 0x18, 0xfe,
12599         0x40, 0x55, 0xfe, 0xe1, 0x55, 0xfe, 0x10, 0x58, 0xfe, 0x91, 0x58, 0xfe,
12600         0x14, 0x59, 0xfe, 0x95,
12601         0x59, 0x1c, 0x85, 0xfe, 0x8c, 0xf0, 0xfe, 0xfc, 0x08, 0xfe, 0xac, 0xf0,
12602         0xfe, 0xf0, 0x08, 0xb5,
12603         0xfe, 0xcb, 0x10, 0xfe, 0xad, 0xf0, 0xfe, 0x0c, 0x09, 0x02, 0xfe, 0x18,
12604         0x0b, 0xb6, 0xfe, 0xbf,
12605         0x10, 0xfe, 0x2b, 0xf0, 0x85, 0xf4, 0x1e, 0xfe, 0x00, 0xfe, 0xfe, 0x1c,
12606         0x12, 0xc2, 0xfe, 0xd2,
12607         0xf0, 0x85, 0xfe, 0x76, 0x18, 0x1e, 0x19, 0x17, 0x85, 0x03, 0xd2, 0x1e,
12608         0x06, 0x17, 0x85, 0xc5,
12609         0x4a, 0xc6, 0x4a, 0xb5, 0xb6, 0xfe, 0x89, 0x10, 0x74, 0x67, 0x2d, 0x15,
12610         0x9d, 0x01, 0x36, 0x10,
12611         0xfe, 0x35, 0x00, 0xfe, 0x01, 0xf0, 0x65, 0x10, 0x80, 0x02, 0x65, 0xfe,
12612         0x98, 0x80, 0xfe, 0x19,
12613         0xe4, 0x0a, 0xfe, 0x1a, 0x12, 0x51, 0xfe, 0x19, 0x82, 0xfe, 0x6c, 0x18,
12614         0xfe, 0x44, 0x54, 0xbe,
12615         0xfe, 0x19, 0x81, 0xfe, 0x74, 0x18, 0x8f, 0x90, 0x17, 0xfe, 0xce, 0x08,
12616         0x02, 0x4a, 0x08, 0x05,
12617         0x5a, 0xec, 0x03, 0x2e, 0x29, 0x3c, 0x0c, 0x3f, 0x14, 0x40, 0x9b, 0x2e,
12618         0x9c, 0x3c, 0xfe, 0x6c,
12619         0x18, 0xfe, 0xed, 0x18, 0xfe, 0x44, 0x54, 0xfe, 0xe5, 0x54, 0x3a, 0x3f,
12620         0x3b, 0x40, 0x03, 0x49,
12621         0x29, 0x63, 0x8f, 0xfe, 0xe3, 0x54, 0xfe, 0x74, 0x18, 0xfe, 0xf5, 0x18,
12622         0x8f, 0xfe, 0xe3, 0x54,
12623         0x90, 0xc0, 0x56, 0xfe, 0xce, 0x08, 0x02, 0x4a, 0xfe, 0x37, 0xf0, 0xfe,
12624         0xda, 0x09, 0xfe, 0x8b,
12625         0xf0, 0xfe, 0x60, 0x09, 0x02, 0x4a, 0x08, 0x05, 0x0a, 0x23, 0xfe, 0xfa,
12626         0x0a, 0x3a, 0x49, 0x3b,
12627         0x63, 0x56, 0xfe, 0x3e, 0x0a, 0x0f, 0xfe, 0xc0, 0x07, 0x41, 0x98, 0x00,
12628         0xad, 0xfe, 0x01, 0x59,
12629         0xfe, 0x52, 0xf0, 0xfe, 0x0c, 0x0a, 0x8f, 0x7a, 0xfe, 0x24, 0x0a, 0x3a,
12630         0x49, 0x8f, 0xfe, 0xe3,
12631         0x54, 0x57, 0x49, 0x7d, 0x63, 0xfe, 0x14, 0x58, 0xfe, 0x95, 0x58, 0x02,
12632         0x4a, 0x3a, 0x49, 0x3b,
12633         0x63, 0xfe, 0x14, 0x59, 0xfe, 0x95, 0x59, 0xbe, 0x57, 0x49, 0x57, 0x63,
12634         0x02, 0x4a, 0x08, 0x05,
12635         0x5a, 0xfe, 0x82, 0x12, 0x08, 0x05, 0x1f, 0xfe, 0x66, 0x13, 0x22, 0x62,
12636         0xb7, 0xfe, 0x03, 0xa1,
12637         0xfe, 0x83, 0x80, 0xfe, 0xc8, 0x44, 0xfe, 0x2e, 0x13, 0xfe, 0x04, 0x91,
12638         0xfe, 0x86, 0x91, 0x6a,
12639         0x2a, 0xfe, 0x40, 0x59, 0xfe, 0xc1, 0x59, 0x56, 0xe0, 0x03, 0x60, 0x29,
12640         0x61, 0x0c, 0x7f, 0x14,
12641         0x80, 0x57, 0x60, 0x7d, 0x61, 0x01, 0xb3, 0xb8, 0x6a, 0x2a, 0x13, 0x62,
12642         0x9b, 0x2e, 0x9c, 0x3c,
12643         0x3a, 0x3f, 0x3b, 0x40, 0x90, 0xc0, 0xfe, 0x04, 0xfa, 0x2e, 0xfe, 0x05,
12644         0xfa, 0x3c, 0x01, 0xef,
12645         0xfe, 0x36, 0x10, 0x21, 0x0c, 0x7f, 0x0c, 0x80, 0x3a, 0x3f, 0x3b, 0x40,
12646         0xe4, 0x08, 0x05, 0x1f,
12647         0x17, 0xe0, 0x3a, 0x3d, 0x3b, 0x3e, 0x08, 0x05, 0xfe, 0xf7, 0x00, 0x37,
12648         0x03, 0x5e, 0x29, 0x5f,
12649         0xfe, 0x10, 0x58, 0xfe, 0x91, 0x58, 0x57, 0x49, 0x7d, 0x63, 0x02, 0xfe,
12650         0xf4, 0x09, 0x08, 0x05,
12651         0x1f, 0x17, 0xe0, 0x08, 0x05, 0xfe, 0xf7, 0x00, 0x37, 0xbe, 0xfe, 0x19,
12652         0x81, 0x50, 0xfe, 0x10,
12653         0x90, 0xfe, 0x92, 0x90, 0xfe, 0xd3, 0x10, 0x32, 0x07, 0xa6, 0x17, 0xfe,
12654         0x08, 0x09, 0x12, 0xa6,
12655         0x08, 0x05, 0x0a, 0xfe, 0x14, 0x13, 0x03, 0x3d, 0x29, 0x3e, 0x56, 0xfe,
12656         0x08, 0x09, 0xfe, 0x0c,
12657         0x58, 0xfe, 0x8d, 0x58, 0x02, 0x4a, 0x21, 0x41, 0xfe, 0x19, 0x80, 0xe7,
12658         0x08, 0x05, 0x0a, 0xfe,
12659         0x1a, 0x12, 0xfe, 0x6c, 0x19, 0xfe, 0x19, 0x41, 0xf4, 0xc2, 0xfe, 0xd1,
12660         0xf0, 0xe2, 0x15, 0x7e,
12661         0x01, 0x36, 0x10, 0xfe, 0x44, 0x00, 0xfe, 0x8e, 0x10, 0xfe, 0x6c, 0x19,
12662         0x57, 0x3d, 0xfe, 0xed,
12663         0x19, 0x7d, 0x3e, 0xfe, 0x0c, 0x51, 0xfe, 0x8e, 0x51, 0xf4, 0x1e, 0xfe,
12664         0x00, 0xff, 0x35, 0xfe,
12665         0x74, 0x10, 0xc2, 0xfe, 0xd2, 0xf0, 0xfe, 0xa6, 0x0b, 0xfe, 0x76, 0x18,
12666         0x1e, 0x19, 0x8a, 0x03,
12667         0xd2, 0x1e, 0x06, 0xfe, 0x08, 0x13, 0x10, 0xfe, 0x16, 0x00, 0x02, 0x65,
12668         0xfe, 0xd1, 0xf0, 0xfe,
12669         0xb8, 0x0b, 0x15, 0x7e, 0x01, 0x36, 0x10, 0xfe, 0x17, 0x00, 0xfe, 0x42,
12670         0x10, 0xfe, 0xce, 0xf0,
12671         0xfe, 0xbe, 0x0b, 0xfe, 0x3c, 0x10, 0xfe, 0xcd, 0xf0, 0xfe, 0xca, 0x0b,
12672         0x10, 0xfe, 0x22, 0x00,
12673         0x02, 0x65, 0xfe, 0xcb, 0xf0, 0xfe, 0xd6, 0x0b, 0x10, 0xfe, 0x24, 0x00,
12674         0x02, 0x65, 0xfe, 0xd0,
12675         0xf0, 0xfe, 0xe0, 0x0b, 0x10, 0x9e, 0xe5, 0xfe, 0xcf, 0xf0, 0xfe, 0xea,
12676         0x0b, 0x10, 0x58, 0xfe,
12677         0x10, 0x10, 0xfe, 0xcc, 0xf0, 0xe2, 0x68, 0x05, 0x1f, 0x4d, 0x10, 0xfe,
12678         0x12, 0x00, 0x2c, 0x0f,
12679         0xfe, 0x4e, 0x11, 0x27, 0xfe, 0x00, 0x0c, 0xfe, 0x9e, 0xf0, 0xfe, 0x14,
12680         0x0c, 0xbc, 0x17, 0x34,
12681         0x2c, 0x77, 0xe6, 0xc5, 0x24, 0xc6, 0x24, 0x2c, 0xfa, 0x27, 0xfe, 0x20,
12682         0x0c, 0x1c, 0x34, 0x94,
12683         0xfe, 0x3c, 0x0c, 0x95, 0x86, 0xc5, 0xdc, 0xc6, 0xdc, 0x02, 0x24, 0x01,
12684         0x4b, 0xfe, 0xdb, 0x10,
12685         0x12, 0xfe, 0xe8, 0x00, 0xb5, 0xb6, 0x74, 0xc7, 0x81, 0xc8, 0x83, 0xfe,
12686         0x89, 0xf0, 0x24, 0x33,
12687         0x31, 0xe1, 0xc7, 0x81, 0xc8, 0x83, 0x27, 0xfe, 0x66, 0x0c, 0x1d, 0x24,
12688         0x33, 0x31, 0xdf, 0xbc,
12689         0x4e, 0x10, 0xfe, 0x42, 0x00, 0x02, 0x65, 0x7c, 0x06, 0xfe, 0x81, 0x49,
12690         0x17, 0xfe, 0x2c, 0x0d,
12691         0x08, 0x05, 0x0a, 0xfe, 0x44, 0x13, 0x10, 0x00, 0x55, 0x0a, 0xfe, 0x54,
12692         0x12, 0x55, 0xfe, 0x28,
12693         0x00, 0x23, 0xfe, 0x9a, 0x0d, 0x09, 0x46, 0x01, 0x0e, 0x07, 0x00, 0x66,
12694         0x44, 0xfe, 0x28, 0x00,
12695         0xfe, 0xe2, 0x10, 0x01, 0xf5, 0x01, 0xf6, 0x09, 0xa4, 0x01, 0xfe, 0x26,
12696         0x0f, 0x64, 0x12, 0x2f,
12697         0x01, 0x73, 0x02, 0x2b, 0x10, 0xfe, 0x44, 0x00, 0x55, 0x0a, 0xe9, 0x44,
12698         0x0a, 0xfe, 0xb4, 0x10,
12699         0x01, 0xb0, 0x44, 0x0a, 0xfe, 0xaa, 0x10, 0x01, 0xb0, 0xfe, 0x19, 0x82,
12700         0xfe, 0x34, 0x46, 0xac,
12701         0x44, 0x0a, 0x10, 0xfe, 0x43, 0x00, 0xfe, 0x96, 0x10, 0x08, 0x54, 0x0a,
12702         0x37, 0x01, 0xf5, 0x01,
12703         0xf6, 0x64, 0x12, 0x2f, 0x01, 0x73, 0x99, 0x0a, 0x64, 0x42, 0x92, 0x02,
12704         0xfe, 0x2e, 0x03, 0x08,
12705         0x05, 0x0a, 0x8a, 0x44, 0x0a, 0x10, 0x00, 0xfe, 0x5c, 0x10, 0x68, 0x05,
12706         0x1a, 0xfe, 0x58, 0x12,
12707         0x08, 0x05, 0x1a, 0xfe, 0x50, 0x13, 0xfe, 0x1c, 0x1c, 0xfe, 0x9d, 0xf0,
12708         0xfe, 0x50, 0x0d, 0xfe,
12709         0x1c, 0x1c, 0xfe, 0x9d, 0xf0, 0xfe, 0x56, 0x0d, 0x08, 0x54, 0x1a, 0x37,
12710         0xfe, 0xa9, 0x10, 0x10,
12711         0xfe, 0x15, 0x00, 0xfe, 0x04, 0xe6, 0x0a, 0x50, 0xfe, 0x2e, 0x10, 0x10,
12712         0xfe, 0x13, 0x00, 0xfe,
12713         0x10, 0x10, 0x10, 0x6f, 0xab, 0x10, 0xfe, 0x41, 0x00, 0xaa, 0x10, 0xfe,
12714         0x24, 0x00, 0x8c, 0xb5,
12715         0xb6, 0x74, 0x03, 0x70, 0x28, 0x23, 0xd8, 0x50, 0xfe, 0x04, 0xe6, 0x1a,
12716         0xfe, 0x9d, 0x41, 0xfe,
12717         0x1c, 0x42, 0x64, 0x01, 0xe3, 0x02, 0x2b, 0xf8, 0x15, 0x0a, 0x39, 0xa0,
12718         0xb4, 0x15, 0xfe, 0x31,
12719         0x00, 0x39, 0xa2, 0x01, 0xfe, 0x48, 0x10, 0x02, 0xd7, 0x42, 0xfe, 0x06,
12720         0xec, 0xd0, 0xfc, 0x44,
12721         0x1b, 0xfe, 0xce, 0x45, 0x35, 0x42, 0xfe, 0x06, 0xea, 0xd0, 0xfe, 0x47,
12722         0x4b, 0x91, 0xfe, 0x75,
12723         0x57, 0x03, 0x5d, 0xfe, 0x98, 0x56, 0xfe, 0x38, 0x12, 0x09, 0x48, 0x01,
12724         0x0e, 0xfe, 0x44, 0x48,
12725         0x4f, 0x08, 0x05, 0x1b, 0xfe, 0x1a, 0x13, 0x09, 0x46, 0x01, 0x0e, 0x41,
12726         0xfe, 0x41, 0x58, 0x09,
12727         0xa4, 0x01, 0x0e, 0xfe, 0x49, 0x54, 0x96, 0xfe, 0x1e, 0x0e, 0x02, 0xfe,
12728         0x2e, 0x03, 0x09, 0x5d,
12729         0xfe, 0xee, 0x14, 0xfc, 0x44, 0x1b, 0xfe, 0xce, 0x45, 0x35, 0x42, 0xfe,
12730         0xce, 0x47, 0xfe, 0xad,
12731         0x13, 0x02, 0x2b, 0x22, 0x20, 0x07, 0x11, 0xfe, 0x9e, 0x12, 0x21, 0x13,
12732         0x59, 0x13, 0x9f, 0x13,
12733         0xd5, 0x22, 0x2f, 0x41, 0x39, 0x2f, 0xbc, 0xad, 0xfe, 0xbc, 0xf0, 0xfe,
12734         0xe0, 0x0e, 0x0f, 0x06,
12735         0x13, 0x59, 0x01, 0xfe, 0xda, 0x16, 0x03, 0xfe, 0x38, 0x01, 0x29, 0xfe,
12736         0x3a, 0x01, 0x56, 0xfe,
12737         0xe4, 0x0e, 0xfe, 0x02, 0xec, 0xd5, 0x69, 0x00, 0x66, 0xfe, 0x04, 0xec,
12738         0x20, 0x4f, 0xfe, 0x05,
12739         0xf6, 0xfe, 0x34, 0x01, 0x01, 0xfe, 0x4a, 0x17, 0xfe, 0x08, 0x90, 0xfe,
12740         0x48, 0xf4, 0x0d, 0xfe,
12741         0x18, 0x13, 0xba, 0xfe, 0x02, 0xea, 0xd5, 0x69, 0x7e, 0xfe, 0xc5, 0x13,
12742         0x15, 0x1a, 0x39, 0xa0,
12743         0xb4, 0xfe, 0x2e, 0x10, 0x03, 0xfe, 0x38, 0x01, 0x1e, 0xfe, 0xf0, 0xff,
12744         0x0c, 0xfe, 0x60, 0x01,
12745         0x03, 0xfe, 0x3a, 0x01, 0x0c, 0xfe, 0x62, 0x01, 0x43, 0x13, 0x20, 0x25,
12746         0x06, 0x13, 0x2f, 0x12,
12747         0x2f, 0x92, 0x0f, 0x06, 0x04, 0x21, 0x04, 0x22, 0x59, 0xfe, 0xf7, 0x12,
12748         0x22, 0x9f, 0xb7, 0x13,
12749         0x9f, 0x07, 0x7e, 0xfe, 0x71, 0x13, 0xfe, 0x24, 0x1c, 0x15, 0x19, 0x39,
12750         0xa0, 0xb4, 0xfe, 0xd9,
12751         0x10, 0xc3, 0xfe, 0x03, 0xdc, 0xfe, 0x73, 0x57, 0xfe, 0x80, 0x5d, 0x04,
12752         0xc3, 0xfe, 0x03, 0xdc,
12753         0xfe, 0x5b, 0x57, 0xfe, 0x80, 0x5d, 0x04, 0xfe, 0x03, 0x57, 0xc3, 0x21,
12754         0xfe, 0x00, 0xcc, 0x04,
12755         0xfe, 0x03, 0x57, 0xc3, 0x78, 0x04, 0x08, 0x05, 0x58, 0xfe, 0x22, 0x13,
12756         0xfe, 0x1c, 0x80, 0x07,
12757         0x06, 0xfe, 0x1a, 0x13, 0xfe, 0x1e, 0x80, 0xed, 0xfe, 0x1d, 0x80, 0xae,
12758         0xfe, 0x0c, 0x90, 0xfe,
12759         0x0e, 0x13, 0xfe, 0x0e, 0x90, 0xac, 0xfe, 0x3c, 0x90, 0xfe, 0x30, 0xf4,
12760         0x0a, 0xfe, 0x3c, 0x50,
12761         0xaa, 0x01, 0xfe, 0x7a, 0x17, 0x32, 0x07, 0x2f, 0xad, 0x01, 0xfe, 0xb4,
12762         0x16, 0x08, 0x05, 0x1b,
12763         0x4e, 0x01, 0xf5, 0x01, 0xf6, 0x12, 0xfe, 0xe9, 0x00, 0x08, 0x05, 0x58,
12764         0xfe, 0x2c, 0x13, 0x01,
12765         0xfe, 0x0c, 0x17, 0xfe, 0x1e, 0x1c, 0xfe, 0x14, 0x90, 0xfe, 0x96, 0x90,
12766         0x0c, 0xfe, 0x64, 0x01,
12767         0x14, 0xfe, 0x66, 0x01, 0x08, 0x05, 0x5b, 0xfe, 0x12, 0x12, 0xfe, 0x03,
12768         0x80, 0x8d, 0xfe, 0x01,
12769         0xec, 0x20, 0xfe, 0x80, 0x40, 0x13, 0x20, 0x6a, 0x2a, 0x12, 0xcf, 0x64,
12770         0x22, 0x20, 0xfb, 0x79,
12771         0x20, 0x04, 0xfe, 0x08, 0x1c, 0x03, 0xfe, 0xac, 0x00, 0xfe, 0x06, 0x58,
12772         0x03, 0xfe, 0xae, 0x00,
12773
12774         0xfe, 0x07, 0x58, 0x03, 0xfe, 0xb0, 0x00, 0xfe, 0x08, 0x58, 0x03, 0xfe,
12775         0xb2, 0x00, 0xfe, 0x09,
12776         0x58, 0xfe, 0x0a, 0x1c, 0x25, 0x6e, 0x13, 0xd0, 0x21, 0x0c, 0x5c, 0x0c,
12777         0x45, 0x0f, 0x46, 0x52,
12778         0x50, 0x18, 0x1b, 0xfe, 0x90, 0x4d, 0xfe, 0x91, 0x54, 0x23, 0xfe, 0xfc,
12779         0x0f, 0x44, 0x11, 0x0f,
12780         0x48, 0x52, 0x18, 0x58, 0xfe, 0x90, 0x4d, 0xfe, 0x91, 0x54, 0x23, 0xe4,
12781         0x25, 0x11, 0x13, 0x20,
12782         0x7c, 0x6f, 0x4f, 0x22, 0x20, 0xfb, 0x79, 0x20, 0x12, 0xcf, 0xfe, 0x14,
12783         0x56, 0xfe, 0xd6, 0xf0,
12784         0xfe, 0x26, 0x10, 0xf8, 0x74, 0xfe, 0x14, 0x1c, 0xfe, 0x10, 0x1c, 0xfe,
12785         0x18, 0x1c, 0x04, 0x42,
12786         0xfe, 0x0c, 0x14, 0xfc, 0xfe, 0x07, 0xe6, 0x1b, 0xfe, 0xce, 0x47, 0xfe,
12787         0xf5, 0x13, 0x04, 0x01,
12788         0xb0, 0x7c, 0x6f, 0x4f, 0xfe, 0x06, 0x80, 0xfe, 0x48, 0x47, 0xfe, 0x42,
12789         0x13, 0x32, 0x07, 0x2f,
12790         0xfe, 0x34, 0x13, 0x09, 0x48, 0x01, 0x0e, 0xbb, 0xfe, 0x36, 0x12, 0xfe,
12791         0x41, 0x48, 0xfe, 0x45,
12792         0x48, 0x01, 0xf0, 0xfe, 0x00, 0xcc, 0xbb, 0xfe, 0xf3, 0x13, 0x43, 0x78,
12793         0x07, 0x11, 0xac, 0x09,
12794         0x84, 0x01, 0x0e, 0xfe, 0x80, 0x5c, 0x01, 0x73, 0xfe, 0x0e, 0x10, 0x07,
12795         0x82, 0x4e, 0xfe, 0x14,
12796         0x56, 0xfe, 0xd6, 0xf0, 0xfe, 0x60, 0x10, 0x04, 0xfe, 0x44, 0x58, 0x8d,
12797         0xfe, 0x01, 0xec, 0xa2,
12798         0xfe, 0x9e, 0x40, 0xfe, 0x9d, 0xe7, 0x00, 0xfe, 0x9c, 0xe7, 0x1a, 0x79,
12799         0x2a, 0x01, 0xe3, 0xfe,
12800         0xdd, 0x10, 0x2c, 0xc7, 0x81, 0xc8, 0x83, 0x33, 0x31, 0xde, 0x07, 0x1a,
12801         0xfe, 0x48, 0x12, 0x07,
12802         0x0a, 0xfe, 0x56, 0x12, 0x07, 0x19, 0xfe, 0x30, 0x12, 0x07, 0xc9, 0x17,
12803         0xfe, 0x32, 0x12, 0x07,
12804         0xfe, 0x23, 0x00, 0x17, 0xeb, 0x07, 0x06, 0x17, 0xfe, 0x9c, 0x12, 0x07,
12805         0x1f, 0xfe, 0x12, 0x12,
12806         0x07, 0x00, 0x17, 0x24, 0x15, 0xc9, 0x01, 0x36, 0xa9, 0x2d, 0x01, 0x0b,
12807         0x94, 0x4b, 0x04, 0x2d,
12808         0xdd, 0x09, 0xd1, 0x01, 0xfe, 0x26, 0x0f, 0x12, 0x82, 0x02, 0x2b, 0x2d,
12809         0x32, 0x07, 0xa6, 0xfe,
12810         0xd9, 0x13, 0x3a, 0x3d, 0x3b, 0x3e, 0x56, 0xfe, 0xf0, 0x11, 0x08, 0x05,
12811         0x5a, 0xfe, 0x72, 0x12,
12812         0x9b, 0x2e, 0x9c, 0x3c, 0x90, 0xc0, 0x96, 0xfe, 0xba, 0x11, 0x22, 0x62,
12813         0xfe, 0x26, 0x13, 0x03,
12814         0x7f, 0x29, 0x80, 0x56, 0xfe, 0x76, 0x0d, 0x0c, 0x60, 0x14, 0x61, 0x21,
12815         0x0c, 0x7f, 0x0c, 0x80,
12816         0x01, 0xb3, 0x25, 0x6e, 0x77, 0x13, 0x62, 0x01, 0xef, 0x9b, 0x2e, 0x9c,
12817         0x3c, 0xfe, 0x04, 0x55,
12818         0xfe, 0xa5, 0x55, 0xfe, 0x04, 0xfa, 0x2e, 0xfe, 0x05, 0xfa, 0x3c, 0xfe,
12819         0x91, 0x10, 0x03, 0x3f,
12820         0x29, 0x40, 0xfe, 0x40, 0x56, 0xfe, 0xe1, 0x56, 0x0c, 0x3f, 0x14, 0x40,
12821         0x88, 0x9b, 0x2e, 0x9c,
12822         0x3c, 0x90, 0xc0, 0x03, 0x5e, 0x29, 0x5f, 0xfe, 0x00, 0x56, 0xfe, 0xa1,
12823         0x56, 0x0c, 0x5e, 0x14,
12824         0x5f, 0x08, 0x05, 0x5a, 0xfe, 0x1e, 0x12, 0x22, 0x62, 0xfe, 0x1f, 0x40,
12825         0x03, 0x60, 0x29, 0x61,
12826         0xfe, 0x2c, 0x50, 0xfe, 0xae, 0x50, 0x03, 0x3f, 0x29, 0x40, 0xfe, 0x44,
12827         0x50, 0xfe, 0xc6, 0x50,
12828         0x03, 0x5e, 0x29, 0x5f, 0xfe, 0x08, 0x50, 0xfe, 0x8a, 0x50, 0x03, 0x3d,
12829         0x29, 0x3e, 0xfe, 0x40,
12830         0x50, 0xfe, 0xc2, 0x50, 0x02, 0x89, 0x25, 0x06, 0x13, 0xd4, 0x02, 0x72,
12831         0x2d, 0x01, 0x0b, 0x1d,
12832         0x4c, 0x33, 0x31, 0xde, 0x07, 0x06, 0x23, 0x4c, 0x32, 0x07, 0xa6, 0x23,
12833         0x72, 0x01, 0xaf, 0x1e,
12834         0x43, 0x17, 0x4c, 0x08, 0x05, 0x0a, 0xee, 0x3a, 0x3d, 0x3b, 0x3e, 0xfe,
12835         0x0a, 0x55, 0x35, 0xfe,
12836         0x8b, 0x55, 0x57, 0x3d, 0x7d, 0x3e, 0xfe, 0x0c, 0x51, 0xfe, 0x8e, 0x51,
12837         0x02, 0x72, 0xfe, 0x19,
12838         0x81, 0xba, 0xfe, 0x19, 0x41, 0x02, 0x72, 0x2d, 0x01, 0x0b, 0x1c, 0x34,
12839         0x1d, 0xe8, 0x33, 0x31,
12840         0xe1, 0x55, 0x19, 0xfe, 0xa6, 0x12, 0x55, 0x0a, 0x4d, 0x02, 0x4c, 0x01,
12841         0x0b, 0x1c, 0x34, 0x1d,
12842         0xe8, 0x33, 0x31, 0xdf, 0x07, 0x19, 0x23, 0x4c, 0x01, 0x0b, 0x1d, 0xe8,
12843         0x33, 0x31, 0xfe, 0xe8,
12844         0x09, 0xfe, 0xc2, 0x49, 0x51, 0x03, 0xfe, 0x9c, 0x00, 0x28, 0x8a, 0x53,
12845         0x05, 0x1f, 0x35, 0xa9,
12846         0xfe, 0xbb, 0x45, 0x55, 0x00, 0x4e, 0x44, 0x06, 0x7c, 0x43, 0xfe, 0xda,
12847         0x14, 0x01, 0xaf, 0x8c,
12848         0xfe, 0x4b, 0x45, 0xee, 0x32, 0x07, 0xa5, 0xed, 0x03, 0xcd, 0x28, 0x8a,
12849         0x03, 0x45, 0x28, 0x35,
12850         0x67, 0x02, 0x72, 0xfe, 0xc0, 0x5d, 0xfe, 0xf8, 0x14, 0xfe, 0x03, 0x17,
12851         0x03, 0x5c, 0xc1, 0x0c,
12852         0x5c, 0x67, 0x2d, 0x01, 0x0b, 0x26, 0x89, 0x01, 0xfe, 0x9e, 0x15, 0x02,
12853         0x89, 0x01, 0x0b, 0x1c,
12854         0x34, 0x1d, 0x4c, 0x33, 0x31, 0xdf, 0x07, 0x06, 0x23, 0x4c, 0x01, 0xf1,
12855         0xfe, 0x42, 0x58, 0xf1,
12856         0xfe, 0xa4, 0x14, 0x8c, 0xfe, 0x4a, 0xf4, 0x0a, 0x17, 0x4c, 0xfe, 0x4a,
12857         0xf4, 0x06, 0xea, 0x32,
12858         0x07, 0xa5, 0x8b, 0x02, 0x72, 0x03, 0x45, 0xc1, 0x0c, 0x45, 0x67, 0x2d,
12859         0x01, 0x0b, 0x26, 0x89,
12860         0x01, 0xfe, 0xcc, 0x15, 0x02, 0x89, 0x0f, 0x06, 0x27, 0xfe, 0xbe, 0x13,
12861         0x26, 0xfe, 0xd4, 0x13,
12862         0x76, 0xfe, 0x89, 0x48, 0x01, 0x0b, 0x21, 0x76, 0x04, 0x7b, 0xfe, 0xd0,
12863         0x13, 0x1c, 0xfe, 0xd0,
12864         0x13, 0x1d, 0xfe, 0xbe, 0x13, 0x67, 0x2d, 0x01, 0x0b, 0xfe, 0xd5, 0x10,
12865         0x0f, 0x71, 0xff, 0x02,
12866         0x00, 0x57, 0x52, 0x93, 0x1e, 0xfe, 0xff, 0x7f, 0xfe, 0x30, 0x56, 0xfe,
12867         0x00, 0x5c, 0x04, 0x0f,
12868         0x71, 0xff, 0x02, 0x00, 0x57, 0x52, 0x93, 0x1e, 0x43, 0xfe, 0x30, 0x56,
12869         0xfe, 0x00, 0x5c, 0x04,
12870         0x0f, 0x71, 0xff, 0x02, 0x00, 0x57, 0x52, 0x93, 0x04, 0x0f, 0x71, 0xff,
12871         0x02, 0x00, 0x57, 0x52,
12872         0x93, 0xfe, 0x0b, 0x58, 0x04, 0x09, 0x5c, 0x01, 0x87, 0x09, 0x45, 0x01,
12873         0x87, 0x04, 0xfe, 0x03,
12874         0xa1, 0x1e, 0x11, 0xff, 0x03, 0x00, 0x54, 0xfe, 0x00, 0xf4, 0x1f, 0x52,
12875         0xfe, 0x00, 0x7d, 0xfe,
12876         0x01, 0x7d, 0xfe, 0x02, 0x7d, 0xfe, 0x03, 0x7c, 0x6a, 0x2a, 0x0c, 0x5e,
12877         0x14, 0x5f, 0x57, 0x3f,
12878         0x7d, 0x40, 0x04, 0xdd, 0xfe, 0x82, 0x4a, 0xfe, 0xe1, 0x1a, 0xfe, 0x83,
12879         0x5a, 0x8d, 0x04, 0x01,
12880         0xfe, 0x0c, 0x19, 0xfe, 0x42, 0x48, 0x50, 0x51, 0x91, 0x01, 0x0b, 0x1d,
12881         0xfe, 0x96, 0x15, 0x33,
12882         0x31, 0xe1, 0x01, 0x0b, 0x1d, 0xfe, 0x96, 0x15, 0x33, 0x31, 0xfe, 0xe8,
12883         0x0a, 0xfe, 0xc1, 0x59,
12884         0x03, 0xcd, 0x28, 0xfe, 0xcc, 0x12, 0x53, 0x05, 0x1a, 0xfe, 0xc4, 0x13,
12885         0x21, 0x69, 0x1a, 0xee,
12886         0x55, 0xca, 0x6b, 0xfe, 0xdc, 0x14, 0x4d, 0x0f, 0x06, 0x18, 0xca, 0x7c,
12887         0x30, 0xfe, 0x78, 0x10,
12888         0xff, 0x02, 0x83, 0x55, 0xab, 0xff, 0x02, 0x83, 0x55, 0x69, 0x19, 0xae,
12889         0x98, 0xfe, 0x30, 0x00,
12890         0x96, 0xf2, 0x18, 0x6d, 0x0f, 0x06, 0xfe, 0x56, 0x10, 0x69, 0x0a, 0xed,
12891         0x98, 0xfe, 0x64, 0x00,
12892         0x96, 0xf2, 0x09, 0xfe, 0x64, 0x00, 0x18, 0x9e, 0x0f, 0x06, 0xfe, 0x28,
12893         0x10, 0x69, 0x06, 0xfe,
12894         0x60, 0x13, 0x98, 0xfe, 0xc8, 0x00, 0x96, 0xf2, 0x09, 0xfe, 0xc8, 0x00,
12895         0x18, 0x59, 0x0f, 0x06,
12896         0x88, 0x98, 0xfe, 0x90, 0x01, 0x7a, 0xfe, 0x42, 0x15, 0x91, 0xe4, 0xfe,
12897         0x43, 0xf4, 0x9f, 0xfe,
12898         0x56, 0xf0, 0xfe, 0x54, 0x15, 0xfe, 0x04, 0xf4, 0x71, 0xfe, 0x43, 0xf4,
12899         0x9e, 0xfe, 0xf3, 0x10,
12900         0xfe, 0x40, 0x5c, 0x01, 0xfe, 0x16, 0x14, 0x1e, 0x43, 0xec, 0xfe, 0x00,
12901         0x17, 0xfe, 0x4d, 0xe4,
12902         0x6e, 0x7a, 0xfe, 0x90, 0x15, 0xc4, 0x6e, 0xfe, 0x1c, 0x10, 0xfe, 0x00,
12903         0x17, 0xfe, 0x4d, 0xe4,
12904         0xcc, 0x7a, 0xfe, 0x90, 0x15, 0xc4, 0xcc, 0x88, 0x51, 0x21, 0xfe, 0x4d,
12905         0xf4, 0x00, 0xe9, 0x91,
12906         0x0f, 0x06, 0xfe, 0xb4, 0x56, 0xfe, 0xc3, 0x58, 0x04, 0x51, 0x0f, 0x0a,
12907         0x04, 0x16, 0x06, 0x01,
12908         0x0b, 0x26, 0xf3, 0x16, 0x0a, 0x01, 0x0b, 0x26, 0xf3, 0x16, 0x19, 0x01,
12909         0x0b, 0x26, 0xf3, 0x76,
12910         0xfe, 0x89, 0x49, 0x01, 0x0b, 0x04, 0x16, 0x06, 0x01, 0x0b, 0x26, 0xb1,
12911         0x16, 0x19, 0x01, 0x0b,
12912         0x26, 0xb1, 0x16, 0x06, 0x01, 0x0b, 0x26, 0xb1, 0xfe, 0x89, 0x49, 0x01,
12913         0x0b, 0x26, 0xb1, 0x76,
12914         0xfe, 0x89, 0x4a, 0x01, 0x0b, 0x04, 0x51, 0x04, 0x22, 0xd3, 0x07, 0x06,
12915         0xfe, 0x48, 0x13, 0xb8,
12916         0x13, 0xd3, 0xfe, 0x49, 0xf4, 0x00, 0x4d, 0x76, 0xa9, 0x67, 0xfe, 0x01,
12917         0xec, 0xfe, 0x27, 0x01,
12918         0xfe, 0x89, 0x48, 0xff, 0x02, 0x00, 0x10, 0x27, 0xfe, 0x2e, 0x16, 0x32,
12919         0x07, 0xfe, 0xe3, 0x00,
12920         0xfe, 0x20, 0x13, 0x1d, 0xfe, 0x52, 0x16, 0x21, 0x13, 0xd4, 0x01, 0x4b,
12921         0x22, 0xd4, 0x07, 0x06,
12922         0x4e, 0x08, 0x54, 0x06, 0x37, 0x04, 0x09, 0x48, 0x01, 0x0e, 0xfb, 0x8e,
12923         0x07, 0x11, 0xae, 0x09,
12924         0x84, 0x01, 0x0e, 0x8e, 0x09, 0x5d, 0x01, 0xa8, 0x04, 0x09, 0x84, 0x01,
12925         0x0e, 0x8e, 0xfe, 0x80,
12926         0xe7, 0x11, 0x07, 0x11, 0x8a, 0xfe, 0x45, 0x58, 0x01, 0xf0, 0x8e, 0x04,
12927         0x09, 0x48, 0x01, 0x0e,
12928         0x8e, 0x09, 0x5d, 0x01, 0xa8, 0x04, 0x09, 0x48, 0x01, 0x0e, 0xfe, 0x80,
12929         0x80, 0xfe, 0x80, 0x4c,
12930         0xfe, 0x49, 0xe4, 0x11, 0xae, 0x09, 0x84, 0x01, 0x0e, 0xfe, 0x80, 0x4c,
12931         0x09, 0x5d, 0x01, 0x87,
12932         0x04, 0x18, 0x11, 0x75, 0x6c, 0xfe, 0x60, 0x01, 0xfe, 0x18, 0xdf, 0xfe,
12933         0x19, 0xde, 0xfe, 0x24,
12934         0x1c, 0xfe, 0x1d, 0xf7, 0x1b, 0x97, 0xfe, 0xee, 0x16, 0x01, 0xfe, 0xf4,
12935         0x17, 0xad, 0x9a, 0x1b,
12936         0x6c, 0xfe, 0x2c, 0x01, 0xfe, 0x2f, 0x19, 0x04, 0xb9, 0x23, 0xfe, 0xde,
12937         0x16, 0xfe, 0xda, 0x10,
12938         0x18, 0x11, 0x75, 0x03, 0xfe, 0x64, 0x01, 0xfe, 0x00, 0xf4, 0x1f, 0xfe,
12939         0x18, 0x58, 0x03, 0xfe,
12940         0x66, 0x01, 0xfe, 0x19, 0x58, 0x9a, 0x1f, 0xfe, 0x3c, 0x90, 0xfe, 0x30,
12941         0xf4, 0x06, 0xfe, 0x3c,
12942         0x50, 0x6c, 0xfe, 0x38, 0x00, 0xfe, 0x0f, 0x79, 0xfe, 0x1c, 0xf7, 0x1f,
12943         0x97, 0xfe, 0x38, 0x17,
12944         0xfe, 0xb6, 0x14, 0x35, 0x04, 0xb9, 0x23, 0xfe, 0x10, 0x17, 0xfe, 0x9c,
12945         0x10, 0x18, 0x11, 0x75,
12946         0xfe, 0x83, 0x5a, 0xfe, 0x18, 0xdf, 0xfe, 0x19, 0xde, 0xfe, 0x1d, 0xf7,
12947         0x2e, 0x97, 0xfe, 0x5a,
12948         0x17, 0xfe, 0x94, 0x14, 0xec, 0x9a, 0x2e, 0x6c, 0x1a, 0xfe, 0xaf, 0x19,
12949         0xfe, 0x98, 0xe7, 0x00,
12950         0x04, 0xb9, 0x23, 0xfe, 0x4e, 0x17, 0xfe, 0x6c, 0x10, 0x18, 0x11, 0x75,
12951         0xfe, 0x30, 0xbc, 0xfe,
12952         0xb2, 0xbc, 0x9a, 0xcb, 0x6c, 0x1a, 0xfe, 0x0f, 0x79, 0xfe, 0x1c, 0xf7,
12953         0xcb, 0x97, 0xfe, 0x92,
12954         0x17, 0xfe, 0x5c, 0x14, 0x35, 0x04, 0xb9, 0x23, 0xfe, 0x7e, 0x17, 0xfe,
12955         0x42, 0x10, 0xfe, 0x02,
12956         0xf6, 0x11, 0x75, 0xfe, 0x18, 0xfe, 0x60, 0xfe, 0x19, 0xfe, 0x61, 0xfe,
12957         0x03, 0xa1, 0xfe, 0x1d,
12958         0xf7, 0x5b, 0x97, 0xfe, 0xb8, 0x17, 0xfe, 0x36, 0x14, 0xfe, 0x1c, 0x13,
12959         0x9a, 0x5b, 0x41, 0xfe,
12960         0x83, 0x58, 0xfe, 0xaf, 0x19, 0xfe, 0x80, 0xe7, 0x11, 0xfe, 0x81, 0xe7,
12961         0x11, 0x12, 0xfe, 0xdd,
12962         0x00, 0x6a, 0x2a, 0x04, 0x6a, 0x2a, 0xfe, 0x12, 0x45, 0x23, 0xfe, 0xa8,
12963         0x17, 0x15, 0x06, 0x39,
12964         0xa0, 0xb4, 0x02, 0x2b, 0xfe, 0x39, 0xf0, 0xfe, 0xfc, 0x17, 0x21, 0x04,
12965         0xfe, 0x7e, 0x18, 0x1e,
12966         0x19, 0x66, 0x0f, 0x0d, 0x04, 0x75, 0x03, 0xd2, 0x1e, 0x06, 0xfe, 0xef,
12967         0x12, 0xfe, 0xe1, 0x10,
12968         0x7c, 0x6f, 0x4f, 0x32, 0x07, 0x2f, 0xfe, 0x3c, 0x13, 0xf1, 0xfe, 0x42,
12969         0x13, 0x42, 0x92, 0x09,
12970         0x48, 0x01, 0x0e, 0xbb, 0xeb, 0xfe, 0x41, 0x48, 0xfe, 0x45, 0x48, 0x01,
12971         0xf0, 0xfe, 0x00, 0xcc,
12972         0xbb, 0xfe, 0xf3, 0x13, 0x43, 0x78, 0x07, 0x11, 0xac, 0x09, 0x84, 0x01,
12973         0x0e, 0xfe, 0x80, 0x4c,
12974         0x01, 0x73, 0xfe, 0x16, 0x10, 0x07, 0x82, 0x8b, 0xfe, 0x40, 0x14, 0xfe,
12975         0x24, 0x12, 0xfe, 0x14,
12976         0x56, 0xfe, 0xd6, 0xf0, 0xfe, 0x1c, 0x18, 0x18, 0x0a, 0x04, 0xfe, 0x9c,
12977         0xe7, 0x0a, 0x10, 0xfe,
12978         0x15, 0x00, 0x64, 0x79, 0x2a, 0x01, 0xe3, 0x18, 0x06, 0x04, 0x42, 0x92,
12979         0x08, 0x54, 0x1b, 0x37,
12980         0x12, 0x2f, 0x01, 0x73, 0x18, 0x06, 0x04, 0xfe, 0x38, 0x90, 0xfe, 0xba,
12981         0x90, 0x3a, 0xce, 0x3b,
12982         0xcf, 0xfe, 0x48, 0x55, 0x35, 0xfe, 0xc9, 0x55, 0x04, 0x22, 0xa3, 0x77,
12983         0x13, 0xa3, 0x04, 0x09,
12984         0xa4, 0x01, 0x0e, 0xfe, 0x41, 0x48, 0x09, 0x46, 0x01, 0x0e, 0xfe, 0x49,
12985         0x44, 0x17, 0xfe, 0xe8,
12986         0x18, 0x77, 0x78, 0x04, 0x09, 0x48, 0x01, 0x0e, 0x07, 0x11, 0x4e, 0x09,
12987         0x5d, 0x01, 0xa8, 0x09,
12988         0x46, 0x01, 0x0e, 0x77, 0x78, 0x04, 0xfe, 0x4e, 0xe4, 0x19, 0x6b, 0xfe,
12989         0x1c, 0x19, 0x03, 0xfe,
12990         0x90, 0x00, 0xfe, 0x3a, 0x45, 0xfe, 0x2c, 0x10, 0xfe, 0x4e, 0xe4, 0xc9,
12991         0x6b, 0xfe, 0x2e, 0x19,
12992         0x03, 0xfe, 0x92, 0x00, 0xfe, 0x02, 0xe6, 0x1a, 0xe5, 0xfe, 0x4e, 0xe4,
12993         0xfe, 0x0b, 0x00, 0x6b,
12994         0xfe, 0x40, 0x19, 0x03, 0xfe, 0x94, 0x00, 0xfe, 0x02, 0xe6, 0x1f, 0xfe,
12995         0x08, 0x10, 0x03, 0xfe,
12996         0x96, 0x00, 0xfe, 0x02, 0xe6, 0x6d, 0xfe, 0x4e, 0x45, 0xea, 0xba, 0xff,
12997         0x04, 0x68, 0x54, 0xe7,
12998         0x1e, 0x6e, 0xfe, 0x08, 0x1c, 0xfe, 0x67, 0x19, 0xfe, 0x0a, 0x1c, 0xfe,
12999         0x1a, 0xf4, 0xfe, 0x00,
13000         0x04, 0xea, 0xfe, 0x48, 0xf4, 0x19, 0x7a, 0xfe, 0x74, 0x19, 0x0f, 0x19,
13001         0x04, 0x07, 0x7e, 0xfe,
13002         0x5a, 0xf0, 0xfe, 0x84, 0x19, 0x25, 0xfe, 0x09, 0x00, 0xfe, 0x34, 0x10,
13003         0x07, 0x1a, 0xfe, 0x5a,
13004         0xf0, 0xfe, 0x92, 0x19, 0x25, 0xca, 0xfe, 0x26, 0x10, 0x07, 0x19, 0x66,
13005         0x25, 0x6d, 0xe5, 0x07,
13006         0x0a, 0x66, 0x25, 0x9e, 0xfe, 0x0e, 0x10, 0x07, 0x06, 0x66, 0x25, 0x59,
13007         0xa9, 0xb8, 0x04, 0x15,
13008         0xfe, 0x09, 0x00, 0x01, 0x36, 0xfe, 0x04, 0xfe, 0x81, 0x03, 0x83, 0xfe,
13009         0x40, 0x5c, 0x04, 0x1c,
13010         0xf7, 0xfe, 0x14, 0xf0, 0x0b, 0x27, 0xfe, 0xd6, 0x19, 0x1c, 0xf7, 0x7b,
13011         0xf7, 0xfe, 0x82, 0xf0,
13012         0xfe, 0xda, 0x19, 0x04, 0xff, 0xcc, 0x00, 0x00,
13013 };
13014
13015 static unsigned short _adv_asc38C0800_size = sizeof(_adv_asc38C0800_buf);       /* 0x14E1 */
13016 static ADV_DCNT _adv_asc38C0800_chksum = 0x050D3FD8UL;  /* Expanded little-endian checksum. */
13017
13018 /* Microcode buffer is kept after initialization for error recovery. */
13019 static unsigned char _adv_asc38C1600_buf[] = {
13020         0x00, 0x00, 0x00, 0xf2, 0x00, 0x16, 0x00, 0xfc, 0x00, 0x10, 0x00, 0xf0,
13021         0x18, 0xe4, 0x01, 0x00,
13022         0x04, 0x1e, 0x48, 0xe4, 0x03, 0xf6, 0xf7, 0x13, 0x2e, 0x1e, 0x02, 0x00,
13023         0x07, 0x17, 0xc0, 0x5f,
13024         0x00, 0xfa, 0xff, 0xff, 0x04, 0x00, 0x00, 0xf6, 0x09, 0xe7, 0x82, 0xe7,
13025         0x85, 0xf0, 0x86, 0xf0,
13026         0x4e, 0x10, 0x9e, 0xe7, 0xff, 0x00, 0x55, 0xf0, 0x01, 0xf6, 0x03, 0x00,
13027         0x98, 0x57, 0x01, 0xe6,
13028         0x00, 0xea, 0x00, 0xec, 0x01, 0xfa, 0x18, 0xf4, 0x08, 0x00, 0xf0, 0x1d,
13029         0x38, 0x54, 0x32, 0xf0,
13030         0x10, 0x00, 0xc2, 0x0e, 0x1e, 0xf0, 0xd5, 0xf0, 0xbc, 0x00, 0x4b, 0xe4,
13031         0x00, 0xe6, 0xb1, 0xf0,
13032         0xb4, 0x00, 0x02, 0x13, 0x3e, 0x1c, 0xc8, 0x47, 0x3e, 0x00, 0xd8, 0x01,
13033         0x06, 0x13, 0x0c, 0x1c,
13034         0x5e, 0x1e, 0x00, 0x57, 0xc8, 0x57, 0x01, 0xfc, 0xbc, 0x0e, 0xa2, 0x12,
13035         0xb9, 0x54, 0x00, 0x80,
13036         0x62, 0x0a, 0x5a, 0x12, 0xc8, 0x15, 0x3e, 0x1e, 0x18, 0x40, 0xbd, 0x56,
13037         0x03, 0xe6, 0x01, 0xea,
13038         0x5c, 0xf0, 0x0f, 0x00, 0x20, 0x00, 0x6c, 0x01, 0x6e, 0x01, 0x04, 0x12,
13039         0x04, 0x13, 0xbb, 0x55,
13040         0x3c, 0x56, 0x3e, 0x57, 0x03, 0x58, 0x4a, 0xe4, 0x40, 0x00, 0xb6, 0x00,
13041         0xbb, 0x00, 0xc0, 0x00,
13042         0x00, 0x01, 0x01, 0x01, 0x3e, 0x01, 0x58, 0x0a, 0x44, 0x10, 0x0a, 0x12,
13043         0x4c, 0x1c, 0x4e, 0x1c,
13044         0x02, 0x4a, 0x30, 0xe4, 0x05, 0xe6, 0x0c, 0x00, 0x3c, 0x00, 0x80, 0x00,
13045         0x24, 0x01, 0x3c, 0x01,
13046         0x68, 0x01, 0x6a, 0x01, 0x70, 0x01, 0x72, 0x01, 0x74, 0x01, 0x76, 0x01,
13047         0x78, 0x01, 0x7c, 0x01,
13048         0xc6, 0x0e, 0x0c, 0x10, 0xac, 0x12, 0xae, 0x12, 0x16, 0x1a, 0x32, 0x1c,
13049         0x6e, 0x1e, 0x02, 0x48,
13050         0x3a, 0x55, 0xc9, 0x57, 0x02, 0xee, 0x5b, 0xf0, 0x03, 0xf7, 0x06, 0xf7,
13051         0x03, 0xfc, 0x06, 0x00,
13052         0x1e, 0x00, 0xbe, 0x00, 0xe1, 0x00, 0x0c, 0x12, 0x18, 0x1a, 0x70, 0x1a,
13053         0x30, 0x1c, 0x38, 0x1c,
13054         0x10, 0x44, 0x00, 0x4c, 0xb0, 0x57, 0x40, 0x5c, 0x4d, 0xe4, 0x04, 0xea,
13055         0x5d, 0xf0, 0xa7, 0xf0,
13056         0x04, 0xf6, 0x02, 0xfc, 0x05, 0x00, 0x09, 0x00, 0x19, 0x00, 0x32, 0x00,
13057         0x33, 0x00, 0x34, 0x00,
13058         0x36, 0x00, 0x98, 0x00, 0x9e, 0x00, 0xcc, 0x00, 0x20, 0x01, 0x4e, 0x01,
13059         0x79, 0x01, 0x3c, 0x09,
13060         0x68, 0x0d, 0x02, 0x10, 0x04, 0x10, 0x3a, 0x10, 0x08, 0x12, 0x0a, 0x13,
13061         0x40, 0x16, 0x50, 0x16,
13062         0x00, 0x17, 0x4a, 0x19, 0x00, 0x4e, 0x00, 0x54, 0x01, 0x58, 0x00, 0xdc,
13063         0x05, 0xf0, 0x09, 0xf0,
13064         0x59, 0xf0, 0xb8, 0xf0, 0x48, 0xf4, 0x0e, 0xf7, 0x0a, 0x00, 0x9b, 0x00,
13065         0x9c, 0x00, 0xa4, 0x00,
13066         0xb5, 0x00, 0xba, 0x00, 0xd0, 0x00, 0xe7, 0x00, 0xf0, 0x03, 0x69, 0x08,
13067         0xe9, 0x09, 0x5c, 0x0c,
13068         0xb6, 0x12, 0xbc, 0x19, 0xd8, 0x1b, 0x20, 0x1c, 0x34, 0x1c, 0x36, 0x1c,
13069         0x42, 0x1d, 0x08, 0x44,
13070         0x38, 0x44, 0x91, 0x44, 0x0a, 0x45, 0x48, 0x46, 0x89, 0x48, 0x68, 0x54,
13071         0x83, 0x55, 0x83, 0x59,
13072         0x31, 0xe4, 0x02, 0xe6, 0x07, 0xf0, 0x08, 0xf0, 0x0b, 0xf0, 0x0c, 0xf0,
13073         0x4b, 0xf4, 0x04, 0xf8,
13074         0x05, 0xf8, 0x02, 0xfa, 0x03, 0xfa, 0x04, 0xfc, 0x05, 0xfc, 0x07, 0x00,
13075         0xa8, 0x00, 0xaa, 0x00,
13076         0xb9, 0x00, 0xe0, 0x00, 0xe5, 0x00, 0x22, 0x01, 0x26, 0x01, 0x60, 0x01,
13077         0x7a, 0x01, 0x82, 0x01,
13078         0xc8, 0x01, 0xca, 0x01, 0x86, 0x02, 0x6a, 0x03, 0x18, 0x05, 0xb2, 0x07,
13079         0x68, 0x08, 0x10, 0x0d,
13080         0x06, 0x10, 0x0a, 0x10, 0x0e, 0x10, 0x12, 0x10, 0x60, 0x10, 0xed, 0x10,
13081         0xf3, 0x10, 0x06, 0x12,
13082         0x10, 0x12, 0x1e, 0x12, 0x0c, 0x13, 0x0e, 0x13, 0x10, 0x13, 0xfe, 0x9c,
13083         0xf0, 0x35, 0x05, 0xfe,
13084         0xec, 0x0e, 0xff, 0x10, 0x00, 0x00, 0xe9, 0xfe, 0x34, 0x1f, 0x00, 0xe8,
13085         0xfe, 0x88, 0x01, 0xff,
13086         0x03, 0x00, 0x00, 0xfe, 0x93, 0x15, 0xfe, 0x0f, 0x05, 0xff, 0x38, 0x00,
13087         0x00, 0xfe, 0x57, 0x24,
13088         0x00, 0xfe, 0x4c, 0x00, 0x65, 0xff, 0x04, 0x00, 0x00, 0x1a, 0xff, 0x09,
13089         0x00, 0x00, 0xff, 0x08,
13090         0x01, 0x01, 0xff, 0x08, 0xff, 0xff, 0xff, 0x27, 0x00, 0x00, 0xff, 0x10,
13091         0xff, 0xff, 0xff, 0x13,
13092         0x00, 0x00, 0xfe, 0x78, 0x56, 0xfe, 0x34, 0x12, 0xff, 0x21, 0x00, 0x00,
13093         0xfe, 0x04, 0xf7, 0xe8,
13094         0x37, 0x7d, 0x0d, 0x01, 0xfe, 0x4a, 0x11, 0xfe, 0x04, 0xf7, 0xe8, 0x7d,
13095         0x0d, 0x51, 0x37, 0xfe,
13096         0x3d, 0xf0, 0xfe, 0x0c, 0x02, 0xfe, 0x20, 0xf0, 0xbc, 0xfe, 0x91, 0xf0,
13097         0xfe, 0xf8, 0x01, 0xfe,
13098         0x90, 0xf0, 0xfe, 0xf8, 0x01, 0xfe, 0x8f, 0xf0, 0xbc, 0x03, 0x67, 0x4d,
13099         0x05, 0xfe, 0x08, 0x0f,
13100         0x01, 0xfe, 0x78, 0x0f, 0xfe, 0xdd, 0x12, 0x05, 0xfe, 0x0e, 0x03, 0xfe,
13101         0x28, 0x1c, 0x03, 0xfe,
13102         0xa6, 0x00, 0xfe, 0xd1, 0x12, 0x3e, 0x22, 0xfe, 0xa6, 0x00, 0xac, 0xfe,
13103         0x48, 0xf0, 0xfe, 0x90,
13104         0x02, 0xfe, 0x49, 0xf0, 0xfe, 0xaa, 0x02, 0xfe, 0x4a, 0xf0, 0xfe, 0xc8,
13105         0x02, 0xfe, 0x46, 0xf0,
13106         0xfe, 0x5a, 0x02, 0xfe, 0x47, 0xf0, 0xfe, 0x60, 0x02, 0xfe, 0x43, 0xf0,
13107         0xfe, 0x4e, 0x02, 0xfe,
13108         0x44, 0xf0, 0xfe, 0x52, 0x02, 0xfe, 0x45, 0xf0, 0xfe, 0x56, 0x02, 0x1c,
13109         0x0d, 0xa2, 0x1c, 0x07,
13110         0x22, 0xb7, 0x05, 0x35, 0xfe, 0x00, 0x1c, 0xfe, 0xf1, 0x10, 0xfe, 0x02,
13111         0x1c, 0xf5, 0xfe, 0x1e,
13112         0x1c, 0xfe, 0xe9, 0x10, 0x01, 0x5f, 0xfe, 0xe7, 0x10, 0xfe, 0x06, 0xfc,
13113         0xde, 0x0a, 0x81, 0x01,
13114         0xa3, 0x05, 0x35, 0x1f, 0x95, 0x47, 0xb8, 0x01, 0xfe, 0xe4, 0x11, 0x0a,
13115         0x81, 0x01, 0x5c, 0xfe,
13116         0xbd, 0x10, 0x0a, 0x81, 0x01, 0x5c, 0xfe, 0xad, 0x10, 0xfe, 0x16, 0x1c,
13117         0xfe, 0x58, 0x1c, 0x1c,
13118         0x07, 0x22, 0xb7, 0x37, 0x2a, 0x35, 0xfe, 0x3d, 0xf0, 0xfe, 0x0c, 0x02,
13119         0x2b, 0xfe, 0x9e, 0x02,
13120         0xfe, 0x5a, 0x1c, 0xfe, 0x12, 0x1c, 0xfe, 0x14, 0x1c, 0x1f, 0xfe, 0x30,
13121         0x00, 0x47, 0xb8, 0x01,
13122         0xfe, 0xd4, 0x11, 0x1c, 0x07, 0x22, 0xb7, 0x05, 0xe9, 0x21, 0x2c, 0x09,
13123         0x1a, 0x31, 0xfe, 0x69,
13124         0x10, 0x1c, 0x07, 0x22, 0xb7, 0xfe, 0x04, 0xec, 0x2c, 0x60, 0x01, 0xfe,
13125         0x1e, 0x1e, 0x20, 0x2c,
13126         0xfe, 0x05, 0xf6, 0xde, 0x01, 0xfe, 0x62, 0x1b, 0x01, 0x0c, 0x61, 0x4a,
13127         0x44, 0x15, 0x56, 0x51,
13128         0x01, 0xfe, 0x9e, 0x1e, 0x01, 0xfe, 0x96, 0x1a, 0x05, 0x35, 0x0a, 0x57,
13129         0x01, 0x18, 0x09, 0x00,
13130         0x36, 0x01, 0x85, 0xfe, 0x18, 0x10, 0xfe, 0x41, 0x58, 0x0a, 0xba, 0x01,
13131         0x18, 0xfe, 0xc8, 0x54,
13132         0x7b, 0xfe, 0x1c, 0x03, 0x01, 0xfe, 0x96, 0x1a, 0x05, 0x35, 0x37, 0x60,
13133         0xfe, 0x02, 0xe8, 0x30,
13134         0xfe, 0xbf, 0x57, 0xfe, 0x9e, 0x43, 0xfe, 0x77, 0x57, 0xfe, 0x27, 0xf0,
13135         0xfe, 0xe4, 0x01, 0xfe,
13136         0x07, 0x4b, 0xfe, 0x20, 0xf0, 0xbc, 0xfe, 0x40, 0x1c, 0x2a, 0xeb, 0xfe,
13137         0x26, 0xf0, 0xfe, 0x66,
13138         0x03, 0xfe, 0xa0, 0xf0, 0xfe, 0x54, 0x03, 0xfe, 0x11, 0xf0, 0xbc, 0xfe,
13139         0xef, 0x10, 0xfe, 0x9f,
13140         0xf0, 0xfe, 0x74, 0x03, 0xfe, 0x46, 0x1c, 0x19, 0xfe, 0x11, 0x00, 0x05,
13141         0x70, 0x37, 0xfe, 0x48,
13142         0x1c, 0xfe, 0x46, 0x1c, 0x01, 0x0c, 0x06, 0x28, 0xfe, 0x18, 0x13, 0x26,
13143         0x21, 0xb9, 0xc7, 0x20,
13144         0xb9, 0x0a, 0x57, 0x01, 0x18, 0xc7, 0x89, 0x01, 0xfe, 0xc8, 0x1a, 0x15,
13145         0xe1, 0x2a, 0xeb, 0xfe,
13146         0x01, 0xf0, 0xeb, 0xfe, 0x82, 0xf0, 0xfe, 0xa4, 0x03, 0xfe, 0x9c, 0x32,
13147         0x15, 0xfe, 0xe4, 0x00,
13148         0x2f, 0xfe, 0xb6, 0x03, 0x2a, 0x3c, 0x16, 0xfe, 0xc6, 0x03, 0x01, 0x41,
13149         0xfe, 0x06, 0xf0, 0xfe,
13150         0xd6, 0x03, 0xaf, 0xa0, 0xfe, 0x0a, 0xf0, 0xfe, 0xa2, 0x07, 0x05, 0x29,
13151         0x03, 0x81, 0x1e, 0x1b,
13152         0xfe, 0x24, 0x05, 0x1f, 0x63, 0x01, 0x42, 0x8f, 0xfe, 0x70, 0x02, 0x05,
13153         0xea, 0xfe, 0x46, 0x1c,
13154         0x37, 0x7d, 0x1d, 0xfe, 0x67, 0x1b, 0xfe, 0xbf, 0x57, 0xfe, 0x77, 0x57,
13155         0xfe, 0x48, 0x1c, 0x75,
13156         0x01, 0xa6, 0x86, 0x0a, 0x57, 0x01, 0x18, 0x09, 0x00, 0x1b, 0xec, 0x0a,
13157         0xe1, 0x01, 0x18, 0x77,
13158         0x50, 0x40, 0x8d, 0x30, 0x03, 0x81, 0x1e, 0xf8, 0x1f, 0x63, 0x01, 0x42,
13159         0x8f, 0xfe, 0x70, 0x02,
13160         0x05, 0xea, 0xd7, 0x99, 0xd8, 0x9c, 0x2a, 0x29, 0x2f, 0xfe, 0x4e, 0x04,
13161         0x16, 0xfe, 0x4a, 0x04,
13162         0x7e, 0xfe, 0xa0, 0x00, 0xfe, 0x9b, 0x57, 0xfe, 0x54, 0x12, 0x32, 0xff,
13163         0x02, 0x00, 0x10, 0x01,
13164         0x08, 0x16, 0xfe, 0x02, 0x05, 0x32, 0x01, 0x08, 0x16, 0x29, 0x27, 0x25,
13165         0xee, 0xfe, 0x4c, 0x44,
13166         0xfe, 0x58, 0x12, 0x50, 0xfe, 0x44, 0x48, 0x13, 0x34, 0xfe, 0x4c, 0x54,
13167         0x7b, 0xec, 0x60, 0x8d,
13168         0x30, 0x01, 0xfe, 0x4e, 0x1e, 0xfe, 0x48, 0x47, 0xfe, 0x7c, 0x13, 0x01,
13169         0x0c, 0x06, 0x28, 0xfe,
13170         0x32, 0x13, 0x01, 0x43, 0x09, 0x9b, 0xfe, 0x68, 0x13, 0xfe, 0x26, 0x10,
13171         0x13, 0x34, 0xfe, 0x4c,
13172         0x54, 0x7b, 0xec, 0x01, 0xfe, 0x4e, 0x1e, 0xfe, 0x48, 0x47, 0xfe, 0x54,
13173         0x13, 0x01, 0x0c, 0x06,
13174         0x28, 0xa5, 0x01, 0x43, 0x09, 0x9b, 0xfe, 0x40, 0x13, 0x01, 0x0c, 0x06,
13175         0x28, 0xf9, 0x1f, 0x7f,
13176         0x01, 0x0c, 0x06, 0x07, 0x4d, 0x1f, 0xfe, 0x0d, 0x00, 0x01, 0x42, 0x8f,
13177         0xfe, 0xa4, 0x0e, 0x05,
13178         0x29, 0x32, 0x15, 0xfe, 0xe6, 0x00, 0x0f, 0xfe, 0x1c, 0x90, 0x04, 0xfe,
13179         0x9c, 0x93, 0x3a, 0x0b,
13180         0x0e, 0x8b, 0x02, 0x1f, 0x7f, 0x01, 0x42, 0x05, 0x35, 0xfe, 0x42, 0x5b,
13181         0x7d, 0x1d, 0xfe, 0x46,
13182         0x59, 0xfe, 0xbf, 0x57, 0xfe, 0x77, 0x57, 0x0f, 0xfe, 0x87, 0x80, 0x04,
13183         0xfe, 0x87, 0x83, 0xfe,
13184         0xc9, 0x47, 0x0b, 0x0e, 0xd0, 0x65, 0x01, 0x0c, 0x06, 0x0d, 0xfe, 0x98,
13185         0x13, 0x0f, 0xfe, 0x20,
13186         0x80, 0x04, 0xfe, 0xa0, 0x83, 0x33, 0x0b, 0x0e, 0x09, 0x1d, 0xfe, 0x84,
13187         0x12, 0x01, 0x38, 0x06,
13188         0x07, 0xfe, 0x70, 0x13, 0x03, 0xfe, 0xa2, 0x00, 0x1e, 0x1b, 0xfe, 0xda,
13189         0x05, 0xd0, 0x54, 0x01,
13190         0x38, 0x06, 0x0d, 0xfe, 0x58, 0x13, 0x03, 0xfe, 0xa0, 0x00, 0x1e, 0xfe,
13191         0x50, 0x12, 0x5e, 0xff,
13192         0x02, 0x00, 0x10, 0x2f, 0xfe, 0x90, 0x05, 0x2a, 0x3c, 0xcc, 0xff, 0x02,
13193         0x00, 0x10, 0x2f, 0xfe,
13194         0x9e, 0x05, 0x17, 0xfe, 0xf4, 0x05, 0x15, 0xfe, 0xe3, 0x00, 0x26, 0x01,
13195         0x38, 0xfe, 0x4a, 0xf0,
13196         0xfe, 0xc0, 0x05, 0xfe, 0x49, 0xf0, 0xfe, 0xba, 0x05, 0x71, 0x2e, 0xfe,
13197         0x21, 0x00, 0xf1, 0x2e,
13198         0xfe, 0x22, 0x00, 0xa2, 0x2e, 0x4a, 0xfe, 0x09, 0x48, 0xff, 0x02, 0x00,
13199         0x10, 0x2f, 0xfe, 0xd0,
13200         0x05, 0x17, 0xfe, 0xf4, 0x05, 0xfe, 0xe2, 0x08, 0x01, 0x38, 0x06, 0xfe,
13201         0x1c, 0x00, 0x4d, 0x01,
13202         0xa7, 0x2e, 0x07, 0x20, 0xe4, 0x47, 0xfe, 0x27, 0x01, 0x01, 0x0c, 0x06,
13203         0x28, 0xfe, 0x24, 0x12,
13204         0x3e, 0x01, 0x84, 0x1f, 0x7f, 0x01, 0x0c, 0x06, 0x07, 0x4d, 0x1f, 0xfe,
13205         0x0d, 0x00, 0x01, 0x42,
13206         0x8f, 0xfe, 0xa4, 0x0e, 0x05, 0x29, 0x03, 0xe6, 0x1e, 0xfe, 0xca, 0x13,
13207         0x03, 0xb6, 0x1e, 0xfe,
13208         0x40, 0x12, 0x03, 0x66, 0x1e, 0xfe, 0x38, 0x13, 0x3e, 0x01, 0x84, 0x17,
13209         0xfe, 0x72, 0x06, 0x0a,
13210         0x07, 0x01, 0x38, 0x06, 0x24, 0xfe, 0x02, 0x12, 0x4f, 0x01, 0xfe, 0x56,
13211         0x19, 0x16, 0xfe, 0x68,
13212         0x06, 0x15, 0x82, 0x01, 0x41, 0x15, 0xe2, 0x03, 0x66, 0x8a, 0x10, 0x66,
13213         0x03, 0x9a, 0x1e, 0xfe,
13214         0x70, 0x12, 0x03, 0x55, 0x1e, 0xfe, 0x68, 0x13, 0x01, 0xc6, 0x09, 0x12,
13215         0x48, 0xfe, 0x92, 0x06,
13216         0x2e, 0x12, 0x01, 0xfe, 0xac, 0x1d, 0xfe, 0x43, 0x48, 0x62, 0x80, 0x13,
13217         0x58, 0xff, 0x02, 0x00,
13218         0x57, 0x52, 0xad, 0x23, 0x3f, 0x4e, 0x62, 0x49, 0x3e, 0x01, 0x84, 0x17,
13219         0xfe, 0xea, 0x06, 0x01,
13220         0x38, 0x06, 0x12, 0xf7, 0x45, 0x0a, 0x95, 0x01, 0xfe, 0x84, 0x19, 0x16,
13221         0xfe, 0xe0, 0x06, 0x15,
13222         0x82, 0x01, 0x41, 0x15, 0xe2, 0x03, 0x55, 0x8a, 0x10, 0x55, 0x1c, 0x07,
13223         0x01, 0x84, 0xfe, 0xae,
13224         0x10, 0x03, 0x6f, 0x1e, 0xfe, 0x9e, 0x13, 0x3e, 0x01, 0x84, 0x03, 0x9a,
13225         0x1e, 0xfe, 0x1a, 0x12,
13226         0x01, 0x38, 0x06, 0x12, 0xfc, 0x01, 0xc6, 0x01, 0xfe, 0xac, 0x1d, 0xfe,
13227         0x43, 0x48, 0x62, 0x80,
13228         0xf0, 0x45, 0x0a, 0x95, 0x03, 0xb6, 0x1e, 0xf8, 0x01, 0x38, 0x06, 0x24,
13229         0x36, 0xfe, 0x02, 0xf6,
13230         0x07, 0x71, 0x78, 0x8c, 0x00, 0x4d, 0x62, 0x49, 0x3e, 0x2d, 0x93, 0x4e,
13231         0xd0, 0x0d, 0x17, 0xfe,
13232         0x9a, 0x07, 0x01, 0xfe, 0xc0, 0x19, 0x16, 0xfe, 0x90, 0x07, 0x26, 0x20,
13233         0x9e, 0x15, 0x82, 0x01,
13234         0x41, 0x15, 0xe2, 0x21, 0x9e, 0x09, 0x07, 0xfb, 0x03, 0xe6, 0xfe, 0x58,
13235         0x57, 0x10, 0xe6, 0x05,
13236         0xfe, 0x2a, 0x06, 0x03, 0x6f, 0x8a, 0x10, 0x6f, 0x1c, 0x07, 0x01, 0x84,
13237         0xfe, 0x9c, 0x32, 0x5f,
13238         0x75, 0x01, 0xa6, 0x86, 0x15, 0xfe, 0xe2, 0x00, 0x2f, 0xed, 0x2a, 0x3c,
13239         0xfe, 0x0a, 0xf0, 0xfe,
13240         0xce, 0x07, 0xae, 0xfe, 0x96, 0x08, 0xfe, 0x06, 0xf0, 0xfe, 0x9e, 0x08,
13241         0xaf, 0xa0, 0x05, 0x29,
13242         0x01, 0x0c, 0x06, 0x0d, 0xfe, 0x2e, 0x12, 0x14, 0x1d, 0x01, 0x08, 0x14,
13243         0x00, 0x01, 0x08, 0x14,
13244         0x00, 0x01, 0x08, 0x14, 0x00, 0x01, 0x08, 0xfe, 0x99, 0xa4, 0x01, 0x08,
13245         0x14, 0x00, 0x05, 0xfe,
13246         0xc6, 0x09, 0x01, 0x76, 0x06, 0x12, 0xfe, 0x3a, 0x12, 0x01, 0x0c, 0x06,
13247         0x12, 0xfe, 0x30, 0x13,
13248         0x14, 0xfe, 0x1b, 0x00, 0x01, 0x08, 0x14, 0x00, 0x01, 0x08, 0x14, 0x00,
13249         0x01, 0x08, 0x14, 0x00,
13250         0x01, 0x08, 0x14, 0x07, 0x01, 0x08, 0x14, 0x00, 0x05, 0xef, 0x7c, 0x4a,
13251         0x78, 0x4f, 0x0f, 0xfe,
13252         0x9a, 0x81, 0x04, 0xfe, 0x9a, 0x83, 0xfe, 0xcb, 0x47, 0x0b, 0x0e, 0x2d,
13253         0x28, 0x48, 0xfe, 0x6c,
13254         0x08, 0x0a, 0x28, 0xfe, 0x09, 0x6f, 0xca, 0xfe, 0xca, 0x45, 0xfe, 0x32,
13255         0x12, 0x53, 0x63, 0x4e,
13256         0x7c, 0x97, 0x2f, 0xfe, 0x7e, 0x08, 0x2a, 0x3c, 0xfe, 0x0a, 0xf0, 0xfe,
13257         0x6c, 0x08, 0xaf, 0xa0,
13258         0xae, 0xfe, 0x96, 0x08, 0x05, 0x29, 0x01, 0x41, 0x05, 0xed, 0x14, 0x24,
13259         0x05, 0xed, 0xfe, 0x9c,
13260         0xf7, 0x9f, 0x01, 0xfe, 0xae, 0x1e, 0xfe, 0x18, 0x58, 0x01, 0xfe, 0xbe,
13261         0x1e, 0xfe, 0x99, 0x58,
13262         0xfe, 0x78, 0x18, 0xfe, 0xf9, 0x18, 0x8e, 0xfe, 0x16, 0x09, 0x10, 0x6a,
13263         0x22, 0x6b, 0x01, 0x0c,
13264         0x61, 0x54, 0x44, 0x21, 0x2c, 0x09, 0x1a, 0xf8, 0x77, 0x01, 0xfe, 0x7e,
13265         0x1e, 0x47, 0x2c, 0x7a,
13266         0x30, 0xf0, 0xfe, 0x83, 0xe7, 0xfe, 0x3f, 0x00, 0x71, 0xfe, 0x03, 0x40,
13267         0x01, 0x0c, 0x61, 0x65,
13268         0x44, 0x01, 0xc2, 0xc8, 0xfe, 0x1f, 0x40, 0x20, 0x6e, 0x01, 0xfe, 0x6a,
13269         0x16, 0xfe, 0x08, 0x50,
13270         0xfe, 0x8a, 0x50, 0xfe, 0x44, 0x51, 0xfe, 0xc6, 0x51, 0xfe, 0x10, 0x10,
13271         0x01, 0xfe, 0xce, 0x1e,
13272         0x01, 0xfe, 0xde, 0x1e, 0x10, 0x68, 0x22, 0x69, 0x01, 0xfe, 0xee, 0x1e,
13273         0x01, 0xfe, 0xfe, 0x1e,
13274         0xfe, 0x40, 0x50, 0xfe, 0xc2, 0x50, 0x10, 0x4b, 0x22, 0x4c, 0xfe, 0x8a,
13275         0x10, 0x01, 0x0c, 0x06,
13276         0x54, 0xfe, 0x50, 0x12, 0x01, 0xfe, 0xae, 0x1e, 0x01, 0xfe, 0xbe, 0x1e,
13277         0x10, 0x6a, 0x22, 0x6b,
13278         0x01, 0x0c, 0x06, 0x65, 0x4e, 0x01, 0xc2, 0x0f, 0xfe, 0x1f, 0x80, 0x04,
13279         0xfe, 0x9f, 0x83, 0x33,
13280         0x0b, 0x0e, 0x20, 0x6e, 0x0f, 0xfe, 0x44, 0x90, 0x04, 0xfe, 0xc4, 0x93,
13281         0x3a, 0x0b, 0xfe, 0xc6,
13282         0x90, 0x04, 0xfe, 0xc6, 0x93, 0x79, 0x0b, 0x0e, 0x10, 0x6c, 0x22, 0x6d,
13283         0x01, 0xfe, 0xce, 0x1e,
13284         0x01, 0xfe, 0xde, 0x1e, 0x10, 0x68, 0x22, 0x69, 0x0f, 0xfe, 0x40, 0x90,
13285         0x04, 0xfe, 0xc0, 0x93,
13286         0x3a, 0x0b, 0xfe, 0xc2, 0x90, 0x04, 0xfe, 0xc2, 0x93, 0x79, 0x0b, 0x0e,
13287         0x10, 0x4b, 0x22, 0x4c,
13288         0x10, 0x64, 0x22, 0x34, 0x01, 0x0c, 0x61, 0x24, 0x44, 0x37, 0x13, 0xfe,
13289         0x4e, 0x11, 0x2f, 0xfe,
13290         0xde, 0x09, 0xfe, 0x9e, 0xf0, 0xfe, 0xf2, 0x09, 0xfe, 0x01, 0x48, 0x1b,
13291         0x3c, 0x37, 0x88, 0xf5,
13292         0xd4, 0xfe, 0x1e, 0x0a, 0xd5, 0xfe, 0x42, 0x0a, 0xd2, 0xfe, 0x1e, 0x0a,
13293         0xd3, 0xfe, 0x42, 0x0a,
13294         0xae, 0xfe, 0x12, 0x0a, 0xfe, 0x06, 0xf0, 0xfe, 0x18, 0x0a, 0xaf, 0xa0,
13295         0x05, 0x29, 0x01, 0x41,
13296         0xfe, 0xc1, 0x10, 0x14, 0x24, 0xfe, 0xc1, 0x10, 0x01, 0x76, 0x06, 0x07,
13297         0xfe, 0x14, 0x12, 0x01,
13298         0x76, 0x06, 0x0d, 0x5d, 0x01, 0x0c, 0x06, 0x0d, 0xfe, 0x74, 0x12, 0xfe,
13299         0x2e, 0x1c, 0x05, 0xfe,
13300         0x1a, 0x0c, 0x01, 0x76, 0x06, 0x07, 0x5d, 0x01, 0x76, 0x06, 0x0d, 0x41,
13301         0xfe, 0x2c, 0x1c, 0xfe,
13302         0xaa, 0xf0, 0xfe, 0xce, 0x0a, 0xfe, 0xac, 0xf0, 0xfe, 0x66, 0x0a, 0xfe,
13303         0x92, 0x10, 0xc4, 0xf6,
13304         0xfe, 0xad, 0xf0, 0xfe, 0x72, 0x0a, 0x05, 0xfe, 0x1a, 0x0c, 0xc5, 0xfe,
13305         0xe7, 0x10, 0xfe, 0x2b,
13306         0xf0, 0xbf, 0xfe, 0x6b, 0x18, 0x23, 0xfe, 0x00, 0xfe, 0xfe, 0x1c, 0x12,
13307         0xac, 0xfe, 0xd2, 0xf0,
13308         0xbf, 0xfe, 0x76, 0x18, 0x23, 0x1d, 0x1b, 0xbf, 0x03, 0xe3, 0x23, 0x07,
13309         0x1b, 0xbf, 0xd4, 0x5b,
13310         0xd5, 0x5b, 0xd2, 0x5b, 0xd3, 0x5b, 0xc4, 0xc5, 0xfe, 0xa9, 0x10, 0x75,
13311         0x5e, 0x32, 0x1f, 0x7f,
13312         0x01, 0x42, 0x19, 0xfe, 0x35, 0x00, 0xfe, 0x01, 0xf0, 0x70, 0x19, 0x98,
13313         0x05, 0x70, 0xfe, 0x74,
13314         0x18, 0x23, 0xfe, 0x00, 0xf8, 0x1b, 0x5b, 0x7d, 0x12, 0x01, 0xfe, 0x78,
13315         0x0f, 0x4d, 0x01, 0xfe,
13316         0x96, 0x1a, 0x21, 0x30, 0x77, 0x7d, 0x1d, 0x05, 0x5b, 0x01, 0x0c, 0x06,
13317         0x0d, 0x2b, 0xfe, 0xe2,
13318         0x0b, 0x01, 0x0c, 0x06, 0x54, 0xfe, 0xa6, 0x12, 0x01, 0x0c, 0x06, 0x24,
13319         0xfe, 0x88, 0x13, 0x21,
13320         0x6e, 0xc7, 0x01, 0xfe, 0x1e, 0x1f, 0x0f, 0xfe, 0x83, 0x80, 0x04, 0xfe,
13321         0x83, 0x83, 0xfe, 0xc9,
13322         0x47, 0x0b, 0x0e, 0xfe, 0xc8, 0x44, 0xfe, 0x42, 0x13, 0x0f, 0xfe, 0x04,
13323         0x91, 0x04, 0xfe, 0x84,
13324         0x93, 0xfe, 0xca, 0x57, 0x0b, 0xfe, 0x86, 0x91, 0x04, 0xfe, 0x86, 0x93,
13325         0xfe, 0xcb, 0x57, 0x0b,
13326         0x0e, 0x7a, 0x30, 0xfe, 0x40, 0x59, 0xfe, 0xc1, 0x59, 0x8e, 0x40, 0x03,
13327         0x6a, 0x3b, 0x6b, 0x10,
13328         0x97, 0x22, 0x98, 0xd9, 0x6a, 0xda, 0x6b, 0x01, 0xc2, 0xc8, 0x7a, 0x30,
13329         0x20, 0x6e, 0xdb, 0x64,
13330         0xdc, 0x34, 0x91, 0x6c, 0x7e, 0x6d, 0xfe, 0x44, 0x55, 0xfe, 0xe5, 0x55,
13331         0xfe, 0x04, 0xfa, 0x64,
13332         0xfe, 0x05, 0xfa, 0x34, 0x01, 0xfe, 0x6a, 0x16, 0xa3, 0x26, 0x10, 0x97,
13333         0x10, 0x98, 0x91, 0x6c,
13334         0x7e, 0x6d, 0xfe, 0x14, 0x10, 0x01, 0x0c, 0x06, 0x24, 0x1b, 0x40, 0x91,
13335         0x4b, 0x7e, 0x4c, 0x01,
13336         0x0c, 0x06, 0xfe, 0xf7, 0x00, 0x44, 0x03, 0x68, 0x3b, 0x69, 0xfe, 0x10,
13337         0x58, 0xfe, 0x91, 0x58,
13338         0xfe, 0x14, 0x59, 0xfe, 0x95, 0x59, 0x05, 0x5b, 0x01, 0x0c, 0x06, 0x24,
13339         0x1b, 0x40, 0x01, 0x0c,
13340         0x06, 0xfe, 0xf7, 0x00, 0x44, 0x78, 0x01, 0xfe, 0x8e, 0x1e, 0x4f, 0x0f,
13341         0xfe, 0x10, 0x90, 0x04,
13342         0xfe, 0x90, 0x93, 0x3a, 0x0b, 0xfe, 0x92, 0x90, 0x04, 0xfe, 0x92, 0x93,
13343         0x79, 0x0b, 0x0e, 0xfe,
13344         0xbd, 0x10, 0x01, 0x43, 0x09, 0xbb, 0x1b, 0xfe, 0x6e, 0x0a, 0x15, 0xbb,
13345         0x01, 0x0c, 0x06, 0x0d,
13346         0xfe, 0x14, 0x13, 0x03, 0x4b, 0x3b, 0x4c, 0x8e, 0xfe, 0x6e, 0x0a, 0xfe,
13347         0x0c, 0x58, 0xfe, 0x8d,
13348         0x58, 0x05, 0x5b, 0x26, 0x3e, 0x0f, 0xfe, 0x19, 0x80, 0x04, 0xfe, 0x99,
13349         0x83, 0x33, 0x0b, 0x0e,
13350         0xfe, 0xe5, 0x10, 0x01, 0x0c, 0x06, 0x0d, 0xfe, 0x1a, 0x12, 0xfe, 0x6c,
13351         0x19, 0xfe, 0x19, 0x41,
13352         0xfe, 0x6b, 0x18, 0xac, 0xfe, 0xd1, 0xf0, 0xef, 0x1f, 0x92, 0x01, 0x42,
13353         0x19, 0xfe, 0x44, 0x00,
13354         0xfe, 0x90, 0x10, 0xfe, 0x6c, 0x19, 0xd9, 0x4b, 0xfe, 0xed, 0x19, 0xda,
13355         0x4c, 0xfe, 0x0c, 0x51,
13356         0xfe, 0x8e, 0x51, 0xfe, 0x6b, 0x18, 0x23, 0xfe, 0x00, 0xff, 0x31, 0xfe,
13357         0x76, 0x10, 0xac, 0xfe,
13358         0xd2, 0xf0, 0xfe, 0xba, 0x0c, 0xfe, 0x76, 0x18, 0x23, 0x1d, 0x5d, 0x03,
13359         0xe3, 0x23, 0x07, 0xfe,
13360         0x08, 0x13, 0x19, 0xfe, 0x16, 0x00, 0x05, 0x70, 0xfe, 0xd1, 0xf0, 0xfe,
13361         0xcc, 0x0c, 0x1f, 0x92,
13362         0x01, 0x42, 0x19, 0xfe, 0x17, 0x00, 0x5c, 0xfe, 0xce, 0xf0, 0xfe, 0xd2,
13363         0x0c, 0xfe, 0x3e, 0x10,
13364         0xfe, 0xcd, 0xf0, 0xfe, 0xde, 0x0c, 0x19, 0xfe, 0x22, 0x00, 0x05, 0x70,
13365         0xfe, 0xcb, 0xf0, 0xfe,
13366         0xea, 0x0c, 0x19, 0xfe, 0x24, 0x00, 0x05, 0x70, 0xfe, 0xd0, 0xf0, 0xfe,
13367         0xf4, 0x0c, 0x19, 0x94,
13368         0xfe, 0x1c, 0x10, 0xfe, 0xcf, 0xf0, 0xfe, 0xfe, 0x0c, 0x19, 0x4a, 0xf3,
13369         0xfe, 0xcc, 0xf0, 0xef,
13370         0x01, 0x76, 0x06, 0x24, 0x4d, 0x19, 0xfe, 0x12, 0x00, 0x37, 0x13, 0xfe,
13371         0x4e, 0x11, 0x2f, 0xfe,
13372         0x16, 0x0d, 0xfe, 0x9e, 0xf0, 0xfe, 0x2a, 0x0d, 0xfe, 0x01, 0x48, 0x1b,
13373         0x3c, 0x37, 0x88, 0xf5,
13374         0xd4, 0x29, 0xd5, 0x29, 0xd2, 0x29, 0xd3, 0x29, 0x37, 0xfe, 0x9c, 0x32,
13375         0x2f, 0xfe, 0x3e, 0x0d,
13376         0x2a, 0x3c, 0xae, 0xfe, 0x62, 0x0d, 0xaf, 0xa0, 0xd4, 0x9f, 0xd5, 0x9f,
13377         0xd2, 0x9f, 0xd3, 0x9f,
13378         0x05, 0x29, 0x01, 0x41, 0xfe, 0xd3, 0x10, 0x15, 0xfe, 0xe8, 0x00, 0xc4,
13379         0xc5, 0x75, 0xd7, 0x99,
13380         0xd8, 0x9c, 0xfe, 0x89, 0xf0, 0x29, 0x27, 0x25, 0xbe, 0xd7, 0x99, 0xd8,
13381         0x9c, 0x2f, 0xfe, 0x8c,
13382         0x0d, 0x16, 0x29, 0x27, 0x25, 0xbd, 0xfe, 0x01, 0x48, 0xa4, 0x19, 0xfe,
13383         0x42, 0x00, 0x05, 0x70,
13384         0x90, 0x07, 0xfe, 0x81, 0x49, 0x1b, 0xfe, 0x64, 0x0e, 0x01, 0x0c, 0x06,
13385         0x0d, 0xfe, 0x44, 0x13,
13386         0x19, 0x00, 0x2d, 0x0d, 0xfe, 0x54, 0x12, 0x2d, 0xfe, 0x28, 0x00, 0x2b,
13387         0xfe, 0xda, 0x0e, 0x0a,
13388         0x57, 0x01, 0x18, 0x09, 0x00, 0x36, 0x46, 0xfe, 0x28, 0x00, 0xfe, 0xfa,
13389         0x10, 0x01, 0xfe, 0xf4,
13390         0x1c, 0x01, 0xfe, 0x00, 0x1d, 0x0a, 0xba, 0x01, 0xfe, 0x58, 0x10, 0x40,
13391         0x15, 0x56, 0x01, 0x85,
13392         0x05, 0x35, 0x19, 0xfe, 0x44, 0x00, 0x2d, 0x0d, 0xf7, 0x46, 0x0d, 0xfe,
13393         0xcc, 0x10, 0x01, 0xa7,
13394         0x46, 0x0d, 0xfe, 0xc2, 0x10, 0x01, 0xa7, 0x0f, 0xfe, 0x19, 0x82, 0x04,
13395         0xfe, 0x99, 0x83, 0xfe,
13396         0xcc, 0x47, 0x0b, 0x0e, 0xfe, 0x34, 0x46, 0xa5, 0x46, 0x0d, 0x19, 0xfe,
13397         0x43, 0x00, 0xfe, 0xa2,
13398         0x10, 0x01, 0x0c, 0x61, 0x0d, 0x44, 0x01, 0xfe, 0xf4, 0x1c, 0x01, 0xfe,
13399         0x00, 0x1d, 0x40, 0x15,
13400         0x56, 0x01, 0x85, 0x7d, 0x0d, 0x40, 0x51, 0x01, 0xfe, 0x9e, 0x1e, 0x05,
13401         0xfe, 0x3a, 0x03, 0x01,
13402         0x0c, 0x06, 0x0d, 0x5d, 0x46, 0x0d, 0x19, 0x00, 0xfe, 0x62, 0x10, 0x01,
13403         0x76, 0x06, 0x12, 0xfe,
13404         0x5c, 0x12, 0x01, 0x0c, 0x06, 0x12, 0xfe, 0x52, 0x13, 0xfe, 0x1c, 0x1c,
13405         0xfe, 0x9d, 0xf0, 0xfe,
13406         0x8e, 0x0e, 0xfe, 0x1c, 0x1c, 0xfe, 0x9d, 0xf0, 0xfe, 0x94, 0x0e, 0x01,
13407         0x0c, 0x61, 0x12, 0x44,
13408         0xfe, 0x9f, 0x10, 0x19, 0xfe, 0x15, 0x00, 0xfe, 0x04, 0xe6, 0x0d, 0x4f,
13409         0xfe, 0x2e, 0x10, 0x19,
13410         0xfe, 0x13, 0x00, 0xfe, 0x10, 0x10, 0x19, 0xfe, 0x47, 0x00, 0xf1, 0x19,
13411         0xfe, 0x41, 0x00, 0xa2,
13412         0x19, 0xfe, 0x24, 0x00, 0x86, 0xc4, 0xc5, 0x75, 0x03, 0x81, 0x1e, 0x2b,
13413         0xea, 0x4f, 0xfe, 0x04,
13414         0xe6, 0x12, 0xfe, 0x9d, 0x41, 0xfe, 0x1c, 0x42, 0x40, 0x01, 0xf4, 0x05,
13415         0x35, 0xfe, 0x12, 0x1c,
13416         0x1f, 0x0d, 0x47, 0xb5, 0xc3, 0x1f, 0xfe, 0x31, 0x00, 0x47, 0xb8, 0x01,
13417         0xfe, 0xd4, 0x11, 0x05,
13418         0xe9, 0x51, 0xfe, 0x06, 0xec, 0xe0, 0xfe, 0x0e, 0x47, 0x46, 0x28, 0xfe,
13419         0xce, 0x45, 0x31, 0x51,
13420         0xfe, 0x06, 0xea, 0xe0, 0xfe, 0x47, 0x4b, 0x45, 0xfe, 0x75, 0x57, 0x03,
13421         0x67, 0xfe, 0x98, 0x56,
13422         0xfe, 0x38, 0x12, 0x0a, 0x5a, 0x01, 0x18, 0xfe, 0x44, 0x48, 0x60, 0x01,
13423         0x0c, 0x06, 0x28, 0xfe,
13424         0x18, 0x13, 0x0a, 0x57, 0x01, 0x18, 0x3e, 0xfe, 0x41, 0x58, 0x0a, 0xba,
13425         0xfe, 0xfa, 0x14, 0xfe,
13426         0x49, 0x54, 0xb0, 0xfe, 0x5e, 0x0f, 0x05, 0xfe, 0x3a, 0x03, 0x0a, 0x67,
13427         0xfe, 0xe0, 0x14, 0xfe,
13428         0x0e, 0x47, 0x46, 0x28, 0xfe, 0xce, 0x45, 0x31, 0x51, 0xfe, 0xce, 0x47,
13429         0xfe, 0xad, 0x13, 0x05,
13430         0x35, 0x21, 0x2c, 0x09, 0x1a, 0xfe, 0x98, 0x12, 0x26, 0x20, 0x96, 0x20,
13431         0xe7, 0xfe, 0x08, 0x1c,
13432         0xfe, 0x7c, 0x19, 0xfe, 0xfd, 0x19, 0xfe, 0x0a, 0x1c, 0x03, 0xe5, 0xfe,
13433         0x48, 0x55, 0xa5, 0x3b,
13434         0xfe, 0x62, 0x01, 0xfe, 0xc9, 0x55, 0x31, 0xfe, 0x74, 0x10, 0x01, 0xfe,
13435         0xf0, 0x1a, 0x03, 0xfe,
13436         0x38, 0x01, 0x3b, 0xfe, 0x3a, 0x01, 0x8e, 0xfe, 0x1e, 0x10, 0xfe, 0x02,
13437         0xec, 0xe7, 0x53, 0x00,
13438         0x36, 0xfe, 0x04, 0xec, 0x2c, 0x60, 0xfe, 0x05, 0xf6, 0xfe, 0x34, 0x01,
13439         0x01, 0xfe, 0x62, 0x1b,
13440         0x01, 0xfe, 0xce, 0x1e, 0xb2, 0x11, 0xfe, 0x18, 0x13, 0xca, 0xfe, 0x02,
13441         0xea, 0xe7, 0x53, 0x92,
13442         0xfe, 0xc3, 0x13, 0x1f, 0x12, 0x47, 0xb5, 0xc3, 0xfe, 0x2a, 0x10, 0x03,
13443         0xfe, 0x38, 0x01, 0x23,
13444         0xfe, 0xf0, 0xff, 0x10, 0xe5, 0x03, 0xfe, 0x3a, 0x01, 0x10, 0xfe, 0x62,
13445         0x01, 0x01, 0xfe, 0x1e,
13446         0x1e, 0x20, 0x2c, 0x15, 0x56, 0x01, 0xfe, 0x9e, 0x1e, 0x13, 0x07, 0x02,
13447         0x26, 0x02, 0x21, 0x96,
13448         0xc7, 0x20, 0x96, 0x09, 0x92, 0xfe, 0x79, 0x13, 0x1f, 0x1d, 0x47, 0xb5,
13449         0xc3, 0xfe, 0xe1, 0x10,
13450         0xcf, 0xfe, 0x03, 0xdc, 0xfe, 0x73, 0x57, 0xfe, 0x80, 0x5d, 0x02, 0xcf,
13451         0xfe, 0x03, 0xdc, 0xfe,
13452         0x5b, 0x57, 0xfe, 0x80, 0x5d, 0x02, 0xfe, 0x03, 0x57, 0xcf, 0x26, 0xfe,
13453         0x00, 0xcc, 0x02, 0xfe,
13454         0x03, 0x57, 0xcf, 0x89, 0x02, 0x01, 0x0c, 0x06, 0x4a, 0xfe, 0x4e, 0x13,
13455         0x0f, 0xfe, 0x1c, 0x80,
13456         0x04, 0xfe, 0x9c, 0x83, 0x33, 0x0b, 0x0e, 0x09, 0x07, 0xfe, 0x3a, 0x13,
13457         0x0f, 0xfe, 0x1e, 0x80,
13458         0x04, 0xfe, 0x9e, 0x83, 0x33, 0x0b, 0x0e, 0xfe, 0x2a, 0x13, 0x0f, 0xfe,
13459         0x1d, 0x80, 0x04, 0xfe,
13460         0x9d, 0x83, 0xfe, 0xf9, 0x13, 0x0e, 0xfe, 0x1c, 0x13, 0x01, 0xfe, 0xee,
13461         0x1e, 0xac, 0xfe, 0x14,
13462         0x13, 0x01, 0xfe, 0xfe, 0x1e, 0xfe, 0x81, 0x58, 0xfa, 0x01, 0xfe, 0x0e,
13463         0x1f, 0xfe, 0x30, 0xf4,
13464         0x0d, 0xfe, 0x3c, 0x50, 0xa2, 0x01, 0xfe, 0x92, 0x1b, 0x01, 0x43, 0x09,
13465         0x56, 0xfb, 0x01, 0xfe,
13466         0xc8, 0x1a, 0x01, 0x0c, 0x06, 0x28, 0xa4, 0x01, 0xfe, 0xf4, 0x1c, 0x01,
13467         0xfe, 0x00, 0x1d, 0x15,
13468         0xfe, 0xe9, 0x00, 0x01, 0x0c, 0x06, 0x4a, 0xfe, 0x4e, 0x13, 0x01, 0xfe,
13469         0x22, 0x1b, 0xfe, 0x1e,
13470         0x1c, 0x0f, 0xfe, 0x14, 0x90, 0x04, 0xfe, 0x94, 0x93, 0x3a, 0x0b, 0xfe,
13471         0x96, 0x90, 0x04, 0xfe,
13472         0x96, 0x93, 0x79, 0x0b, 0x0e, 0x10, 0xfe, 0x64, 0x01, 0x22, 0xfe, 0x66,
13473         0x01, 0x01, 0x0c, 0x06,
13474         0x65, 0xf9, 0x0f, 0xfe, 0x03, 0x80, 0x04, 0xfe, 0x83, 0x83, 0x33, 0x0b,
13475         0x0e, 0x77, 0xfe, 0x01,
13476         0xec, 0x2c, 0xfe, 0x80, 0x40, 0x20, 0x2c, 0x7a, 0x30, 0x15, 0xdf, 0x40,
13477         0x21, 0x2c, 0xfe, 0x00,
13478         0x40, 0x8d, 0x2c, 0x02, 0xfe, 0x08, 0x1c, 0x03, 0xfe, 0xac, 0x00, 0xfe,
13479         0x06, 0x58, 0x03, 0xfe,
13480         0xae, 0x00, 0xfe, 0x07, 0x58, 0x03, 0xfe, 0xb0, 0x00, 0xfe, 0x08, 0x58,
13481         0x03, 0xfe, 0xb2, 0x00,
13482         0xfe, 0x09, 0x58, 0xfe, 0x0a, 0x1c, 0x2e, 0x49, 0x20, 0xe0, 0x26, 0x10,
13483         0x66, 0x10, 0x55, 0x10,
13484         0x6f, 0x13, 0x57, 0x52, 0x4f, 0x1c, 0x28, 0xfe, 0x90, 0x4d, 0xfe, 0x91,
13485         0x54, 0x2b, 0xfe, 0x88,
13486         0x11, 0x46, 0x1a, 0x13, 0x5a, 0x52, 0x1c, 0x4a, 0xfe, 0x90, 0x4d, 0xfe,
13487         0x91, 0x54, 0x2b, 0xfe,
13488         0x9e, 0x11, 0x2e, 0x1a, 0x20, 0x2c, 0x90, 0x34, 0x60, 0x21, 0x2c, 0xfe,
13489         0x00, 0x40, 0x8d, 0x2c,
13490         0x15, 0xdf, 0xfe, 0x14, 0x56, 0xfe, 0xd6, 0xf0, 0xfe, 0xb2, 0x11, 0xfe,
13491         0x12, 0x1c, 0x75, 0xfe,
13492         0x14, 0x1c, 0xfe, 0x10, 0x1c, 0xfe, 0x18, 0x1c, 0x02, 0x51, 0xfe, 0x0c,
13493         0x14, 0xfe, 0x0e, 0x47,
13494         0xfe, 0x07, 0xe6, 0x28, 0xfe, 0xce, 0x47, 0xfe, 0xf5, 0x13, 0x02, 0x01,
13495         0xa7, 0x90, 0x34, 0x60,
13496         0xfe, 0x06, 0x80, 0xfe, 0x48, 0x47, 0xfe, 0x42, 0x13, 0xfe, 0x02, 0x80,
13497         0x09, 0x56, 0xfe, 0x34,
13498         0x13, 0x0a, 0x5a, 0x01, 0x18, 0xcb, 0xfe, 0x36, 0x12, 0xfe, 0x41, 0x48,
13499         0xfe, 0x45, 0x48, 0x01,
13500         0xfe, 0xb2, 0x16, 0xfe, 0x00, 0xcc, 0xcb, 0xfe, 0xf3, 0x13, 0x3f, 0x89,
13501         0x09, 0x1a, 0xa5, 0x0a,
13502         0x9d, 0x01, 0x18, 0xfe, 0x80, 0x5c, 0x01, 0x85, 0xf2, 0x09, 0x9b, 0xa4,
13503         0xfe, 0x14, 0x56, 0xfe,
13504         0xd6, 0xf0, 0xfe, 0xec, 0x11, 0x02, 0xfe, 0x44, 0x58, 0x77, 0xfe, 0x01,
13505         0xec, 0xb8, 0xfe, 0x9e,
13506         0x40, 0xfe, 0x9d, 0xe7, 0x00, 0xfe, 0x9c, 0xe7, 0x12, 0x8d, 0x30, 0x01,
13507         0xf4, 0xfe, 0xdd, 0x10,
13508         0x37, 0xd7, 0x99, 0xd8, 0x9c, 0x27, 0x25, 0xee, 0x09, 0x12, 0xfe, 0x48,
13509         0x12, 0x09, 0x0d, 0xfe,
13510         0x56, 0x12, 0x09, 0x1d, 0xfe, 0x30, 0x12, 0x09, 0xdd, 0x1b, 0xfe, 0xc4,
13511         0x13, 0x09, 0xfe, 0x23,
13512         0x00, 0x1b, 0xfe, 0xd0, 0x13, 0x09, 0x07, 0x1b, 0xfe, 0x34, 0x14, 0x09,
13513         0x24, 0xfe, 0x12, 0x12,
13514         0x09, 0x00, 0x1b, 0x29, 0x1f, 0xdd, 0x01, 0x42, 0xa1, 0x32, 0x01, 0x08,
13515         0xae, 0x41, 0x02, 0x32,
13516         0xfe, 0x62, 0x08, 0x0a, 0xe1, 0x01, 0xfe, 0x58, 0x10, 0x15, 0x9b, 0x05,
13517         0x35, 0x32, 0x01, 0x43,
13518         0x09, 0xbb, 0xfe, 0xd7, 0x13, 0x91, 0x4b, 0x7e, 0x4c, 0x8e, 0xfe, 0x80,
13519         0x13, 0x01, 0x0c, 0x06,
13520         0x54, 0xfe, 0x72, 0x12, 0xdb, 0x64, 0xdc, 0x34, 0xfe, 0x44, 0x55, 0xfe,
13521         0xe5, 0x55, 0xb0, 0xfe,
13522         0x4a, 0x13, 0x21, 0x6e, 0xfe, 0x26, 0x13, 0x03, 0x97, 0x3b, 0x98, 0x8e,
13523         0xfe, 0xb6, 0x0e, 0x10,
13524         0x6a, 0x22, 0x6b, 0x26, 0x10, 0x97, 0x10, 0x98, 0x01, 0xc2, 0x2e, 0x49,
13525         0x88, 0x20, 0x6e, 0x01,
13526         0xfe, 0x6a, 0x16, 0xdb, 0x64, 0xdc, 0x34, 0xfe, 0x04, 0x55, 0xfe, 0xa5,
13527         0x55, 0xfe, 0x04, 0xfa,
13528         0x64, 0xfe, 0x05, 0xfa, 0x34, 0xfe, 0x8f, 0x10, 0x03, 0x6c, 0x3b, 0x6d,
13529         0xfe, 0x40, 0x56, 0xfe,
13530         0xe1, 0x56, 0x10, 0x6c, 0x22, 0x6d, 0x71, 0xdb, 0x64, 0xdc, 0x34, 0xfe,
13531         0x44, 0x55, 0xfe, 0xe5,
13532         0x55, 0x03, 0x68, 0x3b, 0x69, 0xfe, 0x00, 0x56, 0xfe, 0xa1, 0x56, 0x10,
13533         0x68, 0x22, 0x69, 0x01,
13534         0x0c, 0x06, 0x54, 0xf9, 0x21, 0x6e, 0xfe, 0x1f, 0x40, 0x03, 0x6a, 0x3b,
13535         0x6b, 0xfe, 0x2c, 0x50,
13536         0xfe, 0xae, 0x50, 0x03, 0x6c, 0x3b, 0x6d, 0xfe, 0x44, 0x50, 0xfe, 0xc6,
13537         0x50, 0x03, 0x68, 0x3b,
13538         0x69, 0xfe, 0x08, 0x50, 0xfe, 0x8a, 0x50, 0x03, 0x4b, 0x3b, 0x4c, 0xfe,
13539         0x40, 0x50, 0xfe, 0xc2,
13540         0x50, 0x05, 0x73, 0x2e, 0x07, 0x20, 0x9e, 0x05, 0x72, 0x32, 0x01, 0x08,
13541         0x16, 0x3d, 0x27, 0x25,
13542         0xee, 0x09, 0x07, 0x2b, 0x3d, 0x01, 0x43, 0x09, 0xbb, 0x2b, 0x72, 0x01,
13543         0xa6, 0x23, 0x3f, 0x1b,
13544         0x3d, 0x01, 0x0c, 0x06, 0x0d, 0xfe, 0x1e, 0x13, 0x91, 0x4b, 0x7e, 0x4c,
13545         0xfe, 0x0a, 0x55, 0x31,
13546         0xfe, 0x8b, 0x55, 0xd9, 0x4b, 0xda, 0x4c, 0xfe, 0x0c, 0x51, 0xfe, 0x8e,
13547         0x51, 0x05, 0x72, 0x01,
13548         0xfe, 0x8e, 0x1e, 0xca, 0xfe, 0x19, 0x41, 0x05, 0x72, 0x32, 0x01, 0x08,
13549         0x2a, 0x3c, 0x16, 0xc0,
13550         0x27, 0x25, 0xbe, 0x2d, 0x1d, 0xc0, 0x2d, 0x0d, 0x83, 0x2d, 0x7f, 0x1b,
13551         0xfe, 0x66, 0x15, 0x05,
13552         0x3d, 0x01, 0x08, 0x2a, 0x3c, 0x16, 0xc0, 0x27, 0x25, 0xbd, 0x09, 0x1d,
13553         0x2b, 0x3d, 0x01, 0x08,
13554         0x16, 0xc0, 0x27, 0x25, 0xfe, 0xe8, 0x09, 0xfe, 0xc2, 0x49, 0x50, 0x03,
13555         0xb6, 0x1e, 0x83, 0x01,
13556         0x38, 0x06, 0x24, 0x31, 0xa1, 0xfe, 0xbb, 0x45, 0x2d, 0x00, 0xa4, 0x46,
13557         0x07, 0x90, 0x3f, 0x01,
13558         0xfe, 0xf8, 0x15, 0x01, 0xa6, 0x86, 0xfe, 0x4b, 0x45, 0xfe, 0x20, 0x13,
13559         0x01, 0x43, 0x09, 0x82,
13560         0xfe, 0x16, 0x13, 0x03, 0x9a, 0x1e, 0x5d, 0x03, 0x55, 0x1e, 0x31, 0x5e,
13561         0x05, 0x72, 0xfe, 0xc0,
13562         0x5d, 0x01, 0xa7, 0xfe, 0x03, 0x17, 0x03, 0x66, 0x8a, 0x10, 0x66, 0x5e,
13563         0x32, 0x01, 0x08, 0x17,
13564         0x73, 0x01, 0xfe, 0x56, 0x19, 0x05, 0x73, 0x01, 0x08, 0x2a, 0x3c, 0x16,
13565         0x3d, 0x27, 0x25, 0xbd,
13566         0x09, 0x07, 0x2b, 0x3d, 0x01, 0xfe, 0xbe, 0x16, 0xfe, 0x42, 0x58, 0xfe,
13567         0xe8, 0x14, 0x01, 0xa6,
13568         0x86, 0xfe, 0x4a, 0xf4, 0x0d, 0x1b, 0x3d, 0xfe, 0x4a, 0xf4, 0x07, 0xfe,
13569         0x0e, 0x12, 0x01, 0x43,
13570         0x09, 0x82, 0x4e, 0x05, 0x72, 0x03, 0x55, 0x8a, 0x10, 0x55, 0x5e, 0x32,
13571         0x01, 0x08, 0x17, 0x73,
13572         0x01, 0xfe, 0x84, 0x19, 0x05, 0x73, 0x01, 0x08, 0x2a, 0x3c, 0x16, 0x3d,
13573         0x27, 0x25, 0xbd, 0x09,
13574         0x12, 0x2b, 0x3d, 0x01, 0xfe, 0xe8, 0x17, 0x8b, 0xfe, 0xaa, 0x14, 0xfe,
13575         0xb6, 0x14, 0x86, 0xa8,
13576         0xb2, 0x0d, 0x1b, 0x3d, 0xb2, 0x07, 0xfe, 0x0e, 0x12, 0x01, 0x43, 0x09,
13577         0x82, 0x4e, 0x05, 0x72,
13578         0x03, 0x6f, 0x8a, 0x10, 0x6f, 0x5e, 0x32, 0x01, 0x08, 0x17, 0x73, 0x01,
13579         0xfe, 0xc0, 0x19, 0x05,
13580         0x73, 0x13, 0x07, 0x2f, 0xfe, 0xcc, 0x15, 0x17, 0xfe, 0xe2, 0x15, 0x5f,
13581         0xcc, 0x01, 0x08, 0x26,
13582         0x5f, 0x02, 0x8f, 0xfe, 0xde, 0x15, 0x2a, 0xfe, 0xde, 0x15, 0x16, 0xfe,
13583         0xcc, 0x15, 0x5e, 0x32,
13584         0x01, 0x08, 0xfe, 0xd5, 0x10, 0x13, 0x58, 0xff, 0x02, 0x00, 0x57, 0x52,
13585         0xad, 0x23, 0xfe, 0xff,
13586         0x7f, 0xfe, 0x30, 0x56, 0xfe, 0x00, 0x5c, 0x02, 0x13, 0x58, 0xff, 0x02,
13587         0x00, 0x57, 0x52, 0xad,
13588         0x23, 0x3f, 0xfe, 0x30, 0x56, 0xfe, 0x00, 0x5c, 0x02, 0x13, 0x58, 0xff,
13589         0x02, 0x00, 0x57, 0x52,
13590         0xad, 0x02, 0x13, 0x58, 0xff, 0x02, 0x00, 0x57, 0x52, 0xfe, 0x00, 0x5e,
13591         0x02, 0x13, 0x58, 0xff,
13592         0x02, 0x00, 0x57, 0x52, 0xad, 0xfe, 0x0b, 0x58, 0x02, 0x0a, 0x66, 0x01,
13593         0x5c, 0x0a, 0x55, 0x01,
13594         0x5c, 0x0a, 0x6f, 0x01, 0x5c, 0x02, 0x01, 0xfe, 0x1e, 0x1f, 0x23, 0x1a,
13595         0xff, 0x03, 0x00, 0x54,
13596         0xfe, 0x00, 0xf4, 0x24, 0x52, 0x0f, 0xfe, 0x00, 0x7c, 0x04, 0xfe, 0x07,
13597         0x7c, 0x3a, 0x0b, 0x0e,
13598         0xfe, 0x00, 0x71, 0xfe, 0xf9, 0x18, 0xfe, 0x7a, 0x19, 0xfe, 0xfb, 0x19,
13599         0xfe, 0x1a, 0xf7, 0x00,
13600         0xfe, 0x1b, 0xf7, 0x00, 0x7a, 0x30, 0x10, 0x68, 0x22, 0x69, 0xd9, 0x6c,
13601         0xda, 0x6d, 0x02, 0xfe,
13602         0x62, 0x08, 0xfe, 0x82, 0x4a, 0xfe, 0xe1, 0x1a, 0xfe, 0x83, 0x5a, 0x77,
13603         0x02, 0x01, 0xc6, 0xfe,
13604         0x42, 0x48, 0x4f, 0x50, 0x45, 0x01, 0x08, 0x16, 0xfe, 0xe0, 0x17, 0x27,
13605         0x25, 0xbe, 0x01, 0x08,
13606         0x16, 0xfe, 0xe0, 0x17, 0x27, 0x25, 0xfe, 0xe8, 0x0a, 0xfe, 0xc1, 0x59,
13607         0x03, 0x9a, 0x1e, 0xfe,
13608         0xda, 0x12, 0x01, 0x38, 0x06, 0x12, 0xfe, 0xd0, 0x13, 0x26, 0x53, 0x12,
13609         0x48, 0xfe, 0x08, 0x17,
13610         0xd1, 0x12, 0x53, 0x12, 0xfe, 0x1e, 0x13, 0x2d, 0xb4, 0x7b, 0xfe, 0x26,
13611         0x17, 0x4d, 0x13, 0x07,
13612         0x1c, 0xb4, 0x90, 0x04, 0xfe, 0x78, 0x10, 0xff, 0x02, 0x83, 0x55, 0xf1,
13613         0xff, 0x02, 0x83, 0x55,
13614         0x53, 0x1d, 0xfe, 0x12, 0x13, 0xd6, 0xfe, 0x30, 0x00, 0xb0, 0xfe, 0x80,
13615         0x17, 0x1c, 0x63, 0x13,
13616         0x07, 0xfe, 0x56, 0x10, 0x53, 0x0d, 0xfe, 0x16, 0x13, 0xd6, 0xfe, 0x64,
13617         0x00, 0xb0, 0xfe, 0x80,
13618         0x17, 0x0a, 0xfe, 0x64, 0x00, 0x1c, 0x94, 0x13, 0x07, 0xfe, 0x28, 0x10,
13619         0x53, 0x07, 0xfe, 0x60,
13620         0x13, 0xd6, 0xfe, 0xc8, 0x00, 0xb0, 0xfe, 0x80, 0x17, 0x0a, 0xfe, 0xc8,
13621         0x00, 0x1c, 0x95, 0x13,
13622         0x07, 0x71, 0xd6, 0xfe, 0x90, 0x01, 0x48, 0xfe, 0x8c, 0x17, 0x45, 0xf3,
13623         0xfe, 0x43, 0xf4, 0x96,
13624         0xfe, 0x56, 0xf0, 0xfe, 0x9e, 0x17, 0xfe, 0x04, 0xf4, 0x58, 0xfe, 0x43,
13625         0xf4, 0x94, 0xf6, 0x8b,
13626         0x01, 0xfe, 0x24, 0x16, 0x23, 0x3f, 0xfc, 0xa8, 0x8c, 0x49, 0x48, 0xfe,
13627         0xda, 0x17, 0x62, 0x49,
13628         0xfe, 0x1c, 0x10, 0xa8, 0x8c, 0x80, 0x48, 0xfe, 0xda, 0x17, 0x62, 0x80,
13629         0x71, 0x50, 0x26, 0xfe,
13630         0x4d, 0xf4, 0x00, 0xf7, 0x45, 0x13, 0x07, 0xfe, 0xb4, 0x56, 0xfe, 0xc3,
13631         0x58, 0x02, 0x50, 0x13,
13632         0x0d, 0x02, 0x50, 0x3e, 0x78, 0x4f, 0x45, 0x01, 0x08, 0x16, 0xa9, 0x27,
13633         0x25, 0xbe, 0xfe, 0x03,
13634         0xea, 0xfe, 0x7e, 0x01, 0x01, 0x08, 0x16, 0xa9, 0x27, 0x25, 0xfe, 0xe9,
13635         0x0a, 0x01, 0x08, 0x16,
13636         0xa9, 0x27, 0x25, 0xfe, 0xe9, 0x0a, 0xfe, 0x05, 0xea, 0xfe, 0x7f, 0x01,
13637         0x01, 0x08, 0x16, 0xa9,
13638         0x27, 0x25, 0xfe, 0x69, 0x09, 0xfe, 0x02, 0xea, 0xfe, 0x80, 0x01, 0x01,
13639         0x08, 0x16, 0xa9, 0x27,
13640         0x25, 0xfe, 0xe8, 0x08, 0x47, 0xfe, 0x81, 0x01, 0x03, 0xb6, 0x1e, 0x83,
13641         0x01, 0x38, 0x06, 0x24,
13642         0x31, 0xa2, 0x78, 0xf2, 0x53, 0x07, 0x36, 0xfe, 0x34, 0xf4, 0x3f, 0xa1,
13643         0x78, 0x03, 0x9a, 0x1e,
13644         0x83, 0x01, 0x38, 0x06, 0x12, 0x31, 0xf0, 0x4f, 0x45, 0xfe, 0x90, 0x10,
13645         0xfe, 0x40, 0x5a, 0x23,
13646         0x3f, 0xfb, 0x8c, 0x49, 0x48, 0xfe, 0xaa, 0x18, 0x62, 0x49, 0x71, 0x8c,
13647         0x80, 0x48, 0xfe, 0xaa,
13648         0x18, 0x62, 0x80, 0xfe, 0xb4, 0x56, 0xfe, 0x40, 0x5d, 0x01, 0xc6, 0x01,
13649         0xfe, 0xac, 0x1d, 0xfe,
13650         0x02, 0x17, 0xfe, 0xc8, 0x45, 0xfe, 0x5a, 0xf0, 0xfe, 0xc0, 0x18, 0xfe,
13651         0x43, 0x48, 0x2d, 0x93,
13652         0x36, 0xfe, 0x34, 0xf4, 0xfe, 0x00, 0x11, 0xfe, 0x40, 0x10, 0x2d, 0xb4,
13653         0x36, 0xfe, 0x34, 0xf4,
13654         0x04, 0xfe, 0x34, 0x10, 0x2d, 0xfe, 0x0b, 0x00, 0x36, 0x46, 0x63, 0xfe,
13655         0x28, 0x10, 0xfe, 0xc0,
13656         0x49, 0xff, 0x02, 0x00, 0x54, 0xb2, 0xfe, 0x90, 0x01, 0x48, 0xfe, 0xfa,
13657         0x18, 0x45, 0xfe, 0x1c,
13658         0xf4, 0x3f, 0xf3, 0xfe, 0x40, 0xf4, 0x96, 0xfe, 0x56, 0xf0, 0xfe, 0x0c,
13659         0x19, 0xfe, 0x04, 0xf4,
13660         0x58, 0xfe, 0x40, 0xf4, 0x94, 0xf6, 0x3e, 0x2d, 0x93, 0x4e, 0xd0, 0x0d,
13661         0x21, 0xfe, 0x7f, 0x01,
13662         0xfe, 0xc8, 0x46, 0xfe, 0x24, 0x13, 0x8c, 0x00, 0x5d, 0x26, 0x21, 0xfe,
13663         0x7e, 0x01, 0xfe, 0xc8,
13664         0x45, 0xfe, 0x14, 0x13, 0x21, 0xfe, 0x80, 0x01, 0xfe, 0x48, 0x45, 0xfa,
13665         0x21, 0xfe, 0x81, 0x01,
13666         0xfe, 0xc8, 0x44, 0x4e, 0x26, 0x02, 0x13, 0x07, 0x02, 0x78, 0x45, 0x50,
13667         0x13, 0x0d, 0x02, 0x14,
13668         0x07, 0x01, 0x08, 0x17, 0xfe, 0x82, 0x19, 0x14, 0x0d, 0x01, 0x08, 0x17,
13669         0xfe, 0x82, 0x19, 0x14,
13670         0x1d, 0x01, 0x08, 0x17, 0xfe, 0x82, 0x19, 0x5f, 0xfe, 0x89, 0x49, 0x01,
13671         0x08, 0x02, 0x14, 0x07,
13672         0x01, 0x08, 0x17, 0xc1, 0x14, 0x1d, 0x01, 0x08, 0x17, 0xc1, 0x14, 0x07,
13673         0x01, 0x08, 0x17, 0xc1,
13674         0xfe, 0x89, 0x49, 0x01, 0x08, 0x17, 0xc1, 0x5f, 0xfe, 0x89, 0x4a, 0x01,
13675         0x08, 0x02, 0x50, 0x02,
13676         0x14, 0x07, 0x01, 0x08, 0x17, 0x74, 0x14, 0x7f, 0x01, 0x08, 0x17, 0x74,
13677         0x14, 0x12, 0x01, 0x08,
13678         0x17, 0x74, 0xfe, 0x89, 0x49, 0x01, 0x08, 0x17, 0x74, 0x14, 0x00, 0x01,
13679         0x08, 0x17, 0x74, 0xfe,
13680         0x89, 0x4a, 0x01, 0x08, 0x17, 0x74, 0xfe, 0x09, 0x49, 0x01, 0x08, 0x17,
13681         0x74, 0x5f, 0xcc, 0x01,
13682         0x08, 0x02, 0x21, 0xe4, 0x09, 0x07, 0xfe, 0x4c, 0x13, 0xc8, 0x20, 0xe4,
13683         0xfe, 0x49, 0xf4, 0x00,
13684         0x4d, 0x5f, 0xa1, 0x5e, 0xfe, 0x01, 0xec, 0xfe, 0x27, 0x01, 0xcc, 0xff,
13685         0x02, 0x00, 0x10, 0x2f,
13686         0xfe, 0x3e, 0x1a, 0x01, 0x43, 0x09, 0xfe, 0xe3, 0x00, 0xfe, 0x22, 0x13,
13687         0x16, 0xfe, 0x64, 0x1a,
13688         0x26, 0x20, 0x9e, 0x01, 0x41, 0x21, 0x9e, 0x09, 0x07, 0x5d, 0x01, 0x0c,
13689         0x61, 0x07, 0x44, 0x02,
13690         0x0a, 0x5a, 0x01, 0x18, 0xfe, 0x00, 0x40, 0xaa, 0x09, 0x1a, 0xfe, 0x12,
13691         0x13, 0x0a, 0x9d, 0x01,
13692         0x18, 0xaa, 0x0a, 0x67, 0x01, 0xa3, 0x02, 0x0a, 0x9d, 0x01, 0x18, 0xaa,
13693         0xfe, 0x80, 0xe7, 0x1a,
13694         0x09, 0x1a, 0x5d, 0xfe, 0x45, 0x58, 0x01, 0xfe, 0xb2, 0x16, 0xaa, 0x02,
13695         0x0a, 0x5a, 0x01, 0x18,
13696         0xaa, 0x0a, 0x67, 0x01, 0xa3, 0x02, 0x0a, 0x5a, 0x01, 0x18, 0x01, 0xfe,
13697         0x7e, 0x1e, 0xfe, 0x80,
13698         0x4c, 0xfe, 0x49, 0xe4, 0x1a, 0xfe, 0x12, 0x13, 0x0a, 0x9d, 0x01, 0x18,
13699         0xfe, 0x80, 0x4c, 0x0a,
13700         0x67, 0x01, 0x5c, 0x02, 0x1c, 0x1a, 0x87, 0x7c, 0xe5, 0xfe, 0x18, 0xdf,
13701         0xfe, 0x19, 0xde, 0xfe,
13702         0x24, 0x1c, 0xfe, 0x1d, 0xf7, 0x28, 0xb1, 0xfe, 0x04, 0x1b, 0x01, 0xfe,
13703         0x2a, 0x1c, 0xfa, 0xb3,
13704         0x28, 0x7c, 0xfe, 0x2c, 0x01, 0xfe, 0x2f, 0x19, 0x02, 0xc9, 0x2b, 0xfe,
13705         0xf4, 0x1a, 0xfe, 0xfa,
13706         0x10, 0x1c, 0x1a, 0x87, 0x03, 0xfe, 0x64, 0x01, 0xfe, 0x00, 0xf4, 0x24,
13707         0xfe, 0x18, 0x58, 0x03,
13708         0xfe, 0x66, 0x01, 0xfe, 0x19, 0x58, 0xb3, 0x24, 0x01, 0xfe, 0x0e, 0x1f,
13709         0xfe, 0x30, 0xf4, 0x07,
13710         0xfe, 0x3c, 0x50, 0x7c, 0xfe, 0x38, 0x00, 0xfe, 0x0f, 0x79, 0xfe, 0x1c,
13711         0xf7, 0x24, 0xb1, 0xfe,
13712         0x50, 0x1b, 0xfe, 0xd4, 0x14, 0x31, 0x02, 0xc9, 0x2b, 0xfe, 0x26, 0x1b,
13713         0xfe, 0xba, 0x10, 0x1c,
13714         0x1a, 0x87, 0xfe, 0x83, 0x5a, 0xfe, 0x18, 0xdf, 0xfe, 0x19, 0xde, 0xfe,
13715         0x1d, 0xf7, 0x54, 0xb1,
13716         0xfe, 0x72, 0x1b, 0xfe, 0xb2, 0x14, 0xfc, 0xb3, 0x54, 0x7c, 0x12, 0xfe,
13717         0xaf, 0x19, 0xfe, 0x98,
13718         0xe7, 0x00, 0x02, 0xc9, 0x2b, 0xfe, 0x66, 0x1b, 0xfe, 0x8a, 0x10, 0x1c,
13719         0x1a, 0x87, 0x8b, 0x0f,
13720         0xfe, 0x30, 0x90, 0x04, 0xfe, 0xb0, 0x93, 0x3a, 0x0b, 0xfe, 0x18, 0x58,
13721         0xfe, 0x32, 0x90, 0x04,
13722         0xfe, 0xb2, 0x93, 0x3a, 0x0b, 0xfe, 0x19, 0x58, 0x0e, 0xa8, 0xb3, 0x4a,
13723         0x7c, 0x12, 0xfe, 0x0f,
13724         0x79, 0xfe, 0x1c, 0xf7, 0x4a, 0xb1, 0xfe, 0xc6, 0x1b, 0xfe, 0x5e, 0x14,
13725         0x31, 0x02, 0xc9, 0x2b,
13726         0xfe, 0x96, 0x1b, 0x5c, 0xfe, 0x02, 0xf6, 0x1a, 0x87, 0xfe, 0x18, 0xfe,
13727         0x6a, 0xfe, 0x19, 0xfe,
13728         0x6b, 0x01, 0xfe, 0x1e, 0x1f, 0xfe, 0x1d, 0xf7, 0x65, 0xb1, 0xfe, 0xee,
13729         0x1b, 0xfe, 0x36, 0x14,
13730         0xfe, 0x1c, 0x13, 0xb3, 0x65, 0x3e, 0xfe, 0x83, 0x58, 0xfe, 0xaf, 0x19,
13731         0xfe, 0x80, 0xe7, 0x1a,
13732         0xfe, 0x81, 0xe7, 0x1a, 0x15, 0xfe, 0xdd, 0x00, 0x7a, 0x30, 0x02, 0x7a,
13733         0x30, 0xfe, 0x12, 0x45,
13734         0x2b, 0xfe, 0xdc, 0x1b, 0x1f, 0x07, 0x47, 0xb5, 0xc3, 0x05, 0x35, 0xfe,
13735         0x39, 0xf0, 0x75, 0x26,
13736         0x02, 0xfe, 0x7e, 0x18, 0x23, 0x1d, 0x36, 0x13, 0x11, 0x02, 0x87, 0x03,
13737         0xe3, 0x23, 0x07, 0xfe,
13738         0xef, 0x12, 0xfe, 0xe1, 0x10, 0x90, 0x34, 0x60, 0xfe, 0x02, 0x80, 0x09,
13739         0x56, 0xfe, 0x3c, 0x13,
13740         0xfe, 0x82, 0x14, 0xfe, 0x42, 0x13, 0x51, 0xfe, 0x06, 0x83, 0x0a, 0x5a,
13741         0x01, 0x18, 0xcb, 0xfe,
13742         0x3e, 0x12, 0xfe, 0x41, 0x48, 0xfe, 0x45, 0x48, 0x01, 0xfe, 0xb2, 0x16,
13743         0xfe, 0x00, 0xcc, 0xcb,
13744         0xfe, 0xf3, 0x13, 0x3f, 0x89, 0x09, 0x1a, 0xa5, 0x0a, 0x9d, 0x01, 0x18,
13745         0xfe, 0x80, 0x4c, 0x01,
13746         0x85, 0xfe, 0x16, 0x10, 0x09, 0x9b, 0x4e, 0xfe, 0x40, 0x14, 0xfe, 0x24,
13747         0x12, 0xfe, 0x14, 0x56,
13748         0xfe, 0xd6, 0xf0, 0xfe, 0x52, 0x1c, 0x1c, 0x0d, 0x02, 0xfe, 0x9c, 0xe7,
13749         0x0d, 0x19, 0xfe, 0x15,
13750         0x00, 0x40, 0x8d, 0x30, 0x01, 0xf4, 0x1c, 0x07, 0x02, 0x51, 0xfe, 0x06,
13751         0x83, 0xfe, 0x18, 0x80,
13752         0x61, 0x28, 0x44, 0x15, 0x56, 0x01, 0x85, 0x1c, 0x07, 0x02, 0xfe, 0x38,
13753         0x90, 0xfe, 0xba, 0x90,
13754         0x91, 0xde, 0x7e, 0xdf, 0xfe, 0x48, 0x55, 0x31, 0xfe, 0xc9, 0x55, 0x02,
13755         0x21, 0xb9, 0x88, 0x20,
13756         0xb9, 0x02, 0x0a, 0xba, 0x01, 0x18, 0xfe, 0x41, 0x48, 0x0a, 0x57, 0x01,
13757         0x18, 0xfe, 0x49, 0x44,
13758         0x1b, 0xfe, 0x1e, 0x1d, 0x88, 0x89, 0x02, 0x0a, 0x5a, 0x01, 0x18, 0x09,
13759         0x1a, 0xa4, 0x0a, 0x67,
13760         0x01, 0xa3, 0x0a, 0x57, 0x01, 0x18, 0x88, 0x89, 0x02, 0xfe, 0x4e, 0xe4,
13761         0x1d, 0x7b, 0xfe, 0x52,
13762         0x1d, 0x03, 0xfe, 0x90, 0x00, 0xfe, 0x3a, 0x45, 0xfe, 0x2c, 0x10, 0xfe,
13763         0x4e, 0xe4, 0xdd, 0x7b,
13764         0xfe, 0x64, 0x1d, 0x03, 0xfe, 0x92, 0x00, 0xd1, 0x12, 0xfe, 0x1a, 0x10,
13765         0xfe, 0x4e, 0xe4, 0xfe,
13766         0x0b, 0x00, 0x7b, 0xfe, 0x76, 0x1d, 0x03, 0xfe, 0x94, 0x00, 0xd1, 0x24,
13767         0xfe, 0x08, 0x10, 0x03,
13768         0xfe, 0x96, 0x00, 0xd1, 0x63, 0xfe, 0x4e, 0x45, 0x83, 0xca, 0xff, 0x04,
13769         0x68, 0x54, 0xfe, 0xf1,
13770         0x10, 0x23, 0x49, 0xfe, 0x08, 0x1c, 0xfe, 0x67, 0x19, 0xfe, 0x0a, 0x1c,
13771         0xfe, 0x1a, 0xf4, 0xfe,
13772         0x00, 0x04, 0x83, 0xb2, 0x1d, 0x48, 0xfe, 0xaa, 0x1d, 0x13, 0x1d, 0x02,
13773         0x09, 0x92, 0xfe, 0x5a,
13774         0xf0, 0xfe, 0xba, 0x1d, 0x2e, 0x93, 0xfe, 0x34, 0x10, 0x09, 0x12, 0xfe,
13775         0x5a, 0xf0, 0xfe, 0xc8,
13776         0x1d, 0x2e, 0xb4, 0xfe, 0x26, 0x10, 0x09, 0x1d, 0x36, 0x2e, 0x63, 0xfe,
13777         0x1a, 0x10, 0x09, 0x0d,
13778         0x36, 0x2e, 0x94, 0xf2, 0x09, 0x07, 0x36, 0x2e, 0x95, 0xa1, 0xc8, 0x02,
13779         0x1f, 0x93, 0x01, 0x42,
13780         0xfe, 0x04, 0xfe, 0x99, 0x03, 0x9c, 0x8b, 0x02, 0x2a, 0xfe, 0x1c, 0x1e,
13781         0xfe, 0x14, 0xf0, 0x08,
13782         0x2f, 0xfe, 0x0c, 0x1e, 0x2a, 0xfe, 0x1c, 0x1e, 0x8f, 0xfe, 0x1c, 0x1e,
13783         0xfe, 0x82, 0xf0, 0xfe,
13784         0x10, 0x1e, 0x02, 0x0f, 0x3f, 0x04, 0xfe, 0x80, 0x83, 0x33, 0x0b, 0x0e,
13785         0x02, 0x0f, 0xfe, 0x18,
13786         0x80, 0x04, 0xfe, 0x98, 0x83, 0x33, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x02,
13787         0x80, 0x04, 0xfe, 0x82,
13788         0x83, 0x33, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x06, 0x80, 0x04, 0xfe, 0x86,
13789         0x83, 0x33, 0x0b, 0x0e,
13790         0x02, 0x0f, 0xfe, 0x1b, 0x80, 0x04, 0xfe, 0x9b, 0x83, 0x33, 0x0b, 0x0e,
13791         0x02, 0x0f, 0xfe, 0x04,
13792         0x80, 0x04, 0xfe, 0x84, 0x83, 0x33, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x80,
13793         0x80, 0x04, 0xfe, 0x80,
13794         0x83, 0xfe, 0xc9, 0x47, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x19, 0x81, 0x04,
13795         0xfe, 0x99, 0x83, 0xfe,
13796         0xca, 0x47, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x06, 0x83, 0x04, 0xfe, 0x86,
13797         0x83, 0xfe, 0xce, 0x47,
13798         0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x2c, 0x90, 0x04, 0xfe, 0xac, 0x93, 0x3a,
13799         0x0b, 0x0e, 0x02, 0x0f,
13800         0xfe, 0xae, 0x90, 0x04, 0xfe, 0xae, 0x93, 0x79, 0x0b, 0x0e, 0x02, 0x0f,
13801         0xfe, 0x08, 0x90, 0x04,
13802         0xfe, 0x88, 0x93, 0x3a, 0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x8a, 0x90, 0x04,
13803         0xfe, 0x8a, 0x93, 0x79,
13804         0x0b, 0x0e, 0x02, 0x0f, 0xfe, 0x0c, 0x90, 0x04, 0xfe, 0x8c, 0x93, 0x3a,
13805         0x0b, 0x0e, 0x02, 0x0f,
13806         0xfe, 0x8e, 0x90, 0x04, 0xfe, 0x8e, 0x93, 0x79, 0x0b, 0x0e, 0x02, 0x0f,
13807         0xfe, 0x3c, 0x90, 0x04,
13808         0xfe, 0xbc, 0x93, 0x3a, 0x0b, 0x0e, 0x02, 0x8b, 0x0f, 0xfe, 0x03, 0x80,
13809         0x04, 0xfe, 0x83, 0x83,
13810         0x33, 0x0b, 0x77, 0x0e, 0xa8, 0x02, 0xff, 0x66, 0x00, 0x00,
13811 };
13812
13813 static unsigned short _adv_asc38C1600_size = sizeof(_adv_asc38C1600_buf);       /* 0x1673 */
13814 static ADV_DCNT _adv_asc38C1600_chksum = 0x0604EF77UL;  /* Expanded little-endian checksum. */
13815
13816 /* a_init.c */
13817 /*
13818  * EEPROM Configuration.
13819  *
13820  * All drivers should use this structure to set the default EEPROM
13821  * configuration. The BIOS now uses this structure when it is built.
13822  * Additional structure information can be found in a_condor.h where
13823  * the structure is defined.
13824  *
13825  * The *_Field_IsChar structs are needed to correct for endianness.
13826  * These values are read from the board 16 bits at a time directly
13827  * into the structs. Because some fields are char, the values will be
13828  * in the wrong order. The *_Field_IsChar tells when to flip the
13829  * bytes. Data read and written to PCI memory is automatically swapped
13830  * on big-endian platforms so char fields read as words are actually being
13831  * unswapped on big-endian platforms.
13832  */
13833 static ADVEEP_3550_CONFIG Default_3550_EEPROM_Config __initdata = {
13834         ADV_EEPROM_BIOS_ENABLE, /* cfg_lsw */
13835         0x0000,                 /* cfg_msw */
13836         0xFFFF,                 /* disc_enable */
13837         0xFFFF,                 /* wdtr_able */
13838         0xFFFF,                 /* sdtr_able */
13839         0xFFFF,                 /* start_motor */
13840         0xFFFF,                 /* tagqng_able */
13841         0xFFFF,                 /* bios_scan */
13842         0,                      /* scam_tolerant */
13843         7,                      /* adapter_scsi_id */
13844         0,                      /* bios_boot_delay */
13845         3,                      /* scsi_reset_delay */
13846         0,                      /* bios_id_lun */
13847         0,                      /* termination */
13848         0,                      /* reserved1 */
13849         0xFFE7,                 /* bios_ctrl */
13850         0xFFFF,                 /* ultra_able */
13851         0,                      /* reserved2 */
13852         ASC_DEF_MAX_HOST_QNG,   /* max_host_qng */
13853         ASC_DEF_MAX_DVC_QNG,    /* max_dvc_qng */
13854         0,                      /* dvc_cntl */
13855         0,                      /* bug_fix */
13856         0,                      /* serial_number_word1 */
13857         0,                      /* serial_number_word2 */
13858         0,                      /* serial_number_word3 */
13859         0,                      /* check_sum */
13860         {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
13861         ,                       /* oem_name[16] */
13862         0,                      /* dvc_err_code */
13863         0,                      /* adv_err_code */
13864         0,                      /* adv_err_addr */
13865         0,                      /* saved_dvc_err_code */
13866         0,                      /* saved_adv_err_code */
13867         0,                      /* saved_adv_err_addr */
13868         0                       /* num_of_err */
13869 };
13870
13871 static ADVEEP_3550_CONFIG ADVEEP_3550_Config_Field_IsChar __initdata = {
13872         0,                      /* cfg_lsw */
13873         0,                      /* cfg_msw */
13874         0,                      /* -disc_enable */
13875         0,                      /* wdtr_able */
13876         0,                      /* sdtr_able */
13877         0,                      /* start_motor */
13878         0,                      /* tagqng_able */
13879         0,                      /* bios_scan */
13880         0,                      /* scam_tolerant */
13881         1,                      /* adapter_scsi_id */
13882         1,                      /* bios_boot_delay */
13883         1,                      /* scsi_reset_delay */
13884         1,                      /* bios_id_lun */
13885         1,                      /* termination */
13886         1,                      /* reserved1 */
13887         0,                      /* bios_ctrl */
13888         0,                      /* ultra_able */
13889         0,                      /* reserved2 */
13890         1,                      /* max_host_qng */
13891         1,                      /* max_dvc_qng */
13892         0,                      /* dvc_cntl */
13893         0,                      /* bug_fix */
13894         0,                      /* serial_number_word1 */
13895         0,                      /* serial_number_word2 */
13896         0,                      /* serial_number_word3 */
13897         0,                      /* check_sum */
13898         {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
13899         ,                       /* oem_name[16] */
13900         0,                      /* dvc_err_code */
13901         0,                      /* adv_err_code */
13902         0,                      /* adv_err_addr */
13903         0,                      /* saved_dvc_err_code */
13904         0,                      /* saved_adv_err_code */
13905         0,                      /* saved_adv_err_addr */
13906         0                       /* num_of_err */
13907 };
13908
13909 static ADVEEP_38C0800_CONFIG Default_38C0800_EEPROM_Config __initdata = {
13910         ADV_EEPROM_BIOS_ENABLE, /* 00 cfg_lsw */
13911         0x0000,                 /* 01 cfg_msw */
13912         0xFFFF,                 /* 02 disc_enable */
13913         0xFFFF,                 /* 03 wdtr_able */
13914         0x4444,                 /* 04 sdtr_speed1 */
13915         0xFFFF,                 /* 05 start_motor */
13916         0xFFFF,                 /* 06 tagqng_able */
13917         0xFFFF,                 /* 07 bios_scan */
13918         0,                      /* 08 scam_tolerant */
13919         7,                      /* 09 adapter_scsi_id */
13920         0,                      /*    bios_boot_delay */
13921         3,                      /* 10 scsi_reset_delay */
13922         0,                      /*    bios_id_lun */
13923         0,                      /* 11 termination_se */
13924         0,                      /*    termination_lvd */
13925         0xFFE7,                 /* 12 bios_ctrl */
13926         0x4444,                 /* 13 sdtr_speed2 */
13927         0x4444,                 /* 14 sdtr_speed3 */
13928         ASC_DEF_MAX_HOST_QNG,   /* 15 max_host_qng */
13929         ASC_DEF_MAX_DVC_QNG,    /*    max_dvc_qng */
13930         0,                      /* 16 dvc_cntl */
13931         0x4444,                 /* 17 sdtr_speed4 */
13932         0,                      /* 18 serial_number_word1 */
13933         0,                      /* 19 serial_number_word2 */
13934         0,                      /* 20 serial_number_word3 */
13935         0,                      /* 21 check_sum */
13936         {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
13937         ,                       /* 22-29 oem_name[16] */
13938         0,                      /* 30 dvc_err_code */
13939         0,                      /* 31 adv_err_code */
13940         0,                      /* 32 adv_err_addr */
13941         0,                      /* 33 saved_dvc_err_code */
13942         0,                      /* 34 saved_adv_err_code */
13943         0,                      /* 35 saved_adv_err_addr */
13944         0,                      /* 36 reserved */
13945         0,                      /* 37 reserved */
13946         0,                      /* 38 reserved */
13947         0,                      /* 39 reserved */
13948         0,                      /* 40 reserved */
13949         0,                      /* 41 reserved */
13950         0,                      /* 42 reserved */
13951         0,                      /* 43 reserved */
13952         0,                      /* 44 reserved */
13953         0,                      /* 45 reserved */
13954         0,                      /* 46 reserved */
13955         0,                      /* 47 reserved */
13956         0,                      /* 48 reserved */
13957         0,                      /* 49 reserved */
13958         0,                      /* 50 reserved */
13959         0,                      /* 51 reserved */
13960         0,                      /* 52 reserved */
13961         0,                      /* 53 reserved */
13962         0,                      /* 54 reserved */
13963         0,                      /* 55 reserved */
13964         0,                      /* 56 cisptr_lsw */
13965         0,                      /* 57 cisprt_msw */
13966         PCI_VENDOR_ID_ASP,      /* 58 subsysvid */
13967         PCI_DEVICE_ID_38C0800_REV1,     /* 59 subsysid */
13968         0,                      /* 60 reserved */
13969         0,                      /* 61 reserved */
13970         0,                      /* 62 reserved */
13971         0                       /* 63 reserved */
13972 };
13973
13974 static ADVEEP_38C0800_CONFIG ADVEEP_38C0800_Config_Field_IsChar __initdata = {
13975         0,                      /* 00 cfg_lsw */
13976         0,                      /* 01 cfg_msw */
13977         0,                      /* 02 disc_enable */
13978         0,                      /* 03 wdtr_able */
13979         0,                      /* 04 sdtr_speed1 */
13980         0,                      /* 05 start_motor */
13981         0,                      /* 06 tagqng_able */
13982         0,                      /* 07 bios_scan */
13983         0,                      /* 08 scam_tolerant */
13984         1,                      /* 09 adapter_scsi_id */
13985         1,                      /*    bios_boot_delay */
13986         1,                      /* 10 scsi_reset_delay */
13987         1,                      /*    bios_id_lun */
13988         1,                      /* 11 termination_se */
13989         1,                      /*    termination_lvd */
13990         0,                      /* 12 bios_ctrl */
13991         0,                      /* 13 sdtr_speed2 */
13992         0,                      /* 14 sdtr_speed3 */
13993         1,                      /* 15 max_host_qng */
13994         1,                      /*    max_dvc_qng */
13995         0,                      /* 16 dvc_cntl */
13996         0,                      /* 17 sdtr_speed4 */
13997         0,                      /* 18 serial_number_word1 */
13998         0,                      /* 19 serial_number_word2 */
13999         0,                      /* 20 serial_number_word3 */
14000         0,                      /* 21 check_sum */
14001         {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
14002         ,                       /* 22-29 oem_name[16] */
14003         0,                      /* 30 dvc_err_code */
14004         0,                      /* 31 adv_err_code */
14005         0,                      /* 32 adv_err_addr */
14006         0,                      /* 33 saved_dvc_err_code */
14007         0,                      /* 34 saved_adv_err_code */
14008         0,                      /* 35 saved_adv_err_addr */
14009         0,                      /* 36 reserved */
14010         0,                      /* 37 reserved */
14011         0,                      /* 38 reserved */
14012         0,                      /* 39 reserved */
14013         0,                      /* 40 reserved */
14014         0,                      /* 41 reserved */
14015         0,                      /* 42 reserved */
14016         0,                      /* 43 reserved */
14017         0,                      /* 44 reserved */
14018         0,                      /* 45 reserved */
14019         0,                      /* 46 reserved */
14020         0,                      /* 47 reserved */
14021         0,                      /* 48 reserved */
14022         0,                      /* 49 reserved */
14023         0,                      /* 50 reserved */
14024         0,                      /* 51 reserved */
14025         0,                      /* 52 reserved */
14026         0,                      /* 53 reserved */
14027         0,                      /* 54 reserved */
14028         0,                      /* 55 reserved */
14029         0,                      /* 56 cisptr_lsw */
14030         0,                      /* 57 cisprt_msw */
14031         0,                      /* 58 subsysvid */
14032         0,                      /* 59 subsysid */
14033         0,                      /* 60 reserved */
14034         0,                      /* 61 reserved */
14035         0,                      /* 62 reserved */
14036         0                       /* 63 reserved */
14037 };
14038
14039 static ADVEEP_38C1600_CONFIG Default_38C1600_EEPROM_Config __initdata = {
14040         ADV_EEPROM_BIOS_ENABLE, /* 00 cfg_lsw */
14041         0x0000,                 /* 01 cfg_msw */
14042         0xFFFF,                 /* 02 disc_enable */
14043         0xFFFF,                 /* 03 wdtr_able */
14044         0x5555,                 /* 04 sdtr_speed1 */
14045         0xFFFF,                 /* 05 start_motor */
14046         0xFFFF,                 /* 06 tagqng_able */
14047         0xFFFF,                 /* 07 bios_scan */
14048         0,                      /* 08 scam_tolerant */
14049         7,                      /* 09 adapter_scsi_id */
14050         0,                      /*    bios_boot_delay */
14051         3,                      /* 10 scsi_reset_delay */
14052         0,                      /*    bios_id_lun */
14053         0,                      /* 11 termination_se */
14054         0,                      /*    termination_lvd */
14055         0xFFE7,                 /* 12 bios_ctrl */
14056         0x5555,                 /* 13 sdtr_speed2 */
14057         0x5555,                 /* 14 sdtr_speed3 */
14058         ASC_DEF_MAX_HOST_QNG,   /* 15 max_host_qng */
14059         ASC_DEF_MAX_DVC_QNG,    /*    max_dvc_qng */
14060         0,                      /* 16 dvc_cntl */
14061         0x5555,                 /* 17 sdtr_speed4 */
14062         0,                      /* 18 serial_number_word1 */
14063         0,                      /* 19 serial_number_word2 */
14064         0,                      /* 20 serial_number_word3 */
14065         0,                      /* 21 check_sum */
14066         {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
14067         ,                       /* 22-29 oem_name[16] */
14068         0,                      /* 30 dvc_err_code */
14069         0,                      /* 31 adv_err_code */
14070         0,                      /* 32 adv_err_addr */
14071         0,                      /* 33 saved_dvc_err_code */
14072         0,                      /* 34 saved_adv_err_code */
14073         0,                      /* 35 saved_adv_err_addr */
14074         0,                      /* 36 reserved */
14075         0,                      /* 37 reserved */
14076         0,                      /* 38 reserved */
14077         0,                      /* 39 reserved */
14078         0,                      /* 40 reserved */
14079         0,                      /* 41 reserved */
14080         0,                      /* 42 reserved */
14081         0,                      /* 43 reserved */
14082         0,                      /* 44 reserved */
14083         0,                      /* 45 reserved */
14084         0,                      /* 46 reserved */
14085         0,                      /* 47 reserved */
14086         0,                      /* 48 reserved */
14087         0,                      /* 49 reserved */
14088         0,                      /* 50 reserved */
14089         0,                      /* 51 reserved */
14090         0,                      /* 52 reserved */
14091         0,                      /* 53 reserved */
14092         0,                      /* 54 reserved */
14093         0,                      /* 55 reserved */
14094         0,                      /* 56 cisptr_lsw */
14095         0,                      /* 57 cisprt_msw */
14096         PCI_VENDOR_ID_ASP,      /* 58 subsysvid */
14097         PCI_DEVICE_ID_38C1600_REV1,     /* 59 subsysid */
14098         0,                      /* 60 reserved */
14099         0,                      /* 61 reserved */
14100         0,                      /* 62 reserved */
14101         0                       /* 63 reserved */
14102 };
14103
14104 static ADVEEP_38C1600_CONFIG ADVEEP_38C1600_Config_Field_IsChar __initdata = {
14105         0,                      /* 00 cfg_lsw */
14106         0,                      /* 01 cfg_msw */
14107         0,                      /* 02 disc_enable */
14108         0,                      /* 03 wdtr_able */
14109         0,                      /* 04 sdtr_speed1 */
14110         0,                      /* 05 start_motor */
14111         0,                      /* 06 tagqng_able */
14112         0,                      /* 07 bios_scan */
14113         0,                      /* 08 scam_tolerant */
14114         1,                      /* 09 adapter_scsi_id */
14115         1,                      /*    bios_boot_delay */
14116         1,                      /* 10 scsi_reset_delay */
14117         1,                      /*    bios_id_lun */
14118         1,                      /* 11 termination_se */
14119         1,                      /*    termination_lvd */
14120         0,                      /* 12 bios_ctrl */
14121         0,                      /* 13 sdtr_speed2 */
14122         0,                      /* 14 sdtr_speed3 */
14123         1,                      /* 15 max_host_qng */
14124         1,                      /*    max_dvc_qng */
14125         0,                      /* 16 dvc_cntl */
14126         0,                      /* 17 sdtr_speed4 */
14127         0,                      /* 18 serial_number_word1 */
14128         0,                      /* 19 serial_number_word2 */
14129         0,                      /* 20 serial_number_word3 */
14130         0,                      /* 21 check_sum */
14131         {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
14132         ,                       /* 22-29 oem_name[16] */
14133         0,                      /* 30 dvc_err_code */
14134         0,                      /* 31 adv_err_code */
14135         0,                      /* 32 adv_err_addr */
14136         0,                      /* 33 saved_dvc_err_code */
14137         0,                      /* 34 saved_adv_err_code */
14138         0,                      /* 35 saved_adv_err_addr */
14139         0,                      /* 36 reserved */
14140         0,                      /* 37 reserved */
14141         0,                      /* 38 reserved */
14142         0,                      /* 39 reserved */
14143         0,                      /* 40 reserved */
14144         0,                      /* 41 reserved */
14145         0,                      /* 42 reserved */
14146         0,                      /* 43 reserved */
14147         0,                      /* 44 reserved */
14148         0,                      /* 45 reserved */
14149         0,                      /* 46 reserved */
14150         0,                      /* 47 reserved */
14151         0,                      /* 48 reserved */
14152         0,                      /* 49 reserved */
14153         0,                      /* 50 reserved */
14154         0,                      /* 51 reserved */
14155         0,                      /* 52 reserved */
14156         0,                      /* 53 reserved */
14157         0,                      /* 54 reserved */
14158         0,                      /* 55 reserved */
14159         0,                      /* 56 cisptr_lsw */
14160         0,                      /* 57 cisprt_msw */
14161         0,                      /* 58 subsysvid */
14162         0,                      /* 59 subsysid */
14163         0,                      /* 60 reserved */
14164         0,                      /* 61 reserved */
14165         0,                      /* 62 reserved */
14166         0                       /* 63 reserved */
14167 };
14168
14169 /*
14170  * Initialize the ADV_DVC_VAR structure.
14171  *
14172  * On failure set the ADV_DVC_VAR field 'err_code' and return ADV_ERROR.
14173  *
14174  * For a non-fatal error return a warning code. If there are no warnings
14175  * then 0 is returned.
14176  */
14177 static int __init AdvInitGetConfig(ADV_DVC_VAR *asc_dvc)
14178 {
14179         ushort warn_code;
14180         AdvPortAddr iop_base;
14181         uchar pci_cmd_reg;
14182         int status;
14183
14184         warn_code = 0;
14185         asc_dvc->err_code = 0;
14186         iop_base = asc_dvc->iop_base;
14187
14188         /*
14189          * PCI Command Register
14190          *
14191          * Note: AscPCICmdRegBits_BusMastering definition (0x0007) includes
14192          * I/O Space Control, Memory Space Control and Bus Master Control bits.
14193          */
14194
14195         if (((pci_cmd_reg = DvcAdvReadPCIConfigByte(asc_dvc,
14196                                                     AscPCIConfigCommandRegister))
14197              & AscPCICmdRegBits_BusMastering)
14198             != AscPCICmdRegBits_BusMastering) {
14199                 pci_cmd_reg |= AscPCICmdRegBits_BusMastering;
14200
14201                 DvcAdvWritePCIConfigByte(asc_dvc,
14202                                          AscPCIConfigCommandRegister,
14203                                          pci_cmd_reg);
14204
14205                 if (((DvcAdvReadPCIConfigByte
14206                       (asc_dvc, AscPCIConfigCommandRegister))
14207                      & AscPCICmdRegBits_BusMastering)
14208                     != AscPCICmdRegBits_BusMastering) {
14209                         warn_code |= ASC_WARN_SET_PCI_CONFIG_SPACE;
14210                 }
14211         }
14212
14213         /*
14214          * PCI Latency Timer
14215          *
14216          * If the "latency timer" register is 0x20 or above, then we don't need
14217          * to change it.  Otherwise, set it to 0x20 (i.e. set it to 0x20 if it
14218          * comes up less than 0x20).
14219          */
14220         if (DvcAdvReadPCIConfigByte(asc_dvc, AscPCIConfigLatencyTimer) < 0x20) {
14221                 DvcAdvWritePCIConfigByte(asc_dvc, AscPCIConfigLatencyTimer,
14222                                          0x20);
14223                 if (DvcAdvReadPCIConfigByte(asc_dvc, AscPCIConfigLatencyTimer) <
14224                     0x20) {
14225                         warn_code |= ASC_WARN_SET_PCI_CONFIG_SPACE;
14226                 }
14227         }
14228
14229         /*
14230          * Save the state of the PCI Configuration Command Register
14231          * "Parity Error Response Control" Bit. If the bit is clear (0),
14232          * in AdvInitAsc3550/38C0800Driver() tell the microcode to ignore
14233          * DMA parity errors.
14234          */
14235         asc_dvc->cfg->control_flag = 0;
14236         if (((DvcAdvReadPCIConfigByte(asc_dvc, AscPCIConfigCommandRegister)
14237               & AscPCICmdRegBits_ParErrRespCtrl)) == 0) {
14238                 asc_dvc->cfg->control_flag |= CONTROL_FLAG_IGNORE_PERR;
14239         }
14240
14241         asc_dvc->cfg->lib_version = (ADV_LIB_VERSION_MAJOR << 8) |
14242             ADV_LIB_VERSION_MINOR;
14243         asc_dvc->cfg->chip_version =
14244             AdvGetChipVersion(iop_base, asc_dvc->bus_type);
14245
14246         ASC_DBG2(1, "AdvInitGetConfig: iopb_chip_id_1: 0x%x 0x%x\n",
14247                  (ushort)AdvReadByteRegister(iop_base, IOPB_CHIP_ID_1),
14248                  (ushort)ADV_CHIP_ID_BYTE);
14249
14250         ASC_DBG2(1, "AdvInitGetConfig: iopw_chip_id_0: 0x%x 0x%x\n",
14251                  (ushort)AdvReadWordRegister(iop_base, IOPW_CHIP_ID_0),
14252                  (ushort)ADV_CHIP_ID_WORD);
14253
14254         /*
14255          * Reset the chip to start and allow register writes.
14256          */
14257         if (AdvFindSignature(iop_base) == 0) {
14258                 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
14259                 return ADV_ERROR;
14260         } else {
14261                 /*
14262                  * The caller must set 'chip_type' to a valid setting.
14263                  */
14264                 if (asc_dvc->chip_type != ADV_CHIP_ASC3550 &&
14265                     asc_dvc->chip_type != ADV_CHIP_ASC38C0800 &&
14266                     asc_dvc->chip_type != ADV_CHIP_ASC38C1600) {
14267                         asc_dvc->err_code |= ASC_IERR_BAD_CHIPTYPE;
14268                         return ADV_ERROR;
14269                 }
14270
14271                 /*
14272                  * Reset Chip.
14273                  */
14274                 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
14275                                      ADV_CTRL_REG_CMD_RESET);
14276                 DvcSleepMilliSecond(100);
14277                 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
14278                                      ADV_CTRL_REG_CMD_WR_IO_REG);
14279
14280                 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
14281                         if ((status =
14282                              AdvInitFrom38C1600EEP(asc_dvc)) == ADV_ERROR) {
14283                                 return ADV_ERROR;
14284                         }
14285                 } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
14286                         if ((status =
14287                              AdvInitFrom38C0800EEP(asc_dvc)) == ADV_ERROR) {
14288                                 return ADV_ERROR;
14289                         }
14290                 } else {
14291                         if ((status = AdvInitFrom3550EEP(asc_dvc)) == ADV_ERROR) {
14292                                 return ADV_ERROR;
14293                         }
14294                 }
14295                 warn_code |= status;
14296         }
14297
14298         return warn_code;
14299 }
14300
14301 /*
14302  * Initialize the ASC-3550.
14303  *
14304  * On failure set the ADV_DVC_VAR field 'err_code' and return ADV_ERROR.
14305  *
14306  * For a non-fatal error return a warning code. If there are no warnings
14307  * then 0 is returned.
14308  *
14309  * Needed after initialization for error recovery.
14310  */
14311 static int AdvInitAsc3550Driver(ADV_DVC_VAR *asc_dvc)
14312 {
14313         AdvPortAddr iop_base;
14314         ushort warn_code;
14315         ADV_DCNT sum;
14316         int begin_addr;
14317         int end_addr;
14318         ushort code_sum;
14319         int word;
14320         int j;
14321         int adv_asc3550_expanded_size;
14322         ADV_CARR_T *carrp;
14323         ADV_DCNT contig_len;
14324         ADV_SDCNT buf_size;
14325         ADV_PADDR carr_paddr;
14326         int i;
14327         ushort scsi_cfg1;
14328         uchar tid;
14329         ushort bios_mem[ASC_MC_BIOSLEN / 2];    /* BIOS RISC Memory 0x40-0x8F. */
14330         ushort wdtr_able = 0, sdtr_able, tagqng_able;
14331         uchar max_cmd[ADV_MAX_TID + 1];
14332
14333         /* If there is already an error, don't continue. */
14334         if (asc_dvc->err_code != 0) {
14335                 return ADV_ERROR;
14336         }
14337
14338         /*
14339          * The caller must set 'chip_type' to ADV_CHIP_ASC3550.
14340          */
14341         if (asc_dvc->chip_type != ADV_CHIP_ASC3550) {
14342                 asc_dvc->err_code |= ASC_IERR_BAD_CHIPTYPE;
14343                 return ADV_ERROR;
14344         }
14345
14346         warn_code = 0;
14347         iop_base = asc_dvc->iop_base;
14348
14349         /*
14350          * Save the RISC memory BIOS region before writing the microcode.
14351          * The BIOS may already be loaded and using its RISC LRAM region
14352          * so its region must be saved and restored.
14353          *
14354          * Note: This code makes the assumption, which is currently true,
14355          * that a chip reset does not clear RISC LRAM.
14356          */
14357         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
14358                 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
14359                                 bios_mem[i]);
14360         }
14361
14362         /*
14363          * Save current per TID negotiated values.
14364          */
14365         if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] == 0x55AA) {
14366                 ushort bios_version, major, minor;
14367
14368                 bios_version =
14369                     bios_mem[(ASC_MC_BIOS_VERSION - ASC_MC_BIOSMEM) / 2];
14370                 major = (bios_version >> 12) & 0xF;
14371                 minor = (bios_version >> 8) & 0xF;
14372                 if (major < 3 || (major == 3 && minor == 1)) {
14373                         /* BIOS 3.1 and earlier location of 'wdtr_able' variable. */
14374                         AdvReadWordLram(iop_base, 0x120, wdtr_able);
14375                 } else {
14376                         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
14377                 }
14378         }
14379         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
14380         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
14381         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
14382                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
14383                                 max_cmd[tid]);
14384         }
14385
14386         /*
14387          * Load the Microcode
14388          *
14389          * Write the microcode image to RISC memory starting at address 0.
14390          */
14391         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
14392         /* Assume the following compressed format of the microcode buffer:
14393          *
14394          *  254 word (508 byte) table indexed by byte code followed
14395          *  by the following byte codes:
14396          *
14397          *    1-Byte Code:
14398          *      00: Emit word 0 in table.
14399          *      01: Emit word 1 in table.
14400          *      .
14401          *      FD: Emit word 253 in table.
14402          *
14403          *    Multi-Byte Code:
14404          *      FE WW WW: (3 byte code) Word to emit is the next word WW WW.
14405          *      FF BB WW WW: (4 byte code) Emit BB count times next word WW WW.
14406          */
14407         word = 0;
14408         for (i = 253 * 2; i < _adv_asc3550_size; i++) {
14409                 if (_adv_asc3550_buf[i] == 0xff) {
14410                         for (j = 0; j < _adv_asc3550_buf[i + 1]; j++) {
14411                                 AdvWriteWordAutoIncLram(iop_base, (((ushort)
14412                                                                     _adv_asc3550_buf
14413                                                                     [i +
14414                                                                      3] << 8) |
14415                                                                    _adv_asc3550_buf
14416                                                                    [i + 2]));
14417                                 word++;
14418                         }
14419                         i += 3;
14420                 } else if (_adv_asc3550_buf[i] == 0xfe) {
14421                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
14422                                                             _adv_asc3550_buf[i +
14423                                                                              2]
14424                                                             << 8) |
14425                                                            _adv_asc3550_buf[i +
14426                                                                             1]));
14427                         i += 2;
14428                         word++;
14429                 } else {
14430                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
14431                                                             _adv_asc3550_buf[(_adv_asc3550_buf[i] * 2) + 1] << 8) | _adv_asc3550_buf[_adv_asc3550_buf[i] * 2]));
14432                         word++;
14433                 }
14434         }
14435
14436         /*
14437          * Set 'word' for later use to clear the rest of memory and save
14438          * the expanded mcode size.
14439          */
14440         word *= 2;
14441         adv_asc3550_expanded_size = word;
14442
14443         /*
14444          * Clear the rest of ASC-3550 Internal RAM (8KB).
14445          */
14446         for (; word < ADV_3550_MEMSIZE; word += 2) {
14447                 AdvWriteWordAutoIncLram(iop_base, 0);
14448         }
14449
14450         /*
14451          * Verify the microcode checksum.
14452          */
14453         sum = 0;
14454         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
14455
14456         for (word = 0; word < adv_asc3550_expanded_size; word += 2) {
14457                 sum += AdvReadWordAutoIncLram(iop_base);
14458         }
14459
14460         if (sum != _adv_asc3550_chksum) {
14461                 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
14462                 return ADV_ERROR;
14463         }
14464
14465         /*
14466          * Restore the RISC memory BIOS region.
14467          */
14468         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
14469                 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
14470                                  bios_mem[i]);
14471         }
14472
14473         /*
14474          * Calculate and write the microcode code checksum to the microcode
14475          * code checksum location ASC_MC_CODE_CHK_SUM (0x2C).
14476          */
14477         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
14478         AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
14479         code_sum = 0;
14480         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
14481         for (word = begin_addr; word < end_addr; word += 2) {
14482                 code_sum += AdvReadWordAutoIncLram(iop_base);
14483         }
14484         AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
14485
14486         /*
14487          * Read and save microcode version and date.
14488          */
14489         AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
14490                         asc_dvc->cfg->mcode_date);
14491         AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
14492                         asc_dvc->cfg->mcode_version);
14493
14494         /*
14495          * Set the chip type to indicate the ASC3550.
14496          */
14497         AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC3550);
14498
14499         /*
14500          * If the PCI Configuration Command Register "Parity Error Response
14501          * Control" Bit was clear (0), then set the microcode variable
14502          * 'control_flag' CONTROL_FLAG_IGNORE_PERR flag to tell the microcode
14503          * to ignore DMA parity errors.
14504          */
14505         if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
14506                 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
14507                 word |= CONTROL_FLAG_IGNORE_PERR;
14508                 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
14509         }
14510
14511         /*
14512          * For ASC-3550, setting the START_CTL_EMFU [3:2] bits sets a FIFO
14513          * threshold of 128 bytes. This register is only accessible to the host.
14514          */
14515         AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
14516                              START_CTL_EMFU | READ_CMD_MRM);
14517
14518         /*
14519          * Microcode operating variables for WDTR, SDTR, and command tag
14520          * queuing will be set in AdvInquiryHandling() based on what a
14521          * device reports it is capable of in Inquiry byte 7.
14522          *
14523          * If SCSI Bus Resets have been disabled, then directly set
14524          * SDTR and WDTR from the EEPROM configuration. This will allow
14525          * the BIOS and warm boot to work without a SCSI bus hang on
14526          * the Inquiry caused by host and target mismatched DTR values.
14527          * Without the SCSI Bus Reset, before an Inquiry a device can't
14528          * be assumed to be in Asynchronous, Narrow mode.
14529          */
14530         if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
14531                 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
14532                                  asc_dvc->wdtr_able);
14533                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
14534                                  asc_dvc->sdtr_able);
14535         }
14536
14537         /*
14538          * Set microcode operating variables for SDTR_SPEED1, SDTR_SPEED2,
14539          * SDTR_SPEED3, and SDTR_SPEED4 based on the ULTRA EEPROM per TID
14540          * bitmask. These values determine the maximum SDTR speed negotiated
14541          * with a device.
14542          *
14543          * The SDTR per TID bitmask overrides the SDTR_SPEED1, SDTR_SPEED2,
14544          * SDTR_SPEED3, and SDTR_SPEED4 values so it is safe to set them
14545          * without determining here whether the device supports SDTR.
14546          *
14547          * 4-bit speed  SDTR speed name
14548          * ===========  ===============
14549          * 0000b (0x0)  SDTR disabled
14550          * 0001b (0x1)  5 Mhz
14551          * 0010b (0x2)  10 Mhz
14552          * 0011b (0x3)  20 Mhz (Ultra)
14553          * 0100b (0x4)  40 Mhz (LVD/Ultra2)
14554          * 0101b (0x5)  80 Mhz (LVD2/Ultra3)
14555          * 0110b (0x6)  Undefined
14556          * .
14557          * 1111b (0xF)  Undefined
14558          */
14559         word = 0;
14560         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
14561                 if (ADV_TID_TO_TIDMASK(tid) & asc_dvc->ultra_able) {
14562                         /* Set Ultra speed for TID 'tid'. */
14563                         word |= (0x3 << (4 * (tid % 4)));
14564                 } else {
14565                         /* Set Fast speed for TID 'tid'. */
14566                         word |= (0x2 << (4 * (tid % 4)));
14567                 }
14568                 if (tid == 3) { /* Check if done with sdtr_speed1. */
14569                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, word);
14570                         word = 0;
14571                 } else if (tid == 7) {  /* Check if done with sdtr_speed2. */
14572                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, word);
14573                         word = 0;
14574                 } else if (tid == 11) { /* Check if done with sdtr_speed3. */
14575                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, word);
14576                         word = 0;
14577                 } else if (tid == 15) { /* Check if done with sdtr_speed4. */
14578                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, word);
14579                         /* End of loop. */
14580                 }
14581         }
14582
14583         /*
14584          * Set microcode operating variable for the disconnect per TID bitmask.
14585          */
14586         AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
14587                          asc_dvc->cfg->disc_enable);
14588
14589         /*
14590          * Set SCSI_CFG0 Microcode Default Value.
14591          *
14592          * The microcode will set the SCSI_CFG0 register using this value
14593          * after it is started below.
14594          */
14595         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
14596                          PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
14597                          asc_dvc->chip_scsi_id);
14598
14599         /*
14600          * Determine SCSI_CFG1 Microcode Default Value.
14601          *
14602          * The microcode will set the SCSI_CFG1 register using this value
14603          * after it is started below.
14604          */
14605
14606         /* Read current SCSI_CFG1 Register value. */
14607         scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
14608
14609         /*
14610          * If all three connectors are in use, return an error.
14611          */
14612         if ((scsi_cfg1 & CABLE_ILLEGAL_A) == 0 ||
14613             (scsi_cfg1 & CABLE_ILLEGAL_B) == 0) {
14614                 asc_dvc->err_code |= ASC_IERR_ILLEGAL_CONNECTION;
14615                 return ADV_ERROR;
14616         }
14617
14618         /*
14619          * If the internal narrow cable is reversed all of the SCSI_CTRL
14620          * register signals will be set. Check for and return an error if
14621          * this condition is found.
14622          */
14623         if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
14624                 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
14625                 return ADV_ERROR;
14626         }
14627
14628         /*
14629          * If this is a differential board and a single-ended device
14630          * is attached to one of the connectors, return an error.
14631          */
14632         if ((scsi_cfg1 & DIFF_MODE) && (scsi_cfg1 & DIFF_SENSE) == 0) {
14633                 asc_dvc->err_code |= ASC_IERR_SINGLE_END_DEVICE;
14634                 return ADV_ERROR;
14635         }
14636
14637         /*
14638          * If automatic termination control is enabled, then set the
14639          * termination value based on a table listed in a_condor.h.
14640          *
14641          * If manual termination was specified with an EEPROM setting
14642          * then 'termination' was set-up in AdvInitFrom3550EEPROM() and
14643          * is ready to be 'ored' into SCSI_CFG1.
14644          */
14645         if (asc_dvc->cfg->termination == 0) {
14646                 /*
14647                  * The software always controls termination by setting TERM_CTL_SEL.
14648                  * If TERM_CTL_SEL were set to 0, the hardware would set termination.
14649                  */
14650                 asc_dvc->cfg->termination |= TERM_CTL_SEL;
14651
14652                 switch (scsi_cfg1 & CABLE_DETECT) {
14653                         /* TERM_CTL_H: on, TERM_CTL_L: on */
14654                 case 0x3:
14655                 case 0x7:
14656                 case 0xB:
14657                 case 0xD:
14658                 case 0xE:
14659                 case 0xF:
14660                         asc_dvc->cfg->termination |= (TERM_CTL_H | TERM_CTL_L);
14661                         break;
14662
14663                         /* TERM_CTL_H: on, TERM_CTL_L: off */
14664                 case 0x1:
14665                 case 0x5:
14666                 case 0x9:
14667                 case 0xA:
14668                 case 0xC:
14669                         asc_dvc->cfg->termination |= TERM_CTL_H;
14670                         break;
14671
14672                         /* TERM_CTL_H: off, TERM_CTL_L: off */
14673                 case 0x2:
14674                 case 0x6:
14675                         break;
14676                 }
14677         }
14678
14679         /*
14680          * Clear any set TERM_CTL_H and TERM_CTL_L bits.
14681          */
14682         scsi_cfg1 &= ~TERM_CTL;
14683
14684         /*
14685          * Invert the TERM_CTL_H and TERM_CTL_L bits and then
14686          * set 'scsi_cfg1'. The TERM_POL bit does not need to be
14687          * referenced, because the hardware internally inverts
14688          * the Termination High and Low bits if TERM_POL is set.
14689          */
14690         scsi_cfg1 |= (TERM_CTL_SEL | (~asc_dvc->cfg->termination & TERM_CTL));
14691
14692         /*
14693          * Set SCSI_CFG1 Microcode Default Value
14694          *
14695          * Set filter value and possibly modified termination control
14696          * bits in the Microcode SCSI_CFG1 Register Value.
14697          *
14698          * The microcode will set the SCSI_CFG1 register using this value
14699          * after it is started below.
14700          */
14701         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1,
14702                          FLTR_DISABLE | scsi_cfg1);
14703
14704         /*
14705          * Set MEM_CFG Microcode Default Value
14706          *
14707          * The microcode will set the MEM_CFG register using this value
14708          * after it is started below.
14709          *
14710          * MEM_CFG may be accessed as a word or byte, but only bits 0-7
14711          * are defined.
14712          *
14713          * ASC-3550 has 8KB internal memory.
14714          */
14715         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
14716                          BIOS_EN | RAM_SZ_8KB);
14717
14718         /*
14719          * Set SEL_MASK Microcode Default Value
14720          *
14721          * The microcode will set the SEL_MASK register using this value
14722          * after it is started below.
14723          */
14724         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
14725                          ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
14726
14727         /*
14728          * Build carrier freelist.
14729          *
14730          * Driver must have already allocated memory and set 'carrier_buf'.
14731          */
14732         ASC_ASSERT(asc_dvc->carrier_buf != NULL);
14733
14734         carrp = (ADV_CARR_T *) ADV_16BALIGN(asc_dvc->carrier_buf);
14735         asc_dvc->carr_freelist = NULL;
14736         if (carrp == (ADV_CARR_T *) asc_dvc->carrier_buf) {
14737                 buf_size = ADV_CARRIER_BUFSIZE;
14738         } else {
14739                 buf_size = ADV_CARRIER_BUFSIZE - sizeof(ADV_CARR_T);
14740         }
14741
14742         do {
14743                 /*
14744                  * Get physical address of the carrier 'carrp'.
14745                  */
14746                 contig_len = sizeof(ADV_CARR_T);
14747                 carr_paddr =
14748                     cpu_to_le32(DvcGetPhyAddr
14749                                 (asc_dvc, NULL, (uchar *)carrp,
14750                                  (ADV_SDCNT *)&contig_len,
14751                                  ADV_IS_CARRIER_FLAG));
14752
14753                 buf_size -= sizeof(ADV_CARR_T);
14754
14755                 /*
14756                  * If the current carrier is not physically contiguous, then
14757                  * maybe there was a page crossing. Try the next carrier aligned
14758                  * start address.
14759                  */
14760                 if (contig_len < sizeof(ADV_CARR_T)) {
14761                         carrp++;
14762                         continue;
14763                 }
14764
14765                 carrp->carr_pa = carr_paddr;
14766                 carrp->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(carrp));
14767
14768                 /*
14769                  * Insert the carrier at the beginning of the freelist.
14770                  */
14771                 carrp->next_vpa =
14772                     cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
14773                 asc_dvc->carr_freelist = carrp;
14774
14775                 carrp++;
14776         }
14777         while (buf_size > 0);
14778
14779         /*
14780          * Set-up the Host->RISC Initiator Command Queue (ICQ).
14781          */
14782
14783         if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
14784                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
14785                 return ADV_ERROR;
14786         }
14787         asc_dvc->carr_freelist = (ADV_CARR_T *)
14788             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
14789
14790         /*
14791          * The first command issued will be placed in the stopper carrier.
14792          */
14793         asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
14794
14795         /*
14796          * Set RISC ICQ physical address start value.
14797          */
14798         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
14799
14800         /*
14801          * Set-up the RISC->Host Initiator Response Queue (IRQ).
14802          */
14803         if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
14804                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
14805                 return ADV_ERROR;
14806         }
14807         asc_dvc->carr_freelist = (ADV_CARR_T *)
14808             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
14809
14810         /*
14811          * The first command completed by the RISC will be placed in
14812          * the stopper.
14813          *
14814          * Note: Set 'next_vpa' to ASC_CQ_STOPPER. When the request is
14815          * completed the RISC will set the ASC_RQ_STOPPER bit.
14816          */
14817         asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
14818
14819         /*
14820          * Set RISC IRQ physical address start value.
14821          */
14822         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
14823         asc_dvc->carr_pending_cnt = 0;
14824
14825         AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
14826                              (ADV_INTR_ENABLE_HOST_INTR |
14827                               ADV_INTR_ENABLE_GLOBAL_INTR));
14828
14829         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
14830         AdvWriteWordRegister(iop_base, IOPW_PC, word);
14831
14832         /* finally, finally, gentlemen, start your engine */
14833         AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
14834
14835         /*
14836          * Reset the SCSI Bus if the EEPROM indicates that SCSI Bus
14837          * Resets should be performed. The RISC has to be running
14838          * to issue a SCSI Bus Reset.
14839          */
14840         if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
14841                 /*
14842                  * If the BIOS Signature is present in memory, restore the
14843                  * BIOS Handshake Configuration Table and do not perform
14844                  * a SCSI Bus Reset.
14845                  */
14846                 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
14847                     0x55AA) {
14848                         /*
14849                          * Restore per TID negotiated values.
14850                          */
14851                         AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
14852                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
14853                         AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
14854                                          tagqng_able);
14855                         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
14856                                 AdvWriteByteLram(iop_base,
14857                                                  ASC_MC_NUMBER_OF_MAX_CMD + tid,
14858                                                  max_cmd[tid]);
14859                         }
14860                 } else {
14861                         if (AdvResetSB(asc_dvc) != ADV_TRUE) {
14862                                 warn_code = ASC_WARN_BUSRESET_ERROR;
14863                         }
14864                 }
14865         }
14866
14867         return warn_code;
14868 }
14869
14870 /*
14871  * Initialize the ASC-38C0800.
14872  *
14873  * On failure set the ADV_DVC_VAR field 'err_code' and return ADV_ERROR.
14874  *
14875  * For a non-fatal error return a warning code. If there are no warnings
14876  * then 0 is returned.
14877  *
14878  * Needed after initialization for error recovery.
14879  */
14880 static int AdvInitAsc38C0800Driver(ADV_DVC_VAR *asc_dvc)
14881 {
14882         AdvPortAddr iop_base;
14883         ushort warn_code;
14884         ADV_DCNT sum;
14885         int begin_addr;
14886         int end_addr;
14887         ushort code_sum;
14888         int word;
14889         int j;
14890         int adv_asc38C0800_expanded_size;
14891         ADV_CARR_T *carrp;
14892         ADV_DCNT contig_len;
14893         ADV_SDCNT buf_size;
14894         ADV_PADDR carr_paddr;
14895         int i;
14896         ushort scsi_cfg1;
14897         uchar byte;
14898         uchar tid;
14899         ushort bios_mem[ASC_MC_BIOSLEN / 2];    /* BIOS RISC Memory 0x40-0x8F. */
14900         ushort wdtr_able, sdtr_able, tagqng_able;
14901         uchar max_cmd[ADV_MAX_TID + 1];
14902
14903         /* If there is already an error, don't continue. */
14904         if (asc_dvc->err_code != 0) {
14905                 return ADV_ERROR;
14906         }
14907
14908         /*
14909          * The caller must set 'chip_type' to ADV_CHIP_ASC38C0800.
14910          */
14911         if (asc_dvc->chip_type != ADV_CHIP_ASC38C0800) {
14912                 asc_dvc->err_code = ASC_IERR_BAD_CHIPTYPE;
14913                 return ADV_ERROR;
14914         }
14915
14916         warn_code = 0;
14917         iop_base = asc_dvc->iop_base;
14918
14919         /*
14920          * Save the RISC memory BIOS region before writing the microcode.
14921          * The BIOS may already be loaded and using its RISC LRAM region
14922          * so its region must be saved and restored.
14923          *
14924          * Note: This code makes the assumption, which is currently true,
14925          * that a chip reset does not clear RISC LRAM.
14926          */
14927         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
14928                 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
14929                                 bios_mem[i]);
14930         }
14931
14932         /*
14933          * Save current per TID negotiated values.
14934          */
14935         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
14936         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
14937         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
14938         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
14939                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
14940                                 max_cmd[tid]);
14941         }
14942
14943         /*
14944          * RAM BIST (RAM Built-In Self Test)
14945          *
14946          * Address : I/O base + offset 0x38h register (byte).
14947          * Function: Bit 7-6(RW) : RAM mode
14948          *                          Normal Mode   : 0x00
14949          *                          Pre-test Mode : 0x40
14950          *                          RAM Test Mode : 0x80
14951          *           Bit 5       : unused
14952          *           Bit 4(RO)   : Done bit
14953          *           Bit 3-0(RO) : Status
14954          *                          Host Error    : 0x08
14955          *                          Int_RAM Error : 0x04
14956          *                          RISC Error    : 0x02
14957          *                          SCSI Error    : 0x01
14958          *                          No Error      : 0x00
14959          *
14960          * Note: RAM BIST code should be put right here, before loading the
14961          * microcode and after saving the RISC memory BIOS region.
14962          */
14963
14964         /*
14965          * LRAM Pre-test
14966          *
14967          * Write PRE_TEST_MODE (0x40) to register and wait for 10 milliseconds.
14968          * If Done bit not set or low nibble not PRE_TEST_VALUE (0x05), return
14969          * an error. Reset to NORMAL_MODE (0x00) and do again. If cannot reset
14970          * to NORMAL_MODE, return an error too.
14971          */
14972         for (i = 0; i < 2; i++) {
14973                 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, PRE_TEST_MODE);
14974                 DvcSleepMilliSecond(10);        /* Wait for 10ms before reading back. */
14975                 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
14976                 if ((byte & RAM_TEST_DONE) == 0
14977                     || (byte & 0x0F) != PRE_TEST_VALUE) {
14978                         asc_dvc->err_code |= ASC_IERR_BIST_PRE_TEST;
14979                         return ADV_ERROR;
14980                 }
14981
14982                 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
14983                 DvcSleepMilliSecond(10);        /* Wait for 10ms before reading back. */
14984                 if (AdvReadByteRegister(iop_base, IOPB_RAM_BIST)
14985                     != NORMAL_VALUE) {
14986                         asc_dvc->err_code |= ASC_IERR_BIST_PRE_TEST;
14987                         return ADV_ERROR;
14988                 }
14989         }
14990
14991         /*
14992          * LRAM Test - It takes about 1.5 ms to run through the test.
14993          *
14994          * Write RAM_TEST_MODE (0x80) to register and wait for 10 milliseconds.
14995          * If Done bit not set or Status not 0, save register byte, set the
14996          * err_code, and return an error.
14997          */
14998         AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, RAM_TEST_MODE);
14999         DvcSleepMilliSecond(10);        /* Wait for 10ms before checking status. */
15000
15001         byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
15002         if ((byte & RAM_TEST_DONE) == 0 || (byte & RAM_TEST_STATUS) != 0) {
15003                 /* Get here if Done bit not set or Status not 0. */
15004                 asc_dvc->bist_err_code = byte;  /* for BIOS display message */
15005                 asc_dvc->err_code |= ASC_IERR_BIST_RAM_TEST;
15006                 return ADV_ERROR;
15007         }
15008
15009         /* We need to reset back to normal mode after LRAM test passes. */
15010         AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
15011
15012         /*
15013          * Load the Microcode
15014          *
15015          * Write the microcode image to RISC memory starting at address 0.
15016          *
15017          */
15018         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
15019
15020         /* Assume the following compressed format of the microcode buffer:
15021          *
15022          *  254 word (508 byte) table indexed by byte code followed
15023          *  by the following byte codes:
15024          *
15025          *    1-Byte Code:
15026          *      00: Emit word 0 in table.
15027          *      01: Emit word 1 in table.
15028          *      .
15029          *      FD: Emit word 253 in table.
15030          *
15031          *    Multi-Byte Code:
15032          *      FE WW WW: (3 byte code) Word to emit is the next word WW WW.
15033          *      FF BB WW WW: (4 byte code) Emit BB count times next word WW WW.
15034          */
15035         word = 0;
15036         for (i = 253 * 2; i < _adv_asc38C0800_size; i++) {
15037                 if (_adv_asc38C0800_buf[i] == 0xff) {
15038                         for (j = 0; j < _adv_asc38C0800_buf[i + 1]; j++) {
15039                                 AdvWriteWordAutoIncLram(iop_base, (((ushort)
15040                                                                     _adv_asc38C0800_buf
15041                                                                     [i +
15042                                                                      3] << 8) |
15043                                                                    _adv_asc38C0800_buf
15044                                                                    [i + 2]));
15045                                 word++;
15046                         }
15047                         i += 3;
15048                 } else if (_adv_asc38C0800_buf[i] == 0xfe) {
15049                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
15050                                                             _adv_asc38C0800_buf
15051                                                             [i +
15052                                                              2] << 8) |
15053                                                            _adv_asc38C0800_buf[i
15054                                                                                +
15055                                                                                1]));
15056                         i += 2;
15057                         word++;
15058                 } else {
15059                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
15060                                                             _adv_asc38C0800_buf[(_adv_asc38C0800_buf[i] * 2) + 1] << 8) | _adv_asc38C0800_buf[_adv_asc38C0800_buf[i] * 2]));
15061                         word++;
15062                 }
15063         }
15064
15065         /*
15066          * Set 'word' for later use to clear the rest of memory and save
15067          * the expanded mcode size.
15068          */
15069         word *= 2;
15070         adv_asc38C0800_expanded_size = word;
15071
15072         /*
15073          * Clear the rest of ASC-38C0800 Internal RAM (16KB).
15074          */
15075         for (; word < ADV_38C0800_MEMSIZE; word += 2) {
15076                 AdvWriteWordAutoIncLram(iop_base, 0);
15077         }
15078
15079         /*
15080          * Verify the microcode checksum.
15081          */
15082         sum = 0;
15083         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
15084
15085         for (word = 0; word < adv_asc38C0800_expanded_size; word += 2) {
15086                 sum += AdvReadWordAutoIncLram(iop_base);
15087         }
15088         ASC_DBG2(1, "AdvInitAsc38C0800Driver: word %d, i %d\n", word, i);
15089
15090         ASC_DBG2(1,
15091                  "AdvInitAsc38C0800Driver: sum 0x%lx, _adv_asc38C0800_chksum 0x%lx\n",
15092                  (ulong)sum, (ulong)_adv_asc38C0800_chksum);
15093
15094         if (sum != _adv_asc38C0800_chksum) {
15095                 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
15096                 return ADV_ERROR;
15097         }
15098
15099         /*
15100          * Restore the RISC memory BIOS region.
15101          */
15102         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
15103                 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
15104                                  bios_mem[i]);
15105         }
15106
15107         /*
15108          * Calculate and write the microcode code checksum to the microcode
15109          * code checksum location ASC_MC_CODE_CHK_SUM (0x2C).
15110          */
15111         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
15112         AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
15113         code_sum = 0;
15114         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
15115         for (word = begin_addr; word < end_addr; word += 2) {
15116                 code_sum += AdvReadWordAutoIncLram(iop_base);
15117         }
15118         AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
15119
15120         /*
15121          * Read microcode version and date.
15122          */
15123         AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
15124                         asc_dvc->cfg->mcode_date);
15125         AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
15126                         asc_dvc->cfg->mcode_version);
15127
15128         /*
15129          * Set the chip type to indicate the ASC38C0800.
15130          */
15131         AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC38C0800);
15132
15133         /*
15134          * Write 1 to bit 14 'DIS_TERM_DRV' in the SCSI_CFG1 register.
15135          * When DIS_TERM_DRV set to 1, C_DET[3:0] will reflect current
15136          * cable detection and then we are able to read C_DET[3:0].
15137          *
15138          * Note: We will reset DIS_TERM_DRV to 0 in the 'Set SCSI_CFG1
15139          * Microcode Default Value' section below.
15140          */
15141         scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
15142         AdvWriteWordRegister(iop_base, IOPW_SCSI_CFG1,
15143                              scsi_cfg1 | DIS_TERM_DRV);
15144
15145         /*
15146          * If the PCI Configuration Command Register "Parity Error Response
15147          * Control" Bit was clear (0), then set the microcode variable
15148          * 'control_flag' CONTROL_FLAG_IGNORE_PERR flag to tell the microcode
15149          * to ignore DMA parity errors.
15150          */
15151         if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
15152                 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15153                 word |= CONTROL_FLAG_IGNORE_PERR;
15154                 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15155         }
15156
15157         /*
15158          * For ASC-38C0800, set FIFO_THRESH_80B [6:4] bits and START_CTL_TH [3:2]
15159          * bits for the default FIFO threshold.
15160          *
15161          * Note: ASC-38C0800 FIFO threshold has been changed to 256 bytes.
15162          *
15163          * For DMA Errata #4 set the BC_THRESH_ENB bit.
15164          */
15165         AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
15166                              BC_THRESH_ENB | FIFO_THRESH_80B | START_CTL_TH |
15167                              READ_CMD_MRM);
15168
15169         /*
15170          * Microcode operating variables for WDTR, SDTR, and command tag
15171          * queuing will be set in AdvInquiryHandling() based on what a
15172          * device reports it is capable of in Inquiry byte 7.
15173          *
15174          * If SCSI Bus Resets have been disabled, then directly set
15175          * SDTR and WDTR from the EEPROM configuration. This will allow
15176          * the BIOS and warm boot to work without a SCSI bus hang on
15177          * the Inquiry caused by host and target mismatched DTR values.
15178          * Without the SCSI Bus Reset, before an Inquiry a device can't
15179          * be assumed to be in Asynchronous, Narrow mode.
15180          */
15181         if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
15182                 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
15183                                  asc_dvc->wdtr_able);
15184                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
15185                                  asc_dvc->sdtr_able);
15186         }
15187
15188         /*
15189          * Set microcode operating variables for DISC and SDTR_SPEED1,
15190          * SDTR_SPEED2, SDTR_SPEED3, and SDTR_SPEED4 based on the EEPROM
15191          * configuration values.
15192          *
15193          * The SDTR per TID bitmask overrides the SDTR_SPEED1, SDTR_SPEED2,
15194          * SDTR_SPEED3, and SDTR_SPEED4 values so it is safe to set them
15195          * without determining here whether the device supports SDTR.
15196          */
15197         AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
15198                          asc_dvc->cfg->disc_enable);
15199         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, asc_dvc->sdtr_speed1);
15200         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, asc_dvc->sdtr_speed2);
15201         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, asc_dvc->sdtr_speed3);
15202         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, asc_dvc->sdtr_speed4);
15203
15204         /*
15205          * Set SCSI_CFG0 Microcode Default Value.
15206          *
15207          * The microcode will set the SCSI_CFG0 register using this value
15208          * after it is started below.
15209          */
15210         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
15211                          PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
15212                          asc_dvc->chip_scsi_id);
15213
15214         /*
15215          * Determine SCSI_CFG1 Microcode Default Value.
15216          *
15217          * The microcode will set the SCSI_CFG1 register using this value
15218          * after it is started below.
15219          */
15220
15221         /* Read current SCSI_CFG1 Register value. */
15222         scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
15223
15224         /*
15225          * If the internal narrow cable is reversed all of the SCSI_CTRL
15226          * register signals will be set. Check for and return an error if
15227          * this condition is found.
15228          */
15229         if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
15230                 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
15231                 return ADV_ERROR;
15232         }
15233
15234         /*
15235          * All kind of combinations of devices attached to one of four connectors
15236          * are acceptable except HVD device attached. For example, LVD device can
15237          * be attached to SE connector while SE device attached to LVD connector.
15238          * If LVD device attached to SE connector, it only runs up to Ultra speed.
15239          *
15240          * If an HVD device is attached to one of LVD connectors, return an error.
15241          * However, there is no way to detect HVD device attached to SE connectors.
15242          */
15243         if (scsi_cfg1 & HVD) {
15244                 asc_dvc->err_code |= ASC_IERR_HVD_DEVICE;
15245                 return ADV_ERROR;
15246         }
15247
15248         /*
15249          * If either SE or LVD automatic termination control is enabled, then
15250          * set the termination value based on a table listed in a_condor.h.
15251          *
15252          * If manual termination was specified with an EEPROM setting then
15253          * 'termination' was set-up in AdvInitFrom38C0800EEPROM() and is ready to
15254          * be 'ored' into SCSI_CFG1.
15255          */
15256         if ((asc_dvc->cfg->termination & TERM_SE) == 0) {
15257                 /* SE automatic termination control is enabled. */
15258                 switch (scsi_cfg1 & C_DET_SE) {
15259                         /* TERM_SE_HI: on, TERM_SE_LO: on */
15260                 case 0x1:
15261                 case 0x2:
15262                 case 0x3:
15263                         asc_dvc->cfg->termination |= TERM_SE;
15264                         break;
15265
15266                         /* TERM_SE_HI: on, TERM_SE_LO: off */
15267                 case 0x0:
15268                         asc_dvc->cfg->termination |= TERM_SE_HI;
15269                         break;
15270                 }
15271         }
15272
15273         if ((asc_dvc->cfg->termination & TERM_LVD) == 0) {
15274                 /* LVD automatic termination control is enabled. */
15275                 switch (scsi_cfg1 & C_DET_LVD) {
15276                         /* TERM_LVD_HI: on, TERM_LVD_LO: on */
15277                 case 0x4:
15278                 case 0x8:
15279                 case 0xC:
15280                         asc_dvc->cfg->termination |= TERM_LVD;
15281                         break;
15282
15283                         /* TERM_LVD_HI: off, TERM_LVD_LO: off */
15284                 case 0x0:
15285                         break;
15286                 }
15287         }
15288
15289         /*
15290          * Clear any set TERM_SE and TERM_LVD bits.
15291          */
15292         scsi_cfg1 &= (~TERM_SE & ~TERM_LVD);
15293
15294         /*
15295          * Invert the TERM_SE and TERM_LVD bits and then set 'scsi_cfg1'.
15296          */
15297         scsi_cfg1 |= (~asc_dvc->cfg->termination & 0xF0);
15298
15299         /*
15300          * Clear BIG_ENDIAN, DIS_TERM_DRV, Terminator Polarity and HVD/LVD/SE bits
15301          * and set possibly modified termination control bits in the Microcode
15302          * SCSI_CFG1 Register Value.
15303          */
15304         scsi_cfg1 &= (~BIG_ENDIAN & ~DIS_TERM_DRV & ~TERM_POL & ~HVD_LVD_SE);
15305
15306         /*
15307          * Set SCSI_CFG1 Microcode Default Value
15308          *
15309          * Set possibly modified termination control and reset DIS_TERM_DRV
15310          * bits in the Microcode SCSI_CFG1 Register Value.
15311          *
15312          * The microcode will set the SCSI_CFG1 register using this value
15313          * after it is started below.
15314          */
15315         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1, scsi_cfg1);
15316
15317         /*
15318          * Set MEM_CFG Microcode Default Value
15319          *
15320          * The microcode will set the MEM_CFG register using this value
15321          * after it is started below.
15322          *
15323          * MEM_CFG may be accessed as a word or byte, but only bits 0-7
15324          * are defined.
15325          *
15326          * ASC-38C0800 has 16KB internal memory.
15327          */
15328         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
15329                          BIOS_EN | RAM_SZ_16KB);
15330
15331         /*
15332          * Set SEL_MASK Microcode Default Value
15333          *
15334          * The microcode will set the SEL_MASK register using this value
15335          * after it is started below.
15336          */
15337         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
15338                          ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
15339
15340         /*
15341          * Build the carrier freelist.
15342          *
15343          * Driver must have already allocated memory and set 'carrier_buf'.
15344          */
15345         ASC_ASSERT(asc_dvc->carrier_buf != NULL);
15346
15347         carrp = (ADV_CARR_T *) ADV_16BALIGN(asc_dvc->carrier_buf);
15348         asc_dvc->carr_freelist = NULL;
15349         if (carrp == (ADV_CARR_T *) asc_dvc->carrier_buf) {
15350                 buf_size = ADV_CARRIER_BUFSIZE;
15351         } else {
15352                 buf_size = ADV_CARRIER_BUFSIZE - sizeof(ADV_CARR_T);
15353         }
15354
15355         do {
15356                 /*
15357                  * Get physical address for the carrier 'carrp'.
15358                  */
15359                 contig_len = sizeof(ADV_CARR_T);
15360                 carr_paddr =
15361                     cpu_to_le32(DvcGetPhyAddr
15362                                 (asc_dvc, NULL, (uchar *)carrp,
15363                                  (ADV_SDCNT *)&contig_len,
15364                                  ADV_IS_CARRIER_FLAG));
15365
15366                 buf_size -= sizeof(ADV_CARR_T);
15367
15368                 /*
15369                  * If the current carrier is not physically contiguous, then
15370                  * maybe there was a page crossing. Try the next carrier aligned
15371                  * start address.
15372                  */
15373                 if (contig_len < sizeof(ADV_CARR_T)) {
15374                         carrp++;
15375                         continue;
15376                 }
15377
15378                 carrp->carr_pa = carr_paddr;
15379                 carrp->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(carrp));
15380
15381                 /*
15382                  * Insert the carrier at the beginning of the freelist.
15383                  */
15384                 carrp->next_vpa =
15385                     cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
15386                 asc_dvc->carr_freelist = carrp;
15387
15388                 carrp++;
15389         }
15390         while (buf_size > 0);
15391
15392         /*
15393          * Set-up the Host->RISC Initiator Command Queue (ICQ).
15394          */
15395
15396         if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
15397                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
15398                 return ADV_ERROR;
15399         }
15400         asc_dvc->carr_freelist = (ADV_CARR_T *)
15401             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
15402
15403         /*
15404          * The first command issued will be placed in the stopper carrier.
15405          */
15406         asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
15407
15408         /*
15409          * Set RISC ICQ physical address start value.
15410          * carr_pa is LE, must be native before write
15411          */
15412         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
15413
15414         /*
15415          * Set-up the RISC->Host Initiator Response Queue (IRQ).
15416          */
15417         if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
15418                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
15419                 return ADV_ERROR;
15420         }
15421         asc_dvc->carr_freelist = (ADV_CARR_T *)
15422             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
15423
15424         /*
15425          * The first command completed by the RISC will be placed in
15426          * the stopper.
15427          *
15428          * Note: Set 'next_vpa' to ASC_CQ_STOPPER. When the request is
15429          * completed the RISC will set the ASC_RQ_STOPPER bit.
15430          */
15431         asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
15432
15433         /*
15434          * Set RISC IRQ physical address start value.
15435          *
15436          * carr_pa is LE, must be native before write *
15437          */
15438         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
15439         asc_dvc->carr_pending_cnt = 0;
15440
15441         AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
15442                              (ADV_INTR_ENABLE_HOST_INTR |
15443                               ADV_INTR_ENABLE_GLOBAL_INTR));
15444
15445         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
15446         AdvWriteWordRegister(iop_base, IOPW_PC, word);
15447
15448         /* finally, finally, gentlemen, start your engine */
15449         AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
15450
15451         /*
15452          * Reset the SCSI Bus if the EEPROM indicates that SCSI Bus
15453          * Resets should be performed. The RISC has to be running
15454          * to issue a SCSI Bus Reset.
15455          */
15456         if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
15457                 /*
15458                  * If the BIOS Signature is present in memory, restore the
15459                  * BIOS Handshake Configuration Table and do not perform
15460                  * a SCSI Bus Reset.
15461                  */
15462                 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
15463                     0x55AA) {
15464                         /*
15465                          * Restore per TID negotiated values.
15466                          */
15467                         AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
15468                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
15469                         AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
15470                                          tagqng_able);
15471                         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
15472                                 AdvWriteByteLram(iop_base,
15473                                                  ASC_MC_NUMBER_OF_MAX_CMD + tid,
15474                                                  max_cmd[tid]);
15475                         }
15476                 } else {
15477                         if (AdvResetSB(asc_dvc) != ADV_TRUE) {
15478                                 warn_code = ASC_WARN_BUSRESET_ERROR;
15479                         }
15480                 }
15481         }
15482
15483         return warn_code;
15484 }
15485
15486 /*
15487  * Initialize the ASC-38C1600.
15488  *
15489  * On failure set the ASC_DVC_VAR field 'err_code' and return ADV_ERROR.
15490  *
15491  * For a non-fatal error return a warning code. If there are no warnings
15492  * then 0 is returned.
15493  *
15494  * Needed after initialization for error recovery.
15495  */
15496 static int AdvInitAsc38C1600Driver(ADV_DVC_VAR *asc_dvc)
15497 {
15498         AdvPortAddr iop_base;
15499         ushort warn_code;
15500         ADV_DCNT sum;
15501         int begin_addr;
15502         int end_addr;
15503         ushort code_sum;
15504         long word;
15505         int j;
15506         int adv_asc38C1600_expanded_size;
15507         ADV_CARR_T *carrp;
15508         ADV_DCNT contig_len;
15509         ADV_SDCNT buf_size;
15510         ADV_PADDR carr_paddr;
15511         int i;
15512         ushort scsi_cfg1;
15513         uchar byte;
15514         uchar tid;
15515         ushort bios_mem[ASC_MC_BIOSLEN / 2];    /* BIOS RISC Memory 0x40-0x8F. */
15516         ushort wdtr_able, sdtr_able, ppr_able, tagqng_able;
15517         uchar max_cmd[ASC_MAX_TID + 1];
15518
15519         /* If there is already an error, don't continue. */
15520         if (asc_dvc->err_code != 0) {
15521                 return ADV_ERROR;
15522         }
15523
15524         /*
15525          * The caller must set 'chip_type' to ADV_CHIP_ASC38C1600.
15526          */
15527         if (asc_dvc->chip_type != ADV_CHIP_ASC38C1600) {
15528                 asc_dvc->err_code = ASC_IERR_BAD_CHIPTYPE;
15529                 return ADV_ERROR;
15530         }
15531
15532         warn_code = 0;
15533         iop_base = asc_dvc->iop_base;
15534
15535         /*
15536          * Save the RISC memory BIOS region before writing the microcode.
15537          * The BIOS may already be loaded and using its RISC LRAM region
15538          * so its region must be saved and restored.
15539          *
15540          * Note: This code makes the assumption, which is currently true,
15541          * that a chip reset does not clear RISC LRAM.
15542          */
15543         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
15544                 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
15545                                 bios_mem[i]);
15546         }
15547
15548         /*
15549          * Save current per TID negotiated values.
15550          */
15551         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
15552         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
15553         AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
15554         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
15555         for (tid = 0; tid <= ASC_MAX_TID; tid++) {
15556                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
15557                                 max_cmd[tid]);
15558         }
15559
15560         /*
15561          * RAM BIST (Built-In Self Test)
15562          *
15563          * Address : I/O base + offset 0x38h register (byte).
15564          * Function: Bit 7-6(RW) : RAM mode
15565          *                          Normal Mode   : 0x00
15566          *                          Pre-test Mode : 0x40
15567          *                          RAM Test Mode : 0x80
15568          *           Bit 5       : unused
15569          *           Bit 4(RO)   : Done bit
15570          *           Bit 3-0(RO) : Status
15571          *                          Host Error    : 0x08
15572          *                          Int_RAM Error : 0x04
15573          *                          RISC Error    : 0x02
15574          *                          SCSI Error    : 0x01
15575          *                          No Error      : 0x00
15576          *
15577          * Note: RAM BIST code should be put right here, before loading the
15578          * microcode and after saving the RISC memory BIOS region.
15579          */
15580
15581         /*
15582          * LRAM Pre-test
15583          *
15584          * Write PRE_TEST_MODE (0x40) to register and wait for 10 milliseconds.
15585          * If Done bit not set or low nibble not PRE_TEST_VALUE (0x05), return
15586          * an error. Reset to NORMAL_MODE (0x00) and do again. If cannot reset
15587          * to NORMAL_MODE, return an error too.
15588          */
15589         for (i = 0; i < 2; i++) {
15590                 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, PRE_TEST_MODE);
15591                 DvcSleepMilliSecond(10);        /* Wait for 10ms before reading back. */
15592                 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
15593                 if ((byte & RAM_TEST_DONE) == 0
15594                     || (byte & 0x0F) != PRE_TEST_VALUE) {
15595                         asc_dvc->err_code |= ASC_IERR_BIST_PRE_TEST;
15596                         return ADV_ERROR;
15597                 }
15598
15599                 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
15600                 DvcSleepMilliSecond(10);        /* Wait for 10ms before reading back. */
15601                 if (AdvReadByteRegister(iop_base, IOPB_RAM_BIST)
15602                     != NORMAL_VALUE) {
15603                         asc_dvc->err_code |= ASC_IERR_BIST_PRE_TEST;
15604                         return ADV_ERROR;
15605                 }
15606         }
15607
15608         /*
15609          * LRAM Test - It takes about 1.5 ms to run through the test.
15610          *
15611          * Write RAM_TEST_MODE (0x80) to register and wait for 10 milliseconds.
15612          * If Done bit not set or Status not 0, save register byte, set the
15613          * err_code, and return an error.
15614          */
15615         AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, RAM_TEST_MODE);
15616         DvcSleepMilliSecond(10);        /* Wait for 10ms before checking status. */
15617
15618         byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
15619         if ((byte & RAM_TEST_DONE) == 0 || (byte & RAM_TEST_STATUS) != 0) {
15620                 /* Get here if Done bit not set or Status not 0. */
15621                 asc_dvc->bist_err_code = byte;  /* for BIOS display message */
15622                 asc_dvc->err_code |= ASC_IERR_BIST_RAM_TEST;
15623                 return ADV_ERROR;
15624         }
15625
15626         /* We need to reset back to normal mode after LRAM test passes. */
15627         AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
15628
15629         /*
15630          * Load the Microcode
15631          *
15632          * Write the microcode image to RISC memory starting at address 0.
15633          *
15634          */
15635         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
15636
15637         /*
15638          * Assume the following compressed format of the microcode buffer:
15639          *
15640          *  254 word (508 byte) table indexed by byte code followed
15641          *  by the following byte codes:
15642          *
15643          *    1-Byte Code:
15644          *      00: Emit word 0 in table.
15645          *      01: Emit word 1 in table.
15646          *      .
15647          *      FD: Emit word 253 in table.
15648          *
15649          *    Multi-Byte Code:
15650          *      FE WW WW: (3 byte code) Word to emit is the next word WW WW.
15651          *      FF BB WW WW: (4 byte code) Emit BB count times next word WW WW.
15652          */
15653         word = 0;
15654         for (i = 253 * 2; i < _adv_asc38C1600_size; i++) {
15655                 if (_adv_asc38C1600_buf[i] == 0xff) {
15656                         for (j = 0; j < _adv_asc38C1600_buf[i + 1]; j++) {
15657                                 AdvWriteWordAutoIncLram(iop_base, (((ushort)
15658                                                                     _adv_asc38C1600_buf
15659                                                                     [i +
15660                                                                      3] << 8) |
15661                                                                    _adv_asc38C1600_buf
15662                                                                    [i + 2]));
15663                                 word++;
15664                         }
15665                         i += 3;
15666                 } else if (_adv_asc38C1600_buf[i] == 0xfe) {
15667                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
15668                                                             _adv_asc38C1600_buf
15669                                                             [i +
15670                                                              2] << 8) |
15671                                                            _adv_asc38C1600_buf[i
15672                                                                                +
15673                                                                                1]));
15674                         i += 2;
15675                         word++;
15676                 } else {
15677                         AdvWriteWordAutoIncLram(iop_base, (((ushort)
15678                                                             _adv_asc38C1600_buf[(_adv_asc38C1600_buf[i] * 2) + 1] << 8) | _adv_asc38C1600_buf[_adv_asc38C1600_buf[i] * 2]));
15679                         word++;
15680                 }
15681         }
15682
15683         /*
15684          * Set 'word' for later use to clear the rest of memory and save
15685          * the expanded mcode size.
15686          */
15687         word *= 2;
15688         adv_asc38C1600_expanded_size = word;
15689
15690         /*
15691          * Clear the rest of ASC-38C1600 Internal RAM (32KB).
15692          */
15693         for (; word < ADV_38C1600_MEMSIZE; word += 2) {
15694                 AdvWriteWordAutoIncLram(iop_base, 0);
15695         }
15696
15697         /*
15698          * Verify the microcode checksum.
15699          */
15700         sum = 0;
15701         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
15702
15703         for (word = 0; word < adv_asc38C1600_expanded_size; word += 2) {
15704                 sum += AdvReadWordAutoIncLram(iop_base);
15705         }
15706
15707         if (sum != _adv_asc38C1600_chksum) {
15708                 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
15709                 return ADV_ERROR;
15710         }
15711
15712         /*
15713          * Restore the RISC memory BIOS region.
15714          */
15715         for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
15716                 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
15717                                  bios_mem[i]);
15718         }
15719
15720         /*
15721          * Calculate and write the microcode code checksum to the microcode
15722          * code checksum location ASC_MC_CODE_CHK_SUM (0x2C).
15723          */
15724         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
15725         AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
15726         code_sum = 0;
15727         AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
15728         for (word = begin_addr; word < end_addr; word += 2) {
15729                 code_sum += AdvReadWordAutoIncLram(iop_base);
15730         }
15731         AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
15732
15733         /*
15734          * Read microcode version and date.
15735          */
15736         AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
15737                         asc_dvc->cfg->mcode_date);
15738         AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
15739                         asc_dvc->cfg->mcode_version);
15740
15741         /*
15742          * Set the chip type to indicate the ASC38C1600.
15743          */
15744         AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC38C1600);
15745
15746         /*
15747          * Write 1 to bit 14 'DIS_TERM_DRV' in the SCSI_CFG1 register.
15748          * When DIS_TERM_DRV set to 1, C_DET[3:0] will reflect current
15749          * cable detection and then we are able to read C_DET[3:0].
15750          *
15751          * Note: We will reset DIS_TERM_DRV to 0 in the 'Set SCSI_CFG1
15752          * Microcode Default Value' section below.
15753          */
15754         scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
15755         AdvWriteWordRegister(iop_base, IOPW_SCSI_CFG1,
15756                              scsi_cfg1 | DIS_TERM_DRV);
15757
15758         /*
15759          * If the PCI Configuration Command Register "Parity Error Response
15760          * Control" Bit was clear (0), then set the microcode variable
15761          * 'control_flag' CONTROL_FLAG_IGNORE_PERR flag to tell the microcode
15762          * to ignore DMA parity errors.
15763          */
15764         if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
15765                 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15766                 word |= CONTROL_FLAG_IGNORE_PERR;
15767                 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15768         }
15769
15770         /*
15771          * If the BIOS control flag AIPP (Asynchronous Information
15772          * Phase Protection) disable bit is not set, then set the firmware
15773          * 'control_flag' CONTROL_FLAG_ENABLE_AIPP bit to enable
15774          * AIPP checking and encoding.
15775          */
15776         if ((asc_dvc->bios_ctrl & BIOS_CTRL_AIPP_DIS) == 0) {
15777                 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15778                 word |= CONTROL_FLAG_ENABLE_AIPP;
15779                 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
15780         }
15781
15782         /*
15783          * For ASC-38C1600 use DMA_CFG0 default values: FIFO_THRESH_80B [6:4],
15784          * and START_CTL_TH [3:2].
15785          */
15786         AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
15787                              FIFO_THRESH_80B | START_CTL_TH | READ_CMD_MRM);
15788
15789         /*
15790          * Microcode operating variables for WDTR, SDTR, and command tag
15791          * queuing will be set in AdvInquiryHandling() based on what a
15792          * device reports it is capable of in Inquiry byte 7.
15793          *
15794          * If SCSI Bus Resets have been disabled, then directly set
15795          * SDTR and WDTR from the EEPROM configuration. This will allow
15796          * the BIOS and warm boot to work without a SCSI bus hang on
15797          * the Inquiry caused by host and target mismatched DTR values.
15798          * Without the SCSI Bus Reset, before an Inquiry a device can't
15799          * be assumed to be in Asynchronous, Narrow mode.
15800          */
15801         if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
15802                 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
15803                                  asc_dvc->wdtr_able);
15804                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
15805                                  asc_dvc->sdtr_able);
15806         }
15807
15808         /*
15809          * Set microcode operating variables for DISC and SDTR_SPEED1,
15810          * SDTR_SPEED2, SDTR_SPEED3, and SDTR_SPEED4 based on the EEPROM
15811          * configuration values.
15812          *
15813          * The SDTR per TID bitmask overrides the SDTR_SPEED1, SDTR_SPEED2,
15814          * SDTR_SPEED3, and SDTR_SPEED4 values so it is safe to set them
15815          * without determining here whether the device supports SDTR.
15816          */
15817         AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
15818                          asc_dvc->cfg->disc_enable);
15819         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, asc_dvc->sdtr_speed1);
15820         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, asc_dvc->sdtr_speed2);
15821         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, asc_dvc->sdtr_speed3);
15822         AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, asc_dvc->sdtr_speed4);
15823
15824         /*
15825          * Set SCSI_CFG0 Microcode Default Value.
15826          *
15827          * The microcode will set the SCSI_CFG0 register using this value
15828          * after it is started below.
15829          */
15830         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
15831                          PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
15832                          asc_dvc->chip_scsi_id);
15833
15834         /*
15835          * Calculate SCSI_CFG1 Microcode Default Value.
15836          *
15837          * The microcode will set the SCSI_CFG1 register using this value
15838          * after it is started below.
15839          *
15840          * Each ASC-38C1600 function has only two cable detect bits.
15841          * The bus mode override bits are in IOPB_SOFT_OVER_WR.
15842          */
15843         scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
15844
15845         /*
15846          * If the cable is reversed all of the SCSI_CTRL register signals
15847          * will be set. Check for and return an error if this condition is
15848          * found.
15849          */
15850         if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
15851                 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
15852                 return ADV_ERROR;
15853         }
15854
15855         /*
15856          * Each ASC-38C1600 function has two connectors. Only an HVD device
15857          * can not be connected to either connector. An LVD device or SE device
15858          * may be connected to either connecor. If an SE device is connected,
15859          * then at most Ultra speed (20 Mhz) can be used on both connectors.
15860          *
15861          * If an HVD device is attached, return an error.
15862          */
15863         if (scsi_cfg1 & HVD) {
15864                 asc_dvc->err_code |= ASC_IERR_HVD_DEVICE;
15865                 return ADV_ERROR;
15866         }
15867
15868         /*
15869          * Each function in the ASC-38C1600 uses only the SE cable detect and
15870          * termination because there are two connectors for each function. Each
15871          * function may use either LVD or SE mode. Corresponding the SE automatic
15872          * termination control EEPROM bits are used for each function. Each
15873          * function has its own EEPROM. If SE automatic control is enabled for
15874          * the function, then set the termination value based on a table listed
15875          * in a_condor.h.
15876          *
15877          * If manual termination is specified in the EEPROM for the function,
15878          * then 'termination' was set-up in AscInitFrom38C1600EEPROM() and is
15879          * ready to be 'ored' into SCSI_CFG1.
15880          */
15881         if ((asc_dvc->cfg->termination & TERM_SE) == 0) {
15882                 /* SE automatic termination control is enabled. */
15883                 switch (scsi_cfg1 & C_DET_SE) {
15884                         /* TERM_SE_HI: on, TERM_SE_LO: on */
15885                 case 0x1:
15886                 case 0x2:
15887                 case 0x3:
15888                         asc_dvc->cfg->termination |= TERM_SE;
15889                         break;
15890
15891                 case 0x0:
15892                         if (ASC_PCI_ID2FUNC(asc_dvc->cfg->pci_slot_info) == 0) {
15893                                 /* Function 0 - TERM_SE_HI: off, TERM_SE_LO: off */
15894                         } else {
15895                                 /* Function 1 - TERM_SE_HI: on, TERM_SE_LO: off */
15896                                 asc_dvc->cfg->termination |= TERM_SE_HI;
15897                         }
15898                         break;
15899                 }
15900         }
15901
15902         /*
15903          * Clear any set TERM_SE bits.
15904          */
15905         scsi_cfg1 &= ~TERM_SE;
15906
15907         /*
15908          * Invert the TERM_SE bits and then set 'scsi_cfg1'.
15909          */
15910         scsi_cfg1 |= (~asc_dvc->cfg->termination & TERM_SE);
15911
15912         /*
15913          * Clear Big Endian and Terminator Polarity bits and set possibly
15914          * modified termination control bits in the Microcode SCSI_CFG1
15915          * Register Value.
15916          *
15917          * Big Endian bit is not used even on big endian machines.
15918          */
15919         scsi_cfg1 &= (~BIG_ENDIAN & ~DIS_TERM_DRV & ~TERM_POL);
15920
15921         /*
15922          * Set SCSI_CFG1 Microcode Default Value
15923          *
15924          * Set possibly modified termination control bits in the Microcode
15925          * SCSI_CFG1 Register Value.
15926          *
15927          * The microcode will set the SCSI_CFG1 register using this value
15928          * after it is started below.
15929          */
15930         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1, scsi_cfg1);
15931
15932         /*
15933          * Set MEM_CFG Microcode Default Value
15934          *
15935          * The microcode will set the MEM_CFG register using this value
15936          * after it is started below.
15937          *
15938          * MEM_CFG may be accessed as a word or byte, but only bits 0-7
15939          * are defined.
15940          *
15941          * ASC-38C1600 has 32KB internal memory.
15942          *
15943          * XXX - Since ASC38C1600 Rev.3 has a Local RAM failure issue, we come
15944          * out a special 16K Adv Library and Microcode version. After the issue
15945          * resolved, we should turn back to the 32K support. Both a_condor.h and
15946          * mcode.sas files also need to be updated.
15947          *
15948          * AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
15949          *  BIOS_EN | RAM_SZ_32KB);
15950          */
15951         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
15952                          BIOS_EN | RAM_SZ_16KB);
15953
15954         /*
15955          * Set SEL_MASK Microcode Default Value
15956          *
15957          * The microcode will set the SEL_MASK register using this value
15958          * after it is started below.
15959          */
15960         AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
15961                          ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
15962
15963         /*
15964          * Build the carrier freelist.
15965          *
15966          * Driver must have already allocated memory and set 'carrier_buf'.
15967          */
15968
15969         ASC_ASSERT(asc_dvc->carrier_buf != NULL);
15970
15971         carrp = (ADV_CARR_T *) ADV_16BALIGN(asc_dvc->carrier_buf);
15972         asc_dvc->carr_freelist = NULL;
15973         if (carrp == (ADV_CARR_T *) asc_dvc->carrier_buf) {
15974                 buf_size = ADV_CARRIER_BUFSIZE;
15975         } else {
15976                 buf_size = ADV_CARRIER_BUFSIZE - sizeof(ADV_CARR_T);
15977         }
15978
15979         do {
15980                 /*
15981                  * Get physical address for the carrier 'carrp'.
15982                  */
15983                 contig_len = sizeof(ADV_CARR_T);
15984                 carr_paddr =
15985                     cpu_to_le32(DvcGetPhyAddr
15986                                 (asc_dvc, NULL, (uchar *)carrp,
15987                                  (ADV_SDCNT *)&contig_len,
15988                                  ADV_IS_CARRIER_FLAG));
15989
15990                 buf_size -= sizeof(ADV_CARR_T);
15991
15992                 /*
15993                  * If the current carrier is not physically contiguous, then
15994                  * maybe there was a page crossing. Try the next carrier aligned
15995                  * start address.
15996                  */
15997                 if (contig_len < sizeof(ADV_CARR_T)) {
15998                         carrp++;
15999                         continue;
16000                 }
16001
16002                 carrp->carr_pa = carr_paddr;
16003                 carrp->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(carrp));
16004
16005                 /*
16006                  * Insert the carrier at the beginning of the freelist.
16007                  */
16008                 carrp->next_vpa =
16009                     cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
16010                 asc_dvc->carr_freelist = carrp;
16011
16012                 carrp++;
16013         }
16014         while (buf_size > 0);
16015
16016         /*
16017          * Set-up the Host->RISC Initiator Command Queue (ICQ).
16018          */
16019         if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
16020                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
16021                 return ADV_ERROR;
16022         }
16023         asc_dvc->carr_freelist = (ADV_CARR_T *)
16024             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
16025
16026         /*
16027          * The first command issued will be placed in the stopper carrier.
16028          */
16029         asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
16030
16031         /*
16032          * Set RISC ICQ physical address start value. Initialize the
16033          * COMMA register to the same value otherwise the RISC will
16034          * prematurely detect a command is available.
16035          */
16036         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
16037         AdvWriteDWordRegister(iop_base, IOPDW_COMMA,
16038                               le32_to_cpu(asc_dvc->icq_sp->carr_pa));
16039
16040         /*
16041          * Set-up the RISC->Host Initiator Response Queue (IRQ).
16042          */
16043         if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
16044                 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
16045                 return ADV_ERROR;
16046         }
16047         asc_dvc->carr_freelist = (ADV_CARR_T *)
16048             ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
16049
16050         /*
16051          * The first command completed by the RISC will be placed in
16052          * the stopper.
16053          *
16054          * Note: Set 'next_vpa' to ASC_CQ_STOPPER. When the request is
16055          * completed the RISC will set the ASC_RQ_STOPPER bit.
16056          */
16057         asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
16058
16059         /*
16060          * Set RISC IRQ physical address start value.
16061          */
16062         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
16063         asc_dvc->carr_pending_cnt = 0;
16064
16065         AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
16066                              (ADV_INTR_ENABLE_HOST_INTR |
16067                               ADV_INTR_ENABLE_GLOBAL_INTR));
16068         AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
16069         AdvWriteWordRegister(iop_base, IOPW_PC, word);
16070
16071         /* finally, finally, gentlemen, start your engine */
16072         AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
16073
16074         /*
16075          * Reset the SCSI Bus if the EEPROM indicates that SCSI Bus
16076          * Resets should be performed. The RISC has to be running
16077          * to issue a SCSI Bus Reset.
16078          */
16079         if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
16080                 /*
16081                  * If the BIOS Signature is present in memory, restore the
16082                  * per TID microcode operating variables.
16083                  */
16084                 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
16085                     0x55AA) {
16086                         /*
16087                          * Restore per TID negotiated values.
16088                          */
16089                         AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
16090                         AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
16091                         AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
16092                         AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
16093                                          tagqng_able);
16094                         for (tid = 0; tid <= ASC_MAX_TID; tid++) {
16095                                 AdvWriteByteLram(iop_base,
16096                                                  ASC_MC_NUMBER_OF_MAX_CMD + tid,
16097                                                  max_cmd[tid]);
16098                         }
16099                 } else {
16100                         if (AdvResetSB(asc_dvc) != ADV_TRUE) {
16101                                 warn_code = ASC_WARN_BUSRESET_ERROR;
16102                         }
16103                 }
16104         }
16105
16106         return warn_code;
16107 }
16108
16109 /*
16110  * Read the board's EEPROM configuration. Set fields in ADV_DVC_VAR and
16111  * ADV_DVC_CFG based on the EEPROM settings. The chip is stopped while
16112  * all of this is done.
16113  *
16114  * On failure set the ADV_DVC_VAR field 'err_code' and return ADV_ERROR.
16115  *
16116  * For a non-fatal error return a warning code. If there are no warnings
16117  * then 0 is returned.
16118  *
16119  * Note: Chip is stopped on entry.
16120  */
16121 static int __init AdvInitFrom3550EEP(ADV_DVC_VAR *asc_dvc)
16122 {
16123         AdvPortAddr iop_base;
16124         ushort warn_code;
16125         ADVEEP_3550_CONFIG eep_config;
16126         int i;
16127
16128         iop_base = asc_dvc->iop_base;
16129
16130         warn_code = 0;
16131
16132         /*
16133          * Read the board's EEPROM configuration.
16134          *
16135          * Set default values if a bad checksum is found.
16136          */
16137         if (AdvGet3550EEPConfig(iop_base, &eep_config) != eep_config.check_sum) {
16138                 warn_code |= ASC_WARN_EEPROM_CHKSUM;
16139
16140                 /*
16141                  * Set EEPROM default values.
16142                  */
16143                 for (i = 0; i < sizeof(ADVEEP_3550_CONFIG); i++) {
16144                         *((uchar *)&eep_config + i) =
16145                             *((uchar *)&Default_3550_EEPROM_Config + i);
16146                 }
16147
16148                 /*
16149                  * Assume the 6 byte board serial number that was read
16150                  * from EEPROM is correct even if the EEPROM checksum
16151                  * failed.
16152                  */
16153                 eep_config.serial_number_word3 =
16154                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
16155
16156                 eep_config.serial_number_word2 =
16157                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
16158
16159                 eep_config.serial_number_word1 =
16160                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
16161
16162                 AdvSet3550EEPConfig(iop_base, &eep_config);
16163         }
16164         /*
16165          * Set ASC_DVC_VAR and ASC_DVC_CFG variables from the
16166          * EEPROM configuration that was read.
16167          *
16168          * This is the mapping of EEPROM fields to Adv Library fields.
16169          */
16170         asc_dvc->wdtr_able = eep_config.wdtr_able;
16171         asc_dvc->sdtr_able = eep_config.sdtr_able;
16172         asc_dvc->ultra_able = eep_config.ultra_able;
16173         asc_dvc->tagqng_able = eep_config.tagqng_able;
16174         asc_dvc->cfg->disc_enable = eep_config.disc_enable;
16175         asc_dvc->max_host_qng = eep_config.max_host_qng;
16176         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16177         asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ADV_MAX_TID);
16178         asc_dvc->start_motor = eep_config.start_motor;
16179         asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
16180         asc_dvc->bios_ctrl = eep_config.bios_ctrl;
16181         asc_dvc->no_scam = eep_config.scam_tolerant;
16182         asc_dvc->cfg->serial1 = eep_config.serial_number_word1;
16183         asc_dvc->cfg->serial2 = eep_config.serial_number_word2;
16184         asc_dvc->cfg->serial3 = eep_config.serial_number_word3;
16185
16186         /*
16187          * Set the host maximum queuing (max. 253, min. 16) and the per device
16188          * maximum queuing (max. 63, min. 4).
16189          */
16190         if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
16191                 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16192         } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
16193                 /* If the value is zero, assume it is uninitialized. */
16194                 if (eep_config.max_host_qng == 0) {
16195                         eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16196                 } else {
16197                         eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
16198                 }
16199         }
16200
16201         if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
16202                 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16203         } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
16204                 /* If the value is zero, assume it is uninitialized. */
16205                 if (eep_config.max_dvc_qng == 0) {
16206                         eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16207                 } else {
16208                         eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
16209                 }
16210         }
16211
16212         /*
16213          * If 'max_dvc_qng' is greater than 'max_host_qng', then
16214          * set 'max_dvc_qng' to 'max_host_qng'.
16215          */
16216         if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
16217                 eep_config.max_dvc_qng = eep_config.max_host_qng;
16218         }
16219
16220         /*
16221          * Set ADV_DVC_VAR 'max_host_qng' and ADV_DVC_VAR 'max_dvc_qng'
16222          * values based on possibly adjusted EEPROM values.
16223          */
16224         asc_dvc->max_host_qng = eep_config.max_host_qng;
16225         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16226
16227         /*
16228          * If the EEPROM 'termination' field is set to automatic (0), then set
16229          * the ADV_DVC_CFG 'termination' field to automatic also.
16230          *
16231          * If the termination is specified with a non-zero 'termination'
16232          * value check that a legal value is set and set the ADV_DVC_CFG
16233          * 'termination' field appropriately.
16234          */
16235         if (eep_config.termination == 0) {
16236                 asc_dvc->cfg->termination = 0;  /* auto termination */
16237         } else {
16238                 /* Enable manual control with low off / high off. */
16239                 if (eep_config.termination == 1) {
16240                         asc_dvc->cfg->termination = TERM_CTL_SEL;
16241
16242                         /* Enable manual control with low off / high on. */
16243                 } else if (eep_config.termination == 2) {
16244                         asc_dvc->cfg->termination = TERM_CTL_SEL | TERM_CTL_H;
16245
16246                         /* Enable manual control with low on / high on. */
16247                 } else if (eep_config.termination == 3) {
16248                         asc_dvc->cfg->termination =
16249                             TERM_CTL_SEL | TERM_CTL_H | TERM_CTL_L;
16250                 } else {
16251                         /*
16252                          * The EEPROM 'termination' field contains a bad value. Use
16253                          * automatic termination instead.
16254                          */
16255                         asc_dvc->cfg->termination = 0;
16256                         warn_code |= ASC_WARN_EEPROM_TERMINATION;
16257                 }
16258         }
16259
16260         return warn_code;
16261 }
16262
16263 /*
16264  * Read the board's EEPROM configuration. Set fields in ADV_DVC_VAR and
16265  * ADV_DVC_CFG based on the EEPROM settings. The chip is stopped while
16266  * all of this is done.
16267  *
16268  * On failure set the ADV_DVC_VAR field 'err_code' and return ADV_ERROR.
16269  *
16270  * For a non-fatal error return a warning code. If there are no warnings
16271  * then 0 is returned.
16272  *
16273  * Note: Chip is stopped on entry.
16274  */
16275 static int __init AdvInitFrom38C0800EEP(ADV_DVC_VAR *asc_dvc)
16276 {
16277         AdvPortAddr iop_base;
16278         ushort warn_code;
16279         ADVEEP_38C0800_CONFIG eep_config;
16280         int i;
16281         uchar tid, termination;
16282         ushort sdtr_speed = 0;
16283
16284         iop_base = asc_dvc->iop_base;
16285
16286         warn_code = 0;
16287
16288         /*
16289          * Read the board's EEPROM configuration.
16290          *
16291          * Set default values if a bad checksum is found.
16292          */
16293         if (AdvGet38C0800EEPConfig(iop_base, &eep_config) !=
16294             eep_config.check_sum) {
16295                 warn_code |= ASC_WARN_EEPROM_CHKSUM;
16296
16297                 /*
16298                  * Set EEPROM default values.
16299                  */
16300                 for (i = 0; i < sizeof(ADVEEP_38C0800_CONFIG); i++) {
16301                         *((uchar *)&eep_config + i) =
16302                             *((uchar *)&Default_38C0800_EEPROM_Config + i);
16303                 }
16304
16305                 /*
16306                  * Assume the 6 byte board serial number that was read
16307                  * from EEPROM is correct even if the EEPROM checksum
16308                  * failed.
16309                  */
16310                 eep_config.serial_number_word3 =
16311                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
16312
16313                 eep_config.serial_number_word2 =
16314                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
16315
16316                 eep_config.serial_number_word1 =
16317                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
16318
16319                 AdvSet38C0800EEPConfig(iop_base, &eep_config);
16320         }
16321         /*
16322          * Set ADV_DVC_VAR and ADV_DVC_CFG variables from the
16323          * EEPROM configuration that was read.
16324          *
16325          * This is the mapping of EEPROM fields to Adv Library fields.
16326          */
16327         asc_dvc->wdtr_able = eep_config.wdtr_able;
16328         asc_dvc->sdtr_speed1 = eep_config.sdtr_speed1;
16329         asc_dvc->sdtr_speed2 = eep_config.sdtr_speed2;
16330         asc_dvc->sdtr_speed3 = eep_config.sdtr_speed3;
16331         asc_dvc->sdtr_speed4 = eep_config.sdtr_speed4;
16332         asc_dvc->tagqng_able = eep_config.tagqng_able;
16333         asc_dvc->cfg->disc_enable = eep_config.disc_enable;
16334         asc_dvc->max_host_qng = eep_config.max_host_qng;
16335         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16336         asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ADV_MAX_TID);
16337         asc_dvc->start_motor = eep_config.start_motor;
16338         asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
16339         asc_dvc->bios_ctrl = eep_config.bios_ctrl;
16340         asc_dvc->no_scam = eep_config.scam_tolerant;
16341         asc_dvc->cfg->serial1 = eep_config.serial_number_word1;
16342         asc_dvc->cfg->serial2 = eep_config.serial_number_word2;
16343         asc_dvc->cfg->serial3 = eep_config.serial_number_word3;
16344
16345         /*
16346          * For every Target ID if any of its 'sdtr_speed[1234]' bits
16347          * are set, then set an 'sdtr_able' bit for it.
16348          */
16349         asc_dvc->sdtr_able = 0;
16350         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
16351                 if (tid == 0) {
16352                         sdtr_speed = asc_dvc->sdtr_speed1;
16353                 } else if (tid == 4) {
16354                         sdtr_speed = asc_dvc->sdtr_speed2;
16355                 } else if (tid == 8) {
16356                         sdtr_speed = asc_dvc->sdtr_speed3;
16357                 } else if (tid == 12) {
16358                         sdtr_speed = asc_dvc->sdtr_speed4;
16359                 }
16360                 if (sdtr_speed & ADV_MAX_TID) {
16361                         asc_dvc->sdtr_able |= (1 << tid);
16362                 }
16363                 sdtr_speed >>= 4;
16364         }
16365
16366         /*
16367          * Set the host maximum queuing (max. 253, min. 16) and the per device
16368          * maximum queuing (max. 63, min. 4).
16369          */
16370         if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
16371                 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16372         } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
16373                 /* If the value is zero, assume it is uninitialized. */
16374                 if (eep_config.max_host_qng == 0) {
16375                         eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16376                 } else {
16377                         eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
16378                 }
16379         }
16380
16381         if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
16382                 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16383         } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
16384                 /* If the value is zero, assume it is uninitialized. */
16385                 if (eep_config.max_dvc_qng == 0) {
16386                         eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16387                 } else {
16388                         eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
16389                 }
16390         }
16391
16392         /*
16393          * If 'max_dvc_qng' is greater than 'max_host_qng', then
16394          * set 'max_dvc_qng' to 'max_host_qng'.
16395          */
16396         if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
16397                 eep_config.max_dvc_qng = eep_config.max_host_qng;
16398         }
16399
16400         /*
16401          * Set ADV_DVC_VAR 'max_host_qng' and ADV_DVC_VAR 'max_dvc_qng'
16402          * values based on possibly adjusted EEPROM values.
16403          */
16404         asc_dvc->max_host_qng = eep_config.max_host_qng;
16405         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16406
16407         /*
16408          * If the EEPROM 'termination' field is set to automatic (0), then set
16409          * the ADV_DVC_CFG 'termination' field to automatic also.
16410          *
16411          * If the termination is specified with a non-zero 'termination'
16412          * value check that a legal value is set and set the ADV_DVC_CFG
16413          * 'termination' field appropriately.
16414          */
16415         if (eep_config.termination_se == 0) {
16416                 termination = 0;        /* auto termination for SE */
16417         } else {
16418                 /* Enable manual control with low off / high off. */
16419                 if (eep_config.termination_se == 1) {
16420                         termination = 0;
16421
16422                         /* Enable manual control with low off / high on. */
16423                 } else if (eep_config.termination_se == 2) {
16424                         termination = TERM_SE_HI;
16425
16426                         /* Enable manual control with low on / high on. */
16427                 } else if (eep_config.termination_se == 3) {
16428                         termination = TERM_SE;
16429                 } else {
16430                         /*
16431                          * The EEPROM 'termination_se' field contains a bad value.
16432                          * Use automatic termination instead.
16433                          */
16434                         termination = 0;
16435                         warn_code |= ASC_WARN_EEPROM_TERMINATION;
16436                 }
16437         }
16438
16439         if (eep_config.termination_lvd == 0) {
16440                 asc_dvc->cfg->termination = termination;        /* auto termination for LVD */
16441         } else {
16442                 /* Enable manual control with low off / high off. */
16443                 if (eep_config.termination_lvd == 1) {
16444                         asc_dvc->cfg->termination = termination;
16445
16446                         /* Enable manual control with low off / high on. */
16447                 } else if (eep_config.termination_lvd == 2) {
16448                         asc_dvc->cfg->termination = termination | TERM_LVD_HI;
16449
16450                         /* Enable manual control with low on / high on. */
16451                 } else if (eep_config.termination_lvd == 3) {
16452                         asc_dvc->cfg->termination = termination | TERM_LVD;
16453                 } else {
16454                         /*
16455                          * The EEPROM 'termination_lvd' field contains a bad value.
16456                          * Use automatic termination instead.
16457                          */
16458                         asc_dvc->cfg->termination = termination;
16459                         warn_code |= ASC_WARN_EEPROM_TERMINATION;
16460                 }
16461         }
16462
16463         return warn_code;
16464 }
16465
16466 /*
16467  * Read the board's EEPROM configuration. Set fields in ASC_DVC_VAR and
16468  * ASC_DVC_CFG based on the EEPROM settings. The chip is stopped while
16469  * all of this is done.
16470  *
16471  * On failure set the ASC_DVC_VAR field 'err_code' and return ADV_ERROR.
16472  *
16473  * For a non-fatal error return a warning code. If there are no warnings
16474  * then 0 is returned.
16475  *
16476  * Note: Chip is stopped on entry.
16477  */
16478 static int __init AdvInitFrom38C1600EEP(ADV_DVC_VAR *asc_dvc)
16479 {
16480         AdvPortAddr iop_base;
16481         ushort warn_code;
16482         ADVEEP_38C1600_CONFIG eep_config;
16483         int i;
16484         uchar tid, termination;
16485         ushort sdtr_speed = 0;
16486
16487         iop_base = asc_dvc->iop_base;
16488
16489         warn_code = 0;
16490
16491         /*
16492          * Read the board's EEPROM configuration.
16493          *
16494          * Set default values if a bad checksum is found.
16495          */
16496         if (AdvGet38C1600EEPConfig(iop_base, &eep_config) !=
16497             eep_config.check_sum) {
16498                 warn_code |= ASC_WARN_EEPROM_CHKSUM;
16499
16500                 /*
16501                  * Set EEPROM default values.
16502                  */
16503                 for (i = 0; i < sizeof(ADVEEP_38C1600_CONFIG); i++) {
16504                         if (i == 1
16505                             && ASC_PCI_ID2FUNC(asc_dvc->cfg->pci_slot_info) !=
16506                             0) {
16507                                 /*
16508                                  * Set Function 1 EEPROM Word 0 MSB
16509                                  *
16510                                  * Clear the BIOS_ENABLE (bit 14) and INTAB (bit 11)
16511                                  * EEPROM bits.
16512                                  *
16513                                  * Disable Bit 14 (BIOS_ENABLE) to fix SPARC Ultra 60 and
16514                                  * old Mac system booting problem. The Expansion ROM must
16515                                  * be disabled in Function 1 for these systems.
16516                                  *
16517                                  */
16518                                 *((uchar *)&eep_config + i) =
16519                                     ((*
16520                                       ((uchar *)&Default_38C1600_EEPROM_Config
16521                                        +
16522                                        i)) &
16523                                      (~
16524                                       (((ADV_EEPROM_BIOS_ENABLE |
16525                                          ADV_EEPROM_INTAB) >> 8) & 0xFF)));
16526
16527                                 /*
16528                                  * Set the INTAB (bit 11) if the GPIO 0 input indicates
16529                                  * the Function 1 interrupt line is wired to INTA.
16530                                  *
16531                                  * Set/Clear Bit 11 (INTAB) from the GPIO bit 0 input:
16532                                  *   1 - Function 1 interrupt line wired to INT A.
16533                                  *   0 - Function 1 interrupt line wired to INT B.
16534                                  *
16535                                  * Note: Adapter boards always have Function 0 wired to INTA.
16536                                  * Put all 5 GPIO bits in input mode and then read
16537                                  * their input values.
16538                                  */
16539                                 AdvWriteByteRegister(iop_base, IOPB_GPIO_CNTL,
16540                                                      0);
16541                                 if (AdvReadByteRegister
16542                                     (iop_base, IOPB_GPIO_DATA) & 0x01) {
16543                                         /* Function 1 interrupt wired to INTA; Set EEPROM bit. */
16544                                         *((uchar *)&eep_config + i) |=
16545                                             ((ADV_EEPROM_INTAB >> 8) & 0xFF);
16546                                 }
16547                         } else {
16548                                 *((uchar *)&eep_config + i) =
16549                                     *((uchar *)&Default_38C1600_EEPROM_Config
16550                                       + i);
16551                         }
16552                 }
16553
16554                 /*
16555                  * Assume the 6 byte board serial number that was read
16556                  * from EEPROM is correct even if the EEPROM checksum
16557                  * failed.
16558                  */
16559                 eep_config.serial_number_word3 =
16560                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
16561
16562                 eep_config.serial_number_word2 =
16563                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
16564
16565                 eep_config.serial_number_word1 =
16566                     AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
16567
16568                 AdvSet38C1600EEPConfig(iop_base, &eep_config);
16569         }
16570
16571         /*
16572          * Set ASC_DVC_VAR and ASC_DVC_CFG variables from the
16573          * EEPROM configuration that was read.
16574          *
16575          * This is the mapping of EEPROM fields to Adv Library fields.
16576          */
16577         asc_dvc->wdtr_able = eep_config.wdtr_able;
16578         asc_dvc->sdtr_speed1 = eep_config.sdtr_speed1;
16579         asc_dvc->sdtr_speed2 = eep_config.sdtr_speed2;
16580         asc_dvc->sdtr_speed3 = eep_config.sdtr_speed3;
16581         asc_dvc->sdtr_speed4 = eep_config.sdtr_speed4;
16582         asc_dvc->ppr_able = 0;
16583         asc_dvc->tagqng_able = eep_config.tagqng_able;
16584         asc_dvc->cfg->disc_enable = eep_config.disc_enable;
16585         asc_dvc->max_host_qng = eep_config.max_host_qng;
16586         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16587         asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ASC_MAX_TID);
16588         asc_dvc->start_motor = eep_config.start_motor;
16589         asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
16590         asc_dvc->bios_ctrl = eep_config.bios_ctrl;
16591         asc_dvc->no_scam = eep_config.scam_tolerant;
16592
16593         /*
16594          * For every Target ID if any of its 'sdtr_speed[1234]' bits
16595          * are set, then set an 'sdtr_able' bit for it.
16596          */
16597         asc_dvc->sdtr_able = 0;
16598         for (tid = 0; tid <= ASC_MAX_TID; tid++) {
16599                 if (tid == 0) {
16600                         sdtr_speed = asc_dvc->sdtr_speed1;
16601                 } else if (tid == 4) {
16602                         sdtr_speed = asc_dvc->sdtr_speed2;
16603                 } else if (tid == 8) {
16604                         sdtr_speed = asc_dvc->sdtr_speed3;
16605                 } else if (tid == 12) {
16606                         sdtr_speed = asc_dvc->sdtr_speed4;
16607                 }
16608                 if (sdtr_speed & ASC_MAX_TID) {
16609                         asc_dvc->sdtr_able |= (1 << tid);
16610                 }
16611                 sdtr_speed >>= 4;
16612         }
16613
16614         /*
16615          * Set the host maximum queuing (max. 253, min. 16) and the per device
16616          * maximum queuing (max. 63, min. 4).
16617          */
16618         if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
16619                 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16620         } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
16621                 /* If the value is zero, assume it is uninitialized. */
16622                 if (eep_config.max_host_qng == 0) {
16623                         eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
16624                 } else {
16625                         eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
16626                 }
16627         }
16628
16629         if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
16630                 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16631         } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
16632                 /* If the value is zero, assume it is uninitialized. */
16633                 if (eep_config.max_dvc_qng == 0) {
16634                         eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
16635                 } else {
16636                         eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
16637                 }
16638         }
16639
16640         /*
16641          * If 'max_dvc_qng' is greater than 'max_host_qng', then
16642          * set 'max_dvc_qng' to 'max_host_qng'.
16643          */
16644         if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
16645                 eep_config.max_dvc_qng = eep_config.max_host_qng;
16646         }
16647
16648         /*
16649          * Set ASC_DVC_VAR 'max_host_qng' and ASC_DVC_VAR 'max_dvc_qng'
16650          * values based on possibly adjusted EEPROM values.
16651          */
16652         asc_dvc->max_host_qng = eep_config.max_host_qng;
16653         asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
16654
16655         /*
16656          * If the EEPROM 'termination' field is set to automatic (0), then set
16657          * the ASC_DVC_CFG 'termination' field to automatic also.
16658          *
16659          * If the termination is specified with a non-zero 'termination'
16660          * value check that a legal value is set and set the ASC_DVC_CFG
16661          * 'termination' field appropriately.
16662          */
16663         if (eep_config.termination_se == 0) {
16664                 termination = 0;        /* auto termination for SE */
16665         } else {
16666                 /* Enable manual control with low off / high off. */
16667                 if (eep_config.termination_se == 1) {
16668                         termination = 0;
16669
16670                         /* Enable manual control with low off / high on. */
16671                 } else if (eep_config.termination_se == 2) {
16672                         termination = TERM_SE_HI;
16673
16674                         /* Enable manual control with low on / high on. */
16675                 } else if (eep_config.termination_se == 3) {
16676                         termination = TERM_SE;
16677                 } else {
16678                         /*
16679                          * The EEPROM 'termination_se' field contains a bad value.
16680                          * Use automatic termination instead.
16681                          */
16682                         termination = 0;
16683                         warn_code |= ASC_WARN_EEPROM_TERMINATION;
16684                 }
16685         }
16686
16687         if (eep_config.termination_lvd == 0) {
16688                 asc_dvc->cfg->termination = termination;        /* auto termination for LVD */
16689         } else {
16690                 /* Enable manual control with low off / high off. */
16691                 if (eep_config.termination_lvd == 1) {
16692                         asc_dvc->cfg->termination = termination;
16693
16694                         /* Enable manual control with low off / high on. */
16695                 } else if (eep_config.termination_lvd == 2) {
16696                         asc_dvc->cfg->termination = termination | TERM_LVD_HI;
16697
16698                         /* Enable manual control with low on / high on. */
16699                 } else if (eep_config.termination_lvd == 3) {
16700                         asc_dvc->cfg->termination = termination | TERM_LVD;
16701                 } else {
16702                         /*
16703                          * The EEPROM 'termination_lvd' field contains a bad value.
16704                          * Use automatic termination instead.
16705                          */
16706                         asc_dvc->cfg->termination = termination;
16707                         warn_code |= ASC_WARN_EEPROM_TERMINATION;
16708                 }
16709         }
16710
16711         return warn_code;
16712 }
16713
16714 /*
16715  * Read EEPROM configuration into the specified buffer.
16716  *
16717  * Return a checksum based on the EEPROM configuration read.
16718  */
16719 static ushort __init
16720 AdvGet3550EEPConfig(AdvPortAddr iop_base, ADVEEP_3550_CONFIG *cfg_buf)
16721 {
16722         ushort wval, chksum;
16723         ushort *wbuf;
16724         int eep_addr;
16725         ushort *charfields;
16726
16727         charfields = (ushort *)&ADVEEP_3550_Config_Field_IsChar;
16728         wbuf = (ushort *)cfg_buf;
16729         chksum = 0;
16730
16731         for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
16732              eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
16733                 wval = AdvReadEEPWord(iop_base, eep_addr);
16734                 chksum += wval; /* Checksum is calculated from word values. */
16735                 if (*charfields++) {
16736                         *wbuf = le16_to_cpu(wval);
16737                 } else {
16738                         *wbuf = wval;
16739                 }
16740         }
16741         /* Read checksum word. */
16742         *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16743         wbuf++;
16744         charfields++;
16745
16746         /* Read rest of EEPROM not covered by the checksum. */
16747         for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
16748              eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
16749                 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16750                 if (*charfields++) {
16751                         *wbuf = le16_to_cpu(*wbuf);
16752                 }
16753         }
16754         return chksum;
16755 }
16756
16757 /*
16758  * Read EEPROM configuration into the specified buffer.
16759  *
16760  * Return a checksum based on the EEPROM configuration read.
16761  */
16762 static ushort __init
16763 AdvGet38C0800EEPConfig(AdvPortAddr iop_base, ADVEEP_38C0800_CONFIG *cfg_buf)
16764 {
16765         ushort wval, chksum;
16766         ushort *wbuf;
16767         int eep_addr;
16768         ushort *charfields;
16769
16770         charfields = (ushort *)&ADVEEP_38C0800_Config_Field_IsChar;
16771         wbuf = (ushort *)cfg_buf;
16772         chksum = 0;
16773
16774         for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
16775              eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
16776                 wval = AdvReadEEPWord(iop_base, eep_addr);
16777                 chksum += wval; /* Checksum is calculated from word values. */
16778                 if (*charfields++) {
16779                         *wbuf = le16_to_cpu(wval);
16780                 } else {
16781                         *wbuf = wval;
16782                 }
16783         }
16784         /* Read checksum word. */
16785         *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16786         wbuf++;
16787         charfields++;
16788
16789         /* Read rest of EEPROM not covered by the checksum. */
16790         for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
16791              eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
16792                 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16793                 if (*charfields++) {
16794                         *wbuf = le16_to_cpu(*wbuf);
16795                 }
16796         }
16797         return chksum;
16798 }
16799
16800 /*
16801  * Read EEPROM configuration into the specified buffer.
16802  *
16803  * Return a checksum based on the EEPROM configuration read.
16804  */
16805 static ushort __init
16806 AdvGet38C1600EEPConfig(AdvPortAddr iop_base, ADVEEP_38C1600_CONFIG *cfg_buf)
16807 {
16808         ushort wval, chksum;
16809         ushort *wbuf;
16810         int eep_addr;
16811         ushort *charfields;
16812
16813         charfields = (ushort *)&ADVEEP_38C1600_Config_Field_IsChar;
16814         wbuf = (ushort *)cfg_buf;
16815         chksum = 0;
16816
16817         for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
16818              eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
16819                 wval = AdvReadEEPWord(iop_base, eep_addr);
16820                 chksum += wval; /* Checksum is calculated from word values. */
16821                 if (*charfields++) {
16822                         *wbuf = le16_to_cpu(wval);
16823                 } else {
16824                         *wbuf = wval;
16825                 }
16826         }
16827         /* Read checksum word. */
16828         *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16829         wbuf++;
16830         charfields++;
16831
16832         /* Read rest of EEPROM not covered by the checksum. */
16833         for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
16834              eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
16835                 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
16836                 if (*charfields++) {
16837                         *wbuf = le16_to_cpu(*wbuf);
16838                 }
16839         }
16840         return chksum;
16841 }
16842
16843 /*
16844  * Read the EEPROM from specified location
16845  */
16846 static ushort __init AdvReadEEPWord(AdvPortAddr iop_base, int eep_word_addr)
16847 {
16848         AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
16849                              ASC_EEP_CMD_READ | eep_word_addr);
16850         AdvWaitEEPCmd(iop_base);
16851         return AdvReadWordRegister(iop_base, IOPW_EE_DATA);
16852 }
16853
16854 /*
16855  * Wait for EEPROM command to complete
16856  */
16857 static void __init AdvWaitEEPCmd(AdvPortAddr iop_base)
16858 {
16859         int eep_delay_ms;
16860
16861         for (eep_delay_ms = 0; eep_delay_ms < ADV_EEP_DELAY_MS; eep_delay_ms++) {
16862                 if (AdvReadWordRegister(iop_base, IOPW_EE_CMD) &
16863                     ASC_EEP_CMD_DONE) {
16864                         break;
16865                 }
16866                 DvcSleepMilliSecond(1);
16867         }
16868         if ((AdvReadWordRegister(iop_base, IOPW_EE_CMD) & ASC_EEP_CMD_DONE) ==
16869             0) {
16870                 ASC_ASSERT(0);
16871         }
16872         return;
16873 }
16874
16875 /*
16876  * Write the EEPROM from 'cfg_buf'.
16877  */
16878 void __init
16879 AdvSet3550EEPConfig(AdvPortAddr iop_base, ADVEEP_3550_CONFIG *cfg_buf)
16880 {
16881         ushort *wbuf;
16882         ushort addr, chksum;
16883         ushort *charfields;
16884
16885         wbuf = (ushort *)cfg_buf;
16886         charfields = (ushort *)&ADVEEP_3550_Config_Field_IsChar;
16887         chksum = 0;
16888
16889         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
16890         AdvWaitEEPCmd(iop_base);
16891
16892         /*
16893          * Write EEPROM from word 0 to word 20.
16894          */
16895         for (addr = ADV_EEP_DVC_CFG_BEGIN;
16896              addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
16897                 ushort word;
16898
16899                 if (*charfields++) {
16900                         word = cpu_to_le16(*wbuf);
16901                 } else {
16902                         word = *wbuf;
16903                 }
16904                 chksum += *wbuf;        /* Checksum is calculated from word values. */
16905                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
16906                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
16907                                      ASC_EEP_CMD_WRITE | addr);
16908                 AdvWaitEEPCmd(iop_base);
16909                 DvcSleepMilliSecond(ADV_EEP_DELAY_MS);
16910         }
16911
16912         /*
16913          * Write EEPROM checksum at word 21.
16914          */
16915         AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
16916         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
16917         AdvWaitEEPCmd(iop_base);
16918         wbuf++;
16919         charfields++;
16920
16921         /*
16922          * Write EEPROM OEM name at words 22 to 29.
16923          */
16924         for (addr = ADV_EEP_DVC_CTL_BEGIN;
16925              addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
16926                 ushort word;
16927
16928                 if (*charfields++) {
16929                         word = cpu_to_le16(*wbuf);
16930                 } else {
16931                         word = *wbuf;
16932                 }
16933                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
16934                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
16935                                      ASC_EEP_CMD_WRITE | addr);
16936                 AdvWaitEEPCmd(iop_base);
16937         }
16938         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
16939         AdvWaitEEPCmd(iop_base);
16940         return;
16941 }
16942
16943 /*
16944  * Write the EEPROM from 'cfg_buf'.
16945  */
16946 void __init
16947 AdvSet38C0800EEPConfig(AdvPortAddr iop_base, ADVEEP_38C0800_CONFIG *cfg_buf)
16948 {
16949         ushort *wbuf;
16950         ushort *charfields;
16951         ushort addr, chksum;
16952
16953         wbuf = (ushort *)cfg_buf;
16954         charfields = (ushort *)&ADVEEP_38C0800_Config_Field_IsChar;
16955         chksum = 0;
16956
16957         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
16958         AdvWaitEEPCmd(iop_base);
16959
16960         /*
16961          * Write EEPROM from word 0 to word 20.
16962          */
16963         for (addr = ADV_EEP_DVC_CFG_BEGIN;
16964              addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
16965                 ushort word;
16966
16967                 if (*charfields++) {
16968                         word = cpu_to_le16(*wbuf);
16969                 } else {
16970                         word = *wbuf;
16971                 }
16972                 chksum += *wbuf;        /* Checksum is calculated from word values. */
16973                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
16974                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
16975                                      ASC_EEP_CMD_WRITE | addr);
16976                 AdvWaitEEPCmd(iop_base);
16977                 DvcSleepMilliSecond(ADV_EEP_DELAY_MS);
16978         }
16979
16980         /*
16981          * Write EEPROM checksum at word 21.
16982          */
16983         AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
16984         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
16985         AdvWaitEEPCmd(iop_base);
16986         wbuf++;
16987         charfields++;
16988
16989         /*
16990          * Write EEPROM OEM name at words 22 to 29.
16991          */
16992         for (addr = ADV_EEP_DVC_CTL_BEGIN;
16993              addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
16994                 ushort word;
16995
16996                 if (*charfields++) {
16997                         word = cpu_to_le16(*wbuf);
16998                 } else {
16999                         word = *wbuf;
17000                 }
17001                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
17002                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
17003                                      ASC_EEP_CMD_WRITE | addr);
17004                 AdvWaitEEPCmd(iop_base);
17005         }
17006         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
17007         AdvWaitEEPCmd(iop_base);
17008         return;
17009 }
17010
17011 /*
17012  * Write the EEPROM from 'cfg_buf'.
17013  */
17014 void __init
17015 AdvSet38C1600EEPConfig(AdvPortAddr iop_base, ADVEEP_38C1600_CONFIG *cfg_buf)
17016 {
17017         ushort *wbuf;
17018         ushort *charfields;
17019         ushort addr, chksum;
17020
17021         wbuf = (ushort *)cfg_buf;
17022         charfields = (ushort *)&ADVEEP_38C1600_Config_Field_IsChar;
17023         chksum = 0;
17024
17025         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
17026         AdvWaitEEPCmd(iop_base);
17027
17028         /*
17029          * Write EEPROM from word 0 to word 20.
17030          */
17031         for (addr = ADV_EEP_DVC_CFG_BEGIN;
17032              addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
17033                 ushort word;
17034
17035                 if (*charfields++) {
17036                         word = cpu_to_le16(*wbuf);
17037                 } else {
17038                         word = *wbuf;
17039                 }
17040                 chksum += *wbuf;        /* Checksum is calculated from word values. */
17041                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
17042                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
17043                                      ASC_EEP_CMD_WRITE | addr);
17044                 AdvWaitEEPCmd(iop_base);
17045                 DvcSleepMilliSecond(ADV_EEP_DELAY_MS);
17046         }
17047
17048         /*
17049          * Write EEPROM checksum at word 21.
17050          */
17051         AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
17052         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
17053         AdvWaitEEPCmd(iop_base);
17054         wbuf++;
17055         charfields++;
17056
17057         /*
17058          * Write EEPROM OEM name at words 22 to 29.
17059          */
17060         for (addr = ADV_EEP_DVC_CTL_BEGIN;
17061              addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
17062                 ushort word;
17063
17064                 if (*charfields++) {
17065                         word = cpu_to_le16(*wbuf);
17066                 } else {
17067                         word = *wbuf;
17068                 }
17069                 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
17070                 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
17071                                      ASC_EEP_CMD_WRITE | addr);
17072                 AdvWaitEEPCmd(iop_base);
17073         }
17074         AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
17075         AdvWaitEEPCmd(iop_base);
17076         return;
17077 }
17078
17079 /* a_advlib.c */
17080 /*
17081  * AdvExeScsiQueue() - Send a request to the RISC microcode program.
17082  *
17083  *   Allocate a carrier structure, point the carrier to the ADV_SCSI_REQ_Q,
17084  *   add the carrier to the ICQ (Initiator Command Queue), and tickle the
17085  *   RISC to notify it a new command is ready to be executed.
17086  *
17087  * If 'done_status' is not set to QD_DO_RETRY, then 'error_retry' will be
17088  * set to SCSI_MAX_RETRY.
17089  *
17090  * Multi-byte fields in the ASC_SCSI_REQ_Q that are used by the microcode
17091  * for DMA addresses or math operations are byte swapped to little-endian
17092  * order.
17093  *
17094  * Return:
17095  *      ADV_SUCCESS(1) - The request was successfully queued.
17096  *      ADV_BUSY(0) -    Resource unavailable; Retry again after pending
17097  *                       request completes.
17098  *      ADV_ERROR(-1) -  Invalid ADV_SCSI_REQ_Q request structure
17099  *                       host IC error.
17100  */
17101 static int AdvExeScsiQueue(ADV_DVC_VAR *asc_dvc, ADV_SCSI_REQ_Q *scsiq)
17102 {
17103         ulong last_int_level;
17104         AdvPortAddr iop_base;
17105         ADV_DCNT req_size;
17106         ADV_PADDR req_paddr;
17107         ADV_CARR_T *new_carrp;
17108
17109         ASC_ASSERT(scsiq != NULL);      /* 'scsiq' should never be NULL. */
17110
17111         /*
17112          * The ADV_SCSI_REQ_Q 'target_id' field should never exceed ADV_MAX_TID.
17113          */
17114         if (scsiq->target_id > ADV_MAX_TID) {
17115                 scsiq->host_status = QHSTA_M_INVALID_DEVICE;
17116                 scsiq->done_status = QD_WITH_ERROR;
17117                 return ADV_ERROR;
17118         }
17119
17120         iop_base = asc_dvc->iop_base;
17121
17122         last_int_level = DvcEnterCritical();
17123
17124         /*
17125          * Allocate a carrier ensuring at least one carrier always
17126          * remains on the freelist and initialize fields.
17127          */
17128         if ((new_carrp = asc_dvc->carr_freelist) == NULL) {
17129                 DvcLeaveCritical(last_int_level);
17130                 return ADV_BUSY;
17131         }
17132         asc_dvc->carr_freelist = (ADV_CARR_T *)
17133             ADV_U32_TO_VADDR(le32_to_cpu(new_carrp->next_vpa));
17134         asc_dvc->carr_pending_cnt++;
17135
17136         /*
17137          * Set the carrier to be a stopper by setting 'next_vpa'
17138          * to the stopper value. The current stopper will be changed
17139          * below to point to the new stopper.
17140          */
17141         new_carrp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
17142
17143         /*
17144          * Clear the ADV_SCSI_REQ_Q done flag.
17145          */
17146         scsiq->a_flag &= ~ADV_SCSIQ_DONE;
17147
17148         req_size = sizeof(ADV_SCSI_REQ_Q);
17149         req_paddr = DvcGetPhyAddr(asc_dvc, scsiq, (uchar *)scsiq,
17150                                   (ADV_SDCNT *)&req_size, ADV_IS_SCSIQ_FLAG);
17151
17152         ASC_ASSERT(ADV_32BALIGN(req_paddr) == req_paddr);
17153         ASC_ASSERT(req_size >= sizeof(ADV_SCSI_REQ_Q));
17154
17155         /* Wait for assertion before making little-endian */
17156         req_paddr = cpu_to_le32(req_paddr);
17157
17158         /* Save virtual and physical address of ADV_SCSI_REQ_Q and carrier. */
17159         scsiq->scsiq_ptr = cpu_to_le32(ADV_VADDR_TO_U32(scsiq));
17160         scsiq->scsiq_rptr = req_paddr;
17161
17162         scsiq->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->icq_sp));
17163         /*
17164          * Every ADV_CARR_T.carr_pa is byte swapped to little-endian
17165          * order during initialization.
17166          */
17167         scsiq->carr_pa = asc_dvc->icq_sp->carr_pa;
17168
17169         /*
17170          * Use the current stopper to send the ADV_SCSI_REQ_Q command to
17171          * the microcode. The newly allocated stopper will become the new
17172          * stopper.
17173          */
17174         asc_dvc->icq_sp->areq_vpa = req_paddr;
17175
17176         /*
17177          * Set the 'next_vpa' pointer for the old stopper to be the
17178          * physical address of the new stopper. The RISC can only
17179          * follow physical addresses.
17180          */
17181         asc_dvc->icq_sp->next_vpa = new_carrp->carr_pa;
17182
17183         /*
17184          * Set the host adapter stopper pointer to point to the new carrier.
17185          */
17186         asc_dvc->icq_sp = new_carrp;
17187
17188         if (asc_dvc->chip_type == ADV_CHIP_ASC3550 ||
17189             asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
17190                 /*
17191                  * Tickle the RISC to tell it to read its Command Queue Head pointer.
17192                  */
17193                 AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_A);
17194                 if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
17195                         /*
17196                          * Clear the tickle value. In the ASC-3550 the RISC flag
17197                          * command 'clr_tickle_a' does not work unless the host
17198                          * value is cleared.
17199                          */
17200                         AdvWriteByteRegister(iop_base, IOPB_TICKLE,
17201                                              ADV_TICKLE_NOP);
17202                 }
17203         } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
17204                 /*
17205                  * Notify the RISC a carrier is ready by writing the physical
17206                  * address of the new carrier stopper to the COMMA register.
17207                  */
17208                 AdvWriteDWordRegister(iop_base, IOPDW_COMMA,
17209                                       le32_to_cpu(new_carrp->carr_pa));
17210         }
17211
17212         DvcLeaveCritical(last_int_level);
17213
17214         return ADV_SUCCESS;
17215 }
17216
17217 /*
17218  * Reset SCSI Bus and purge all outstanding requests.
17219  *
17220  * Return Value:
17221  *      ADV_TRUE(1) -   All requests are purged and SCSI Bus is reset.
17222  *      ADV_FALSE(0) -  Microcode command failed.
17223  *      ADV_ERROR(-1) - Microcode command timed-out. Microcode or IC
17224  *                      may be hung which requires driver recovery.
17225  */
17226 static int AdvResetSB(ADV_DVC_VAR *asc_dvc)
17227 {
17228         int status;
17229
17230         /*
17231          * Send the SCSI Bus Reset idle start idle command which asserts
17232          * the SCSI Bus Reset signal.
17233          */
17234         status = AdvSendIdleCmd(asc_dvc, (ushort)IDLE_CMD_SCSI_RESET_START, 0L);
17235         if (status != ADV_TRUE) {
17236                 return status;
17237         }
17238
17239         /*
17240          * Delay for the specified SCSI Bus Reset hold time.
17241          *
17242          * The hold time delay is done on the host because the RISC has no
17243          * microsecond accurate timer.
17244          */
17245         DvcDelayMicroSecond(asc_dvc, (ushort)ASC_SCSI_RESET_HOLD_TIME_US);
17246
17247         /*
17248          * Send the SCSI Bus Reset end idle command which de-asserts
17249          * the SCSI Bus Reset signal and purges any pending requests.
17250          */
17251         status = AdvSendIdleCmd(asc_dvc, (ushort)IDLE_CMD_SCSI_RESET_END, 0L);
17252         if (status != ADV_TRUE) {
17253                 return status;
17254         }
17255
17256         DvcSleepMilliSecond((ADV_DCNT)asc_dvc->scsi_reset_wait * 1000);
17257
17258         return status;
17259 }
17260
17261 /*
17262  * Reset chip and SCSI Bus.
17263  *
17264  * Return Value:
17265  *      ADV_TRUE(1) -   Chip re-initialization and SCSI Bus Reset successful.
17266  *      ADV_FALSE(0) -  Chip re-initialization and SCSI Bus Reset failure.
17267  */
17268 static int AdvResetChipAndSB(ADV_DVC_VAR *asc_dvc)
17269 {
17270         int status;
17271         ushort wdtr_able, sdtr_able, tagqng_able;
17272         ushort ppr_able = 0;
17273         uchar tid, max_cmd[ADV_MAX_TID + 1];
17274         AdvPortAddr iop_base;
17275         ushort bios_sig;
17276
17277         iop_base = asc_dvc->iop_base;
17278
17279         /*
17280          * Save current per TID negotiated values.
17281          */
17282         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
17283         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
17284         if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
17285                 AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
17286         }
17287         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
17288         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
17289                 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
17290                                 max_cmd[tid]);
17291         }
17292
17293         /*
17294          * Force the AdvInitAsc3550/38C0800Driver() function to
17295          * perform a SCSI Bus Reset by clearing the BIOS signature word.
17296          * The initialization functions assumes a SCSI Bus Reset is not
17297          * needed if the BIOS signature word is present.
17298          */
17299         AdvReadWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, bios_sig);
17300         AdvWriteWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, 0);
17301
17302         /*
17303          * Stop chip and reset it.
17304          */
17305         AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_STOP);
17306         AdvWriteWordRegister(iop_base, IOPW_CTRL_REG, ADV_CTRL_REG_CMD_RESET);
17307         DvcSleepMilliSecond(100);
17308         AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
17309                              ADV_CTRL_REG_CMD_WR_IO_REG);
17310
17311         /*
17312          * Reset Adv Library error code, if any, and try
17313          * re-initializing the chip.
17314          */
17315         asc_dvc->err_code = 0;
17316         if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
17317                 status = AdvInitAsc38C1600Driver(asc_dvc);
17318         } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
17319                 status = AdvInitAsc38C0800Driver(asc_dvc);
17320         } else {
17321                 status = AdvInitAsc3550Driver(asc_dvc);
17322         }
17323
17324         /* Translate initialization return value to status value. */
17325         if (status == 0) {
17326                 status = ADV_TRUE;
17327         } else {
17328                 status = ADV_FALSE;
17329         }
17330
17331         /*
17332          * Restore the BIOS signature word.
17333          */
17334         AdvWriteWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, bios_sig);
17335
17336         /*
17337          * Restore per TID negotiated values.
17338          */
17339         AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
17340         AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
17341         if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
17342                 AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
17343         }
17344         AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
17345         for (tid = 0; tid <= ADV_MAX_TID; tid++) {
17346                 AdvWriteByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
17347                                  max_cmd[tid]);
17348         }
17349
17350         return status;
17351 }
17352
17353 /*
17354  * Adv Library Interrupt Service Routine
17355  *
17356  *  This function is called by a driver's interrupt service routine.
17357  *  The function disables and re-enables interrupts.
17358  *
17359  *  When a microcode idle command is completed, the ADV_DVC_VAR
17360  *  'idle_cmd_done' field is set to ADV_TRUE.
17361  *
17362  *  Note: AdvISR() can be called when interrupts are disabled or even
17363  *  when there is no hardware interrupt condition present. It will
17364  *  always check for completed idle commands and microcode requests.
17365  *  This is an important feature that shouldn't be changed because it
17366  *  allows commands to be completed from polling mode loops.
17367  *
17368  * Return:
17369  *   ADV_TRUE(1) - interrupt was pending
17370  *   ADV_FALSE(0) - no interrupt was pending
17371  */
17372 static int AdvISR(ADV_DVC_VAR *asc_dvc)
17373 {
17374         AdvPortAddr iop_base;
17375         uchar int_stat;
17376         ushort target_bit;
17377         ADV_CARR_T *free_carrp;
17378         ADV_VADDR irq_next_vpa;
17379         int flags;
17380         ADV_SCSI_REQ_Q *scsiq;
17381
17382         flags = DvcEnterCritical();
17383
17384         iop_base = asc_dvc->iop_base;
17385
17386         /* Reading the register clears the interrupt. */
17387         int_stat = AdvReadByteRegister(iop_base, IOPB_INTR_STATUS_REG);
17388
17389         if ((int_stat & (ADV_INTR_STATUS_INTRA | ADV_INTR_STATUS_INTRB |
17390                          ADV_INTR_STATUS_INTRC)) == 0) {
17391                 DvcLeaveCritical(flags);
17392                 return ADV_FALSE;
17393         }
17394
17395         /*
17396          * Notify the driver of an asynchronous microcode condition by
17397          * calling the ADV_DVC_VAR.async_callback function. The function
17398          * is passed the microcode ASC_MC_INTRB_CODE byte value.
17399          */
17400         if (int_stat & ADV_INTR_STATUS_INTRB) {
17401                 uchar intrb_code;
17402
17403                 AdvReadByteLram(iop_base, ASC_MC_INTRB_CODE, intrb_code);
17404
17405                 if (asc_dvc->chip_type == ADV_CHIP_ASC3550 ||
17406                     asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
17407                         if (intrb_code == ADV_ASYNC_CARRIER_READY_FAILURE &&
17408                             asc_dvc->carr_pending_cnt != 0) {
17409                                 AdvWriteByteRegister(iop_base, IOPB_TICKLE,
17410                                                      ADV_TICKLE_A);
17411                                 if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
17412                                         AdvWriteByteRegister(iop_base,
17413                                                              IOPB_TICKLE,
17414                                                              ADV_TICKLE_NOP);
17415                                 }
17416                         }
17417                 }
17418
17419                 if (asc_dvc->async_callback != 0) {
17420                         (*asc_dvc->async_callback) (asc_dvc, intrb_code);
17421                 }
17422         }
17423
17424         /*
17425          * Check if the IRQ stopper carrier contains a completed request.
17426          */
17427         while (((irq_next_vpa =
17428                  le32_to_cpu(asc_dvc->irq_sp->next_vpa)) & ASC_RQ_DONE) != 0) {
17429                 /*
17430                  * Get a pointer to the newly completed ADV_SCSI_REQ_Q structure.
17431                  * The RISC will have set 'areq_vpa' to a virtual address.
17432                  *
17433                  * The firmware will have copied the ASC_SCSI_REQ_Q.scsiq_ptr
17434                  * field to the carrier ADV_CARR_T.areq_vpa field. The conversion
17435                  * below complements the conversion of ASC_SCSI_REQ_Q.scsiq_ptr'
17436                  * in AdvExeScsiQueue().
17437                  */
17438                 scsiq = (ADV_SCSI_REQ_Q *)
17439                     ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->areq_vpa));
17440
17441                 /*
17442                  * Request finished with good status and the queue was not
17443                  * DMAed to host memory by the firmware. Set all status fields
17444                  * to indicate good status.
17445                  */
17446                 if ((irq_next_vpa & ASC_RQ_GOOD) != 0) {
17447                         scsiq->done_status = QD_NO_ERROR;
17448                         scsiq->host_status = scsiq->scsi_status = 0;
17449                         scsiq->data_cnt = 0L;
17450                 }
17451
17452                 /*
17453                  * Advance the stopper pointer to the next carrier
17454                  * ignoring the lower four bits. Free the previous
17455                  * stopper carrier.
17456                  */
17457                 free_carrp = asc_dvc->irq_sp;
17458                 asc_dvc->irq_sp = (ADV_CARR_T *)
17459                     ADV_U32_TO_VADDR(ASC_GET_CARRP(irq_next_vpa));
17460
17461                 free_carrp->next_vpa =
17462                     cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
17463                 asc_dvc->carr_freelist = free_carrp;
17464                 asc_dvc->carr_pending_cnt--;
17465
17466                 ASC_ASSERT(scsiq != NULL);
17467                 target_bit = ADV_TID_TO_TIDMASK(scsiq->target_id);
17468
17469                 /*
17470                  * Clear request microcode control flag.
17471                  */
17472                 scsiq->cntl = 0;
17473
17474                 /*
17475                  * If the command that completed was a SCSI INQUIRY and
17476                  * LUN 0 was sent the command, then process the INQUIRY
17477                  * command information for the device.
17478                  *
17479                  * Note: If data returned were either VPD or CmdDt data,
17480                  * don't process the INQUIRY command information for
17481                  * the device, otherwise may erroneously set *_able bits.
17482                  */
17483                 if (scsiq->done_status == QD_NO_ERROR &&
17484                     scsiq->cdb[0] == INQUIRY &&
17485                     scsiq->target_lun == 0 &&
17486                     (scsiq->cdb[1] & ADV_INQ_RTN_VPD_AND_CMDDT)
17487                     == ADV_INQ_RTN_STD_INQUIRY_DATA) {
17488                         AdvInquiryHandling(asc_dvc, scsiq);
17489                 }
17490
17491                 /*
17492                  * Notify the driver of the completed request by passing
17493                  * the ADV_SCSI_REQ_Q pointer to its callback function.
17494                  */
17495                 scsiq->a_flag |= ADV_SCSIQ_DONE;
17496                 (*asc_dvc->isr_callback) (asc_dvc, scsiq);
17497                 /*
17498                  * Note: After the driver callback function is called, 'scsiq'
17499                  * can no longer be referenced.
17500                  *
17501                  * Fall through and continue processing other completed
17502                  * requests...
17503                  */
17504
17505                 /*
17506                  * Disable interrupts again in case the driver inadvertently
17507                  * enabled interrupts in its callback function.
17508                  *
17509                  * The DvcEnterCritical() return value is ignored, because
17510                  * the 'flags' saved when AdvISR() was first entered will be
17511                  * used to restore the interrupt flag on exit.
17512                  */
17513                 (void)DvcEnterCritical();
17514         }
17515         DvcLeaveCritical(flags);
17516         return ADV_TRUE;
17517 }
17518
17519 /*
17520  * Send an idle command to the chip and wait for completion.
17521  *
17522  * Command completion is polled for once per microsecond.
17523  *
17524  * The function can be called from anywhere including an interrupt handler.
17525  * But the function is not re-entrant, so it uses the DvcEnter/LeaveCritical()
17526  * functions to prevent reentrancy.
17527  *
17528  * Return Values:
17529  *   ADV_TRUE - command completed successfully
17530  *   ADV_FALSE - command failed
17531  *   ADV_ERROR - command timed out
17532  */
17533 static int
17534 AdvSendIdleCmd(ADV_DVC_VAR *asc_dvc,
17535                ushort idle_cmd, ADV_DCNT idle_cmd_parameter)
17536 {
17537         ulong last_int_level;
17538         int result;
17539         ADV_DCNT i, j;
17540         AdvPortAddr iop_base;
17541
17542         last_int_level = DvcEnterCritical();
17543
17544         iop_base = asc_dvc->iop_base;
17545
17546         /*
17547          * Clear the idle command status which is set by the microcode
17548          * to a non-zero value to indicate when the command is completed.
17549          * The non-zero result is one of the IDLE_CMD_STATUS_* values
17550          * defined in a_advlib.h.
17551          */
17552         AdvWriteWordLram(iop_base, ASC_MC_IDLE_CMD_STATUS, (ushort)0);
17553
17554         /*
17555          * Write the idle command value after the idle command parameter
17556          * has been written to avoid a race condition. If the order is not
17557          * followed, the microcode may process the idle command before the
17558          * parameters have been written to LRAM.
17559          */
17560         AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IDLE_CMD_PARAMETER,
17561                                 cpu_to_le32(idle_cmd_parameter));
17562         AdvWriteWordLram(iop_base, ASC_MC_IDLE_CMD, idle_cmd);
17563
17564         /*
17565          * Tickle the RISC to tell it to process the idle command.
17566          */
17567         AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_B);
17568         if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
17569                 /*
17570                  * Clear the tickle value. In the ASC-3550 the RISC flag
17571                  * command 'clr_tickle_b' does not work unless the host
17572                  * value is cleared.
17573                  */
17574                 AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_NOP);
17575         }
17576
17577         /* Wait for up to 100 millisecond for the idle command to timeout. */
17578         for (i = 0; i < SCSI_WAIT_100_MSEC; i++) {
17579                 /* Poll once each microsecond for command completion. */
17580                 for (j = 0; j < SCSI_US_PER_MSEC; j++) {
17581                         AdvReadWordLram(iop_base, ASC_MC_IDLE_CMD_STATUS,
17582                                         result);
17583                         if (result != 0) {
17584                                 DvcLeaveCritical(last_int_level);
17585                                 return result;
17586                         }
17587                         DvcDelayMicroSecond(asc_dvc, (ushort)1);
17588                 }
17589         }
17590
17591         ASC_ASSERT(0);          /* The idle command should never timeout. */
17592         DvcLeaveCritical(last_int_level);
17593         return ADV_ERROR;
17594 }
17595
17596 /*
17597  * Inquiry Information Byte 7 Handling
17598  *
17599  * Handle SCSI Inquiry Command information for a device by setting
17600  * microcode operating variables that affect WDTR, SDTR, and Tag
17601  * Queuing.
17602  */
17603 static void AdvInquiryHandling(ADV_DVC_VAR *asc_dvc, ADV_SCSI_REQ_Q *scsiq)
17604 {
17605         AdvPortAddr iop_base;
17606         uchar tid;
17607         ADV_SCSI_INQUIRY *inq;
17608         ushort tidmask;
17609         ushort cfg_word;
17610
17611         /*
17612          * AdvInquiryHandling() requires up to INQUIRY information Byte 7
17613          * to be available.
17614          *
17615          * If less than 8 bytes of INQUIRY information were requested or less
17616          * than 8 bytes were transferred, then return. cdb[4] is the request
17617          * length and the ADV_SCSI_REQ_Q 'data_cnt' field is set by the
17618          * microcode to the transfer residual count.
17619          */
17620
17621         if (scsiq->cdb[4] < 8 ||
17622             (scsiq->cdb[4] - le32_to_cpu(scsiq->data_cnt)) < 8) {
17623                 return;
17624         }
17625
17626         iop_base = asc_dvc->iop_base;
17627         tid = scsiq->target_id;
17628
17629         inq = (ADV_SCSI_INQUIRY *) scsiq->vdata_addr;
17630
17631         /*
17632          * WDTR, SDTR, and Tag Queuing cannot be enabled for old devices.
17633          */
17634         if (ADV_INQ_RESPONSE_FMT(inq) < 2 && ADV_INQ_ANSI_VER(inq) < 2) {
17635                 return;
17636         } else {
17637                 /*
17638                  * INQUIRY Byte 7 Handling
17639                  *
17640                  * Use a device's INQUIRY byte 7 to determine whether it
17641                  * supports WDTR, SDTR, and Tag Queuing. If the feature
17642                  * is enabled in the EEPROM and the device supports the
17643                  * feature, then enable it in the microcode.
17644                  */
17645
17646                 tidmask = ADV_TID_TO_TIDMASK(tid);
17647
17648                 /*
17649                  * Wide Transfers
17650                  *
17651                  * If the EEPROM enabled WDTR for the device and the device
17652                  * supports wide bus (16 bit) transfers, then turn on the
17653                  * device's 'wdtr_able' bit and write the new value to the
17654                  * microcode.
17655                  */
17656                 if ((asc_dvc->wdtr_able & tidmask) && ADV_INQ_WIDE16(inq)) {
17657                         AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, cfg_word);
17658                         if ((cfg_word & tidmask) == 0) {
17659                                 cfg_word |= tidmask;
17660                                 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
17661                                                  cfg_word);
17662
17663                                 /*
17664                                  * Clear the microcode "SDTR negotiation" and "WDTR
17665                                  * negotiation" done indicators for the target to cause
17666                                  * it to negotiate with the new setting set above.
17667                                  * WDTR when accepted causes the target to enter
17668                                  * asynchronous mode, so SDTR must be negotiated.
17669                                  */
17670                                 AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE,
17671                                                 cfg_word);
17672                                 cfg_word &= ~tidmask;
17673                                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_DONE,
17674                                                  cfg_word);
17675                                 AdvReadWordLram(iop_base, ASC_MC_WDTR_DONE,
17676                                                 cfg_word);
17677                                 cfg_word &= ~tidmask;
17678                                 AdvWriteWordLram(iop_base, ASC_MC_WDTR_DONE,
17679                                                  cfg_word);
17680                         }
17681                 }
17682
17683                 /*
17684                  * Synchronous Transfers
17685                  *
17686                  * If the EEPROM enabled SDTR for the device and the device
17687                  * supports synchronous transfers, then turn on the device's
17688                  * 'sdtr_able' bit. Write the new value to the microcode.
17689                  */
17690                 if ((asc_dvc->sdtr_able & tidmask) && ADV_INQ_SYNC(inq)) {
17691                         AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, cfg_word);
17692                         if ((cfg_word & tidmask) == 0) {
17693                                 cfg_word |= tidmask;
17694                                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
17695                                                  cfg_word);
17696
17697                                 /*
17698                                  * Clear the microcode "SDTR negotiation" done indicator
17699                                  * for the target to cause it to negotiate with the new
17700                                  * setting set above.
17701                                  */
17702                                 AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE,
17703                                                 cfg_word);
17704                                 cfg_word &= ~tidmask;
17705                                 AdvWriteWordLram(iop_base, ASC_MC_SDTR_DONE,
17706                                                  cfg_word);
17707                         }
17708                 }
17709                 /*
17710                  * If the Inquiry data included enough space for the SPI-3
17711                  * Clocking field, then check if DT mode is supported.
17712                  */
17713                 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600 &&
17714                     (scsiq->cdb[4] >= 57 ||
17715                      (scsiq->cdb[4] - le32_to_cpu(scsiq->data_cnt)) >= 57)) {
17716                         /*
17717                          * PPR (Parallel Protocol Request) Capable
17718                          *
17719                          * If the device supports DT mode, then it must be PPR capable.
17720                          * The PPR message will be used in place of the SDTR and WDTR
17721                          * messages to negotiate synchronous speed and offset, transfer
17722                          * width, and protocol options.
17723                          */
17724                         if (ADV_INQ_CLOCKING(inq) & ADV_INQ_CLOCKING_DT_ONLY) {
17725                                 AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE,
17726                                                 asc_dvc->ppr_able);
17727                                 asc_dvc->ppr_able |= tidmask;
17728                                 AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE,
17729                                                  asc_dvc->ppr_able);
17730                         }
17731                 }
17732
17733                 /*
17734                  * If the EEPROM enabled Tag Queuing for the device and the
17735                  * device supports Tag Queueing, then turn on the device's
17736                  * 'tagqng_enable' bit in the microcode and set the microcode
17737                  * maximum command count to the ADV_DVC_VAR 'max_dvc_qng'
17738                  * value.
17739                  *
17740                  * Tag Queuing is disabled for the BIOS which runs in polled
17741                  * mode and would see no benefit from Tag Queuing. Also by
17742                  * disabling Tag Queuing in the BIOS devices with Tag Queuing
17743                  * bugs will at least work with the BIOS.
17744                  */
17745                 if ((asc_dvc->tagqng_able & tidmask) && ADV_INQ_CMD_QUEUE(inq)) {
17746                         AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, cfg_word);
17747                         cfg_word |= tidmask;
17748                         AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
17749                                          cfg_word);
17750
17751                         AdvWriteByteLram(iop_base,
17752                                          ASC_MC_NUMBER_OF_MAX_CMD + tid,
17753                                          asc_dvc->max_dvc_qng);
17754                 }
17755         }
17756 }
17757
17758 static struct Scsi_Host *__devinit
17759 advansys_board_found(int iop, struct device *dev, int bus_type)
17760 {
17761         struct Scsi_Host *shost;
17762         struct pci_dev *pdev = bus_type == ASC_IS_PCI ? to_pci_dev(dev) : NULL;
17763         asc_board_t *boardp;
17764         ASC_DVC_VAR *asc_dvc_varp = NULL;
17765         ADV_DVC_VAR *adv_dvc_varp = NULL;
17766         adv_sgblk_t *sgp = NULL;
17767         int share_irq = FALSE;
17768         int iolen = 0;
17769         ADV_PADDR pci_memory_address;
17770         int warn_code, err_code;
17771         int ret;
17772
17773         /*
17774          * Adapter found.
17775          *
17776          * Register the adapter, get its configuration, and
17777          * initialize it.
17778          */
17779         ASC_DBG(2, "advansys_board_found: scsi_register()\n");
17780         shost = scsi_register(&driver_template, sizeof(asc_board_t));
17781
17782         if (!shost)
17783                 return NULL;
17784
17785         /* Save a pointer to the Scsi_Host of each board found. */
17786         asc_host[asc_board_count++] = shost;
17787
17788         /* Initialize private per board data */
17789         boardp = ASC_BOARDP(shost);
17790         memset(boardp, 0, sizeof(asc_board_t));
17791         boardp->id = asc_board_count - 1;
17792
17793         /* Initialize spinlock. */
17794         spin_lock_init(&boardp->lock);
17795
17796         /*
17797          * Handle both narrow and wide boards.
17798          *
17799          * If a Wide board was detected, set the board structure
17800          * wide board flag. Set-up the board structure based on
17801          * the board type.
17802          */
17803 #ifdef CONFIG_PCI
17804         if (bus_type == ASC_IS_PCI &&
17805             (pdev->device == PCI_DEVICE_ID_ASP_ABP940UW ||
17806              pdev->device == PCI_DEVICE_ID_38C0800_REV1 ||
17807              pdev->device == PCI_DEVICE_ID_38C1600_REV1)) {
17808                 boardp->flags |= ASC_IS_WIDE_BOARD;
17809         }
17810 #endif /* CONFIG_PCI */
17811
17812         if (ASC_NARROW_BOARD(boardp)) {
17813                 ASC_DBG(1, "advansys_board_found: narrow board\n");
17814                 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
17815                 asc_dvc_varp->bus_type = bus_type;
17816                 asc_dvc_varp->drv_ptr = boardp;
17817                 asc_dvc_varp->cfg = &boardp->dvc_cfg.asc_dvc_cfg;
17818                 asc_dvc_varp->cfg->overrun_buf = &overrun_buf[0];
17819                 asc_dvc_varp->iop_base = iop;
17820                 asc_dvc_varp->isr_callback = asc_isr_callback;
17821         } else {
17822                 ASC_DBG(1, "advansys_board_found: wide board\n");
17823                 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
17824                 adv_dvc_varp->drv_ptr = boardp;
17825                 adv_dvc_varp->cfg = &boardp->dvc_cfg.adv_dvc_cfg;
17826                 adv_dvc_varp->isr_callback = adv_isr_callback;
17827                 adv_dvc_varp->async_callback = adv_async_callback;
17828 #ifdef CONFIG_PCI
17829                 if (pdev->device == PCI_DEVICE_ID_ASP_ABP940UW) {
17830                         ASC_DBG(1, "advansys_board_found: ASC-3550\n");
17831                         adv_dvc_varp->chip_type = ADV_CHIP_ASC3550;
17832                 } else if (pdev->device == PCI_DEVICE_ID_38C0800_REV1) {
17833                         ASC_DBG(1, "advansys_board_found: ASC-38C0800\n");
17834                         adv_dvc_varp->chip_type = ADV_CHIP_ASC38C0800;
17835                 } else {
17836                         ASC_DBG(1, "advansys_board_found: ASC-38C1600\n");
17837                         adv_dvc_varp->chip_type = ADV_CHIP_ASC38C1600;
17838                 }
17839 #endif /* CONFIG_PCI */
17840
17841                 /*
17842                  * Map the board's registers into virtual memory for
17843                  * PCI slave access. Only memory accesses are used to
17844                  * access the board's registers.
17845                  *
17846                  * Note: The PCI register base address is not always
17847                  * page aligned, but the address passed to ioremap()
17848                  * must be page aligned. It is guaranteed that the
17849                  * PCI register base address will not cross a page
17850                  * boundary.
17851                  */
17852                 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
17853                         iolen = ADV_3550_IOLEN;
17854                 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
17855                         iolen = ADV_38C0800_IOLEN;
17856                 } else {
17857                         iolen = ADV_38C1600_IOLEN;
17858                 }
17859 #ifdef CONFIG_PCI
17860                 pci_memory_address = pci_resource_start(pdev, 1);
17861                 ASC_DBG1(1,
17862                          "advansys_board_found: pci_memory_address: 0x%lx\n",
17863                          (ulong)pci_memory_address);
17864                 if ((boardp->ioremap_addr =
17865                      ioremap(pci_memory_address & PAGE_MASK, PAGE_SIZE)) == 0) {
17866                         ASC_PRINT3
17867                             ("advansys_board_found: board %d: ioremap(%x, %d) returned NULL\n",
17868                              boardp->id, pci_memory_address, iolen);
17869                         scsi_unregister(shost);
17870                         asc_board_count--;
17871                         return NULL;
17872                 }
17873                 ASC_DBG1(1,
17874                          "advansys_board_found: ioremap_addr: 0x%lx\n",
17875                          (ulong)boardp->ioremap_addr);
17876                 adv_dvc_varp->iop_base = (AdvPortAddr)
17877                     (boardp->ioremap_addr +
17878                      (pci_memory_address - (pci_memory_address & PAGE_MASK)));
17879                 ASC_DBG1(1,
17880                          "advansys_board_found: iop_base: 0x%lx\n",
17881                          adv_dvc_varp->iop_base);
17882 #endif /* CONFIG_PCI */
17883
17884                 /*
17885                  * Even though it isn't used to access wide boards, other
17886                  * than for the debug line below, save I/O Port address so
17887                  * that it can be reported.
17888                  */
17889                 boardp->ioport = iop;
17890
17891                 ASC_DBG2(1,
17892                          "advansys_board_found: iopb_chip_id_1 0x%x, iopw_chip_id_0 0x%x\n",
17893                          (ushort)inp(iop + 1), (ushort)inpw(iop));
17894         }
17895
17896 #ifdef CONFIG_PROC_FS
17897         /*
17898          * Allocate buffer for printing information from
17899          * /proc/scsi/advansys/[0...].
17900          */
17901         if ((boardp->prtbuf = kmalloc(ASC_PRTBUF_SIZE, GFP_ATOMIC)) == NULL) {
17902                 ASC_PRINT3
17903                     ("advansys_board_found: board %d: kmalloc(%d, %d) returned NULL\n",
17904                      boardp->id, ASC_PRTBUF_SIZE, GFP_ATOMIC);
17905                 scsi_unregister(shost);
17906                 asc_board_count--;
17907                 return NULL;
17908         }
17909 #endif /* CONFIG_PROC_FS */
17910
17911         if (ASC_NARROW_BOARD(boardp)) {
17912                 asc_dvc_varp->cfg->dev = dev;
17913                 /*
17914                  * Set the board bus type and PCI IRQ before
17915                  * calling AscInitGetConfig().
17916                  */
17917                 switch (asc_dvc_varp->bus_type) {
17918 #ifdef CONFIG_ISA
17919                 case ASC_IS_ISA:
17920                         shost->unchecked_isa_dma = TRUE;
17921                         share_irq = FALSE;
17922                         break;
17923                 case ASC_IS_VL:
17924                         shost->unchecked_isa_dma = FALSE;
17925                         share_irq = FALSE;
17926                         break;
17927                 case ASC_IS_EISA:
17928                         shost->unchecked_isa_dma = FALSE;
17929                         share_irq = TRUE;
17930                         break;
17931 #endif /* CONFIG_ISA */
17932 #ifdef CONFIG_PCI
17933                 case ASC_IS_PCI:
17934                         shost->irq = asc_dvc_varp->irq_no = pdev->irq;
17935                         asc_dvc_varp->cfg->pci_slot_info =
17936                             ASC_PCI_MKID(pdev->bus->number,
17937                                          PCI_SLOT(pdev->devfn),
17938                                          PCI_FUNC(pdev->devfn));
17939                         shost->unchecked_isa_dma = FALSE;
17940                         share_irq = TRUE;
17941                         break;
17942 #endif /* CONFIG_PCI */
17943                 default:
17944                         ASC_PRINT2
17945                             ("advansys_board_found: board %d: unknown adapter type: %d\n",
17946                              boardp->id, asc_dvc_varp->bus_type);
17947                         shost->unchecked_isa_dma = TRUE;
17948                         share_irq = FALSE;
17949                         break;
17950                 }
17951         } else {
17952                 adv_dvc_varp->cfg->dev = dev;
17953                 /*
17954                  * For Wide boards set PCI information before calling
17955                  * AdvInitGetConfig().
17956                  */
17957 #ifdef CONFIG_PCI
17958                 shost->irq = adv_dvc_varp->irq_no = pdev->irq;
17959                 adv_dvc_varp->cfg->pci_slot_info =
17960                     ASC_PCI_MKID(pdev->bus->number,
17961                                  PCI_SLOT(pdev->devfn),
17962                                  PCI_FUNC(pdev->devfn));
17963                 shost->unchecked_isa_dma = FALSE;
17964                 share_irq = TRUE;
17965 #endif /* CONFIG_PCI */
17966         }
17967
17968         /*
17969          * Read the board configuration.
17970          */
17971         if (ASC_NARROW_BOARD(boardp)) {
17972                 /*
17973                  * NOTE: AscInitGetConfig() may change the board's
17974                  * bus_type value. The bus_type value should no
17975                  * longer be used. If the bus_type field must be
17976                  * referenced only use the bit-wise AND operator "&".
17977                  */
17978                 ASC_DBG(2, "advansys_board_found: AscInitGetConfig()\n");
17979                 switch (ret = AscInitGetConfig(asc_dvc_varp)) {
17980                 case 0: /* No error */
17981                         break;
17982                 case ASC_WARN_IO_PORT_ROTATE:
17983                         ASC_PRINT1
17984                             ("AscInitGetConfig: board %d: I/O port address modified\n",
17985                              boardp->id);
17986                         break;
17987                 case ASC_WARN_AUTO_CONFIG:
17988                         ASC_PRINT1
17989                             ("AscInitGetConfig: board %d: I/O port increment switch enabled\n",
17990                              boardp->id);
17991                         break;
17992                 case ASC_WARN_EEPROM_CHKSUM:
17993                         ASC_PRINT1
17994                             ("AscInitGetConfig: board %d: EEPROM checksum error\n",
17995                              boardp->id);
17996                         break;
17997                 case ASC_WARN_IRQ_MODIFIED:
17998                         ASC_PRINT1
17999                             ("AscInitGetConfig: board %d: IRQ modified\n",
18000                              boardp->id);
18001                         break;
18002                 case ASC_WARN_CMD_QNG_CONFLICT:
18003                         ASC_PRINT1
18004                             ("AscInitGetConfig: board %d: tag queuing enabled w/o disconnects\n",
18005                              boardp->id);
18006                         break;
18007                 default:
18008                         ASC_PRINT2
18009                             ("AscInitGetConfig: board %d: unknown warning: 0x%x\n",
18010                              boardp->id, ret);
18011                         break;
18012                 }
18013                 if ((err_code = asc_dvc_varp->err_code) != 0) {
18014                         ASC_PRINT3
18015                             ("AscInitGetConfig: board %d error: init_state 0x%x, err_code 0x%x\n",
18016                              boardp->id,
18017                              asc_dvc_varp->init_state, asc_dvc_varp->err_code);
18018                 }
18019         } else {
18020                 ASC_DBG(2, "advansys_board_found: AdvInitGetConfig()\n");
18021                 if ((ret = AdvInitGetConfig(adv_dvc_varp)) != 0) {
18022                         ASC_PRINT2
18023                             ("AdvInitGetConfig: board %d: warning: 0x%x\n",
18024                              boardp->id, ret);
18025                 }
18026                 if ((err_code = adv_dvc_varp->err_code) != 0) {
18027                         ASC_PRINT2
18028                             ("AdvInitGetConfig: board %d error: err_code 0x%x\n",
18029                              boardp->id, adv_dvc_varp->err_code);
18030                 }
18031         }
18032
18033         if (err_code != 0) {
18034 #ifdef CONFIG_PROC_FS
18035                 kfree(boardp->prtbuf);
18036 #endif /* CONFIG_PROC_FS */
18037                 scsi_unregister(shost);
18038                 asc_board_count--;
18039                 return NULL;
18040         }
18041
18042         /*
18043          * Save the EEPROM configuration so that it can be displayed
18044          * from /proc/scsi/advansys/[0...].
18045          */
18046         if (ASC_NARROW_BOARD(boardp)) {
18047
18048                 ASCEEP_CONFIG *ep;
18049
18050                 /*
18051                  * Set the adapter's target id bit in the 'init_tidmask' field.
18052                  */
18053                 boardp->init_tidmask |=
18054                     ADV_TID_TO_TIDMASK(asc_dvc_varp->cfg->chip_scsi_id);
18055
18056                 /*
18057                  * Save EEPROM settings for the board.
18058                  */
18059                 ep = &boardp->eep_config.asc_eep;
18060
18061                 ep->init_sdtr = asc_dvc_varp->cfg->sdtr_enable;
18062                 ep->disc_enable = asc_dvc_varp->cfg->disc_enable;
18063                 ep->use_cmd_qng = asc_dvc_varp->cfg->cmd_qng_enabled;
18064                 ASC_EEP_SET_DMA_SPD(ep, asc_dvc_varp->cfg->isa_dma_speed);
18065                 ep->start_motor = asc_dvc_varp->start_motor;
18066                 ep->cntl = asc_dvc_varp->dvc_cntl;
18067                 ep->no_scam = asc_dvc_varp->no_scam;
18068                 ep->max_total_qng = asc_dvc_varp->max_total_qng;
18069                 ASC_EEP_SET_CHIP_ID(ep, asc_dvc_varp->cfg->chip_scsi_id);
18070                 /* 'max_tag_qng' is set to the same value for every device. */
18071                 ep->max_tag_qng = asc_dvc_varp->cfg->max_tag_qng[0];
18072                 ep->adapter_info[0] = asc_dvc_varp->cfg->adapter_info[0];
18073                 ep->adapter_info[1] = asc_dvc_varp->cfg->adapter_info[1];
18074                 ep->adapter_info[2] = asc_dvc_varp->cfg->adapter_info[2];
18075                 ep->adapter_info[3] = asc_dvc_varp->cfg->adapter_info[3];
18076                 ep->adapter_info[4] = asc_dvc_varp->cfg->adapter_info[4];
18077                 ep->adapter_info[5] = asc_dvc_varp->cfg->adapter_info[5];
18078
18079                 /*
18080                  * Modify board configuration.
18081                  */
18082                 ASC_DBG(2, "advansys_board_found: AscInitSetConfig()\n");
18083                 switch (ret = AscInitSetConfig(asc_dvc_varp)) {
18084                 case 0: /* No error. */
18085                         break;
18086                 case ASC_WARN_IO_PORT_ROTATE:
18087                         ASC_PRINT1
18088                             ("AscInitSetConfig: board %d: I/O port address modified\n",
18089                              boardp->id);
18090                         break;
18091                 case ASC_WARN_AUTO_CONFIG:
18092                         ASC_PRINT1
18093                             ("AscInitSetConfig: board %d: I/O port increment switch enabled\n",
18094                              boardp->id);
18095                         break;
18096                 case ASC_WARN_EEPROM_CHKSUM:
18097                         ASC_PRINT1
18098                             ("AscInitSetConfig: board %d: EEPROM checksum error\n",
18099                              boardp->id);
18100                         break;
18101                 case ASC_WARN_IRQ_MODIFIED:
18102                         ASC_PRINT1
18103                             ("AscInitSetConfig: board %d: IRQ modified\n",
18104                              boardp->id);
18105                         break;
18106                 case ASC_WARN_CMD_QNG_CONFLICT:
18107                         ASC_PRINT1
18108                             ("AscInitSetConfig: board %d: tag queuing w/o disconnects\n",
18109                              boardp->id);
18110                         break;
18111                 default:
18112                         ASC_PRINT2
18113                             ("AscInitSetConfig: board %d: unknown warning: 0x%x\n",
18114                              boardp->id, ret);
18115                         break;
18116                 }
18117                 if (asc_dvc_varp->err_code != 0) {
18118                         ASC_PRINT3
18119                             ("AscInitSetConfig: board %d error: init_state 0x%x, err_code 0x%x\n",
18120                              boardp->id,
18121                              asc_dvc_varp->init_state, asc_dvc_varp->err_code);
18122 #ifdef CONFIG_PROC_FS
18123                         kfree(boardp->prtbuf);
18124 #endif /* CONFIG_PROC_FS */
18125                         scsi_unregister(shost);
18126                         asc_board_count--;
18127                         return NULL;
18128                 }
18129
18130                 /*
18131                  * Finish initializing the 'Scsi_Host' structure.
18132                  */
18133                 /* AscInitSetConfig() will set the IRQ for non-PCI boards. */
18134                 if ((asc_dvc_varp->bus_type & ASC_IS_PCI) == 0) {
18135                         shost->irq = asc_dvc_varp->irq_no;
18136                 }
18137         } else {
18138                 ADVEEP_3550_CONFIG *ep_3550;
18139                 ADVEEP_38C0800_CONFIG *ep_38C0800;
18140                 ADVEEP_38C1600_CONFIG *ep_38C1600;
18141
18142                 /*
18143                  * Save Wide EEP Configuration Information.
18144                  */
18145                 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
18146                         ep_3550 = &boardp->eep_config.adv_3550_eep;
18147
18148                         ep_3550->adapter_scsi_id = adv_dvc_varp->chip_scsi_id;
18149                         ep_3550->max_host_qng = adv_dvc_varp->max_host_qng;
18150                         ep_3550->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
18151                         ep_3550->termination = adv_dvc_varp->cfg->termination;
18152                         ep_3550->disc_enable = adv_dvc_varp->cfg->disc_enable;
18153                         ep_3550->bios_ctrl = adv_dvc_varp->bios_ctrl;
18154                         ep_3550->wdtr_able = adv_dvc_varp->wdtr_able;
18155                         ep_3550->sdtr_able = adv_dvc_varp->sdtr_able;
18156                         ep_3550->ultra_able = adv_dvc_varp->ultra_able;
18157                         ep_3550->tagqng_able = adv_dvc_varp->tagqng_able;
18158                         ep_3550->start_motor = adv_dvc_varp->start_motor;
18159                         ep_3550->scsi_reset_delay =
18160                             adv_dvc_varp->scsi_reset_wait;
18161                         ep_3550->serial_number_word1 =
18162                             adv_dvc_varp->cfg->serial1;
18163                         ep_3550->serial_number_word2 =
18164                             adv_dvc_varp->cfg->serial2;
18165                         ep_3550->serial_number_word3 =
18166                             adv_dvc_varp->cfg->serial3;
18167                 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
18168                         ep_38C0800 = &boardp->eep_config.adv_38C0800_eep;
18169
18170                         ep_38C0800->adapter_scsi_id =
18171                             adv_dvc_varp->chip_scsi_id;
18172                         ep_38C0800->max_host_qng = adv_dvc_varp->max_host_qng;
18173                         ep_38C0800->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
18174                         ep_38C0800->termination_lvd =
18175                             adv_dvc_varp->cfg->termination;
18176                         ep_38C0800->disc_enable =
18177                             adv_dvc_varp->cfg->disc_enable;
18178                         ep_38C0800->bios_ctrl = adv_dvc_varp->bios_ctrl;
18179                         ep_38C0800->wdtr_able = adv_dvc_varp->wdtr_able;
18180                         ep_38C0800->tagqng_able = adv_dvc_varp->tagqng_able;
18181                         ep_38C0800->sdtr_speed1 = adv_dvc_varp->sdtr_speed1;
18182                         ep_38C0800->sdtr_speed2 = adv_dvc_varp->sdtr_speed2;
18183                         ep_38C0800->sdtr_speed3 = adv_dvc_varp->sdtr_speed3;
18184                         ep_38C0800->sdtr_speed4 = adv_dvc_varp->sdtr_speed4;
18185                         ep_38C0800->tagqng_able = adv_dvc_varp->tagqng_able;
18186                         ep_38C0800->start_motor = adv_dvc_varp->start_motor;
18187                         ep_38C0800->scsi_reset_delay =
18188                             adv_dvc_varp->scsi_reset_wait;
18189                         ep_38C0800->serial_number_word1 =
18190                             adv_dvc_varp->cfg->serial1;
18191                         ep_38C0800->serial_number_word2 =
18192                             adv_dvc_varp->cfg->serial2;
18193                         ep_38C0800->serial_number_word3 =
18194                             adv_dvc_varp->cfg->serial3;
18195                 } else {
18196                         ep_38C1600 = &boardp->eep_config.adv_38C1600_eep;
18197
18198                         ep_38C1600->adapter_scsi_id =
18199                             adv_dvc_varp->chip_scsi_id;
18200                         ep_38C1600->max_host_qng = adv_dvc_varp->max_host_qng;
18201                         ep_38C1600->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
18202                         ep_38C1600->termination_lvd =
18203                             adv_dvc_varp->cfg->termination;
18204                         ep_38C1600->disc_enable =
18205                             adv_dvc_varp->cfg->disc_enable;
18206                         ep_38C1600->bios_ctrl = adv_dvc_varp->bios_ctrl;
18207                         ep_38C1600->wdtr_able = adv_dvc_varp->wdtr_able;
18208                         ep_38C1600->tagqng_able = adv_dvc_varp->tagqng_able;
18209                         ep_38C1600->sdtr_speed1 = adv_dvc_varp->sdtr_speed1;
18210                         ep_38C1600->sdtr_speed2 = adv_dvc_varp->sdtr_speed2;
18211                         ep_38C1600->sdtr_speed3 = adv_dvc_varp->sdtr_speed3;
18212                         ep_38C1600->sdtr_speed4 = adv_dvc_varp->sdtr_speed4;
18213                         ep_38C1600->tagqng_able = adv_dvc_varp->tagqng_able;
18214                         ep_38C1600->start_motor = adv_dvc_varp->start_motor;
18215                         ep_38C1600->scsi_reset_delay =
18216                             adv_dvc_varp->scsi_reset_wait;
18217                         ep_38C1600->serial_number_word1 =
18218                             adv_dvc_varp->cfg->serial1;
18219                         ep_38C1600->serial_number_word2 =
18220                             adv_dvc_varp->cfg->serial2;
18221                         ep_38C1600->serial_number_word3 =
18222                             adv_dvc_varp->cfg->serial3;
18223                 }
18224
18225                 /*
18226                  * Set the adapter's target id bit in the 'init_tidmask' field.
18227                  */
18228                 boardp->init_tidmask |=
18229                     ADV_TID_TO_TIDMASK(adv_dvc_varp->chip_scsi_id);
18230
18231                 /*
18232                  * Finish initializing the 'Scsi_Host' structure.
18233                  */
18234                 shost->irq = adv_dvc_varp->irq_no;
18235         }
18236
18237         /*
18238          * Channels are numbered beginning with 0. For AdvanSys one host
18239          * structure supports one channel. Multi-channel boards have a
18240          * separate host structure for each channel.
18241          */
18242         shost->max_channel = 0;
18243         if (ASC_NARROW_BOARD(boardp)) {
18244                 shost->max_id = ASC_MAX_TID + 1;
18245                 shost->max_lun = ASC_MAX_LUN + 1;
18246
18247                 shost->io_port = asc_dvc_varp->iop_base;
18248                 boardp->asc_n_io_port = ASC_IOADR_GAP;
18249                 shost->this_id = asc_dvc_varp->cfg->chip_scsi_id;
18250
18251                 /* Set maximum number of queues the adapter can handle. */
18252                 shost->can_queue = asc_dvc_varp->max_total_qng;
18253         } else {
18254                 shost->max_id = ADV_MAX_TID + 1;
18255                 shost->max_lun = ADV_MAX_LUN + 1;
18256
18257                 /*
18258                  * Save the I/O Port address and length even though
18259                  * I/O ports are not used to access Wide boards.
18260                  * Instead the Wide boards are accessed with
18261                  * PCI Memory Mapped I/O.
18262                  */
18263                 shost->io_port = iop;
18264                 boardp->asc_n_io_port = iolen;
18265
18266                 shost->this_id = adv_dvc_varp->chip_scsi_id;
18267
18268                 /* Set maximum number of queues the adapter can handle. */
18269                 shost->can_queue = adv_dvc_varp->max_host_qng;
18270         }
18271
18272         /*
18273          * 'n_io_port' currently is one byte.
18274          *
18275          * Set a value to 'n_io_port', but never referenced it because
18276          * it may be truncated.
18277          */
18278         shost->n_io_port = boardp->asc_n_io_port <= 255 ?
18279             boardp->asc_n_io_port : 255;
18280
18281         /*
18282          * Following v1.3.89, 'cmd_per_lun' is no longer needed
18283          * and should be set to zero.
18284          *
18285          * But because of a bug introduced in v1.3.89 if the driver is
18286          * compiled as a module and 'cmd_per_lun' is zero, the Mid-Level
18287          * SCSI function 'allocate_device' will panic. To allow the driver
18288          * to work as a module in these kernels set 'cmd_per_lun' to 1.
18289          *
18290          * Note: This is wrong.  cmd_per_lun should be set to the depth
18291          * you want on untagged devices always.
18292          #ifdef MODULE
18293          */
18294         shost->cmd_per_lun = 1;
18295 /* #else
18296             shost->cmd_per_lun = 0;
18297 #endif */
18298
18299         /*
18300          * Set the maximum number of scatter-gather elements the
18301          * adapter can handle.
18302          */
18303         if (ASC_NARROW_BOARD(boardp)) {
18304                 /*
18305                  * Allow two commands with 'sg_tablesize' scatter-gather
18306                  * elements to be executed simultaneously. This value is
18307                  * the theoretical hardware limit. It may be decreased
18308                  * below.
18309                  */
18310                 shost->sg_tablesize =
18311                     (((asc_dvc_varp->max_total_qng - 2) / 2) *
18312                      ASC_SG_LIST_PER_Q) + 1;
18313         } else {
18314                 shost->sg_tablesize = ADV_MAX_SG_LIST;
18315         }
18316
18317         /*
18318          * The value of 'sg_tablesize' can not exceed the SCSI
18319          * mid-level driver definition of SG_ALL. SG_ALL also
18320          * must not be exceeded, because it is used to define the
18321          * size of the scatter-gather table in 'struct asc_sg_head'.
18322          */
18323         if (shost->sg_tablesize > SG_ALL) {
18324                 shost->sg_tablesize = SG_ALL;
18325         }
18326
18327         ASC_DBG1(1, "advansys_board_found: sg_tablesize: %d\n", shost->sg_tablesize);
18328
18329         /* BIOS start address. */
18330         if (ASC_NARROW_BOARD(boardp)) {
18331                 shost->base = ((ulong)
18332                              AscGetChipBiosAddress(asc_dvc_varp->
18333                                                    iop_base,
18334                                                    asc_dvc_varp->bus_type));
18335         } else {
18336                 /*
18337                  * Fill-in BIOS board variables. The Wide BIOS saves
18338                  * information in LRAM that is used by the driver.
18339                  */
18340                 AdvReadWordLram(adv_dvc_varp->iop_base,
18341                                 BIOS_SIGNATURE, boardp->bios_signature);
18342                 AdvReadWordLram(adv_dvc_varp->iop_base,
18343                                 BIOS_VERSION, boardp->bios_version);
18344                 AdvReadWordLram(adv_dvc_varp->iop_base,
18345                                 BIOS_CODESEG, boardp->bios_codeseg);
18346                 AdvReadWordLram(adv_dvc_varp->iop_base,
18347                                 BIOS_CODELEN, boardp->bios_codelen);
18348
18349                 ASC_DBG2(1,
18350                          "advansys_board_found: bios_signature 0x%x, bios_version 0x%x\n",
18351                          boardp->bios_signature, boardp->bios_version);
18352
18353                 ASC_DBG2(1,
18354                          "advansys_board_found: bios_codeseg 0x%x, bios_codelen 0x%x\n",
18355                          boardp->bios_codeseg, boardp->bios_codelen);
18356
18357                 /*
18358                  * If the BIOS saved a valid signature, then fill in
18359                  * the BIOS code segment base address.
18360                  */
18361                 if (boardp->bios_signature == 0x55AA) {
18362                         /*
18363                          * Convert x86 realmode code segment to a linear
18364                          * address by shifting left 4.
18365                          */
18366                         shost->base = ((ulong)boardp->bios_codeseg << 4);
18367                 } else {
18368                         shost->base = 0;
18369                 }
18370         }
18371
18372         /*
18373          * Register Board Resources - I/O Port, DMA, IRQ
18374          */
18375
18376         /*
18377          * Register I/O port range.
18378          *
18379          * For Wide boards the I/O ports are not used to access
18380          * the board, but request the region anyway.
18381          *
18382          * 'shost->n_io_port' is not referenced, because it may be truncated.
18383          */
18384         ASC_DBG2(2,
18385                  "advansys_board_found: request_region port 0x%lx, len 0x%x\n",
18386                  (ulong)shost->io_port, boardp->asc_n_io_port);
18387         if (request_region(shost->io_port, boardp->asc_n_io_port,
18388                            "advansys") == NULL) {
18389                 ASC_PRINT3
18390                     ("advansys_board_found: board %d: request_region() failed, port 0x%lx, len 0x%x\n",
18391                      boardp->id, (ulong)shost->io_port, boardp->asc_n_io_port);
18392 #ifdef CONFIG_PROC_FS
18393                 kfree(boardp->prtbuf);
18394 #endif /* CONFIG_PROC_FS */
18395                 scsi_unregister(shost);
18396                 asc_board_count--;
18397                 return NULL;
18398         }
18399
18400         /* Register DMA Channel for Narrow boards. */
18401         shost->dma_channel = NO_ISA_DMA;        /* Default to no ISA DMA. */
18402 #ifdef CONFIG_ISA
18403         if (ASC_NARROW_BOARD(boardp)) {
18404                 /* Register DMA channel for ISA bus. */
18405                 if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
18406                         shost->dma_channel = asc_dvc_varp->cfg->isa_dma_channel;
18407                         if ((ret =
18408                              request_dma(shost->dma_channel, "advansys")) != 0) {
18409                                 ASC_PRINT3
18410                                     ("advansys_board_found: board %d: request_dma() %d failed %d\n",
18411                                      boardp->id, shost->dma_channel, ret);
18412                                 release_region(shost->io_port,
18413                                                boardp->asc_n_io_port);
18414 #ifdef CONFIG_PROC_FS
18415                                 kfree(boardp->prtbuf);
18416 #endif /* CONFIG_PROC_FS */
18417                                 scsi_unregister(shost);
18418                                 asc_board_count--;
18419                                 return NULL;
18420                         }
18421                         AscEnableIsaDma(shost->dma_channel);
18422                 }
18423         }
18424 #endif /* CONFIG_ISA */
18425
18426         /* Register IRQ Number. */
18427         ASC_DBG1(2, "advansys_board_found: request_irq() %d\n", shost->irq);
18428         /*
18429          * If request_irq() fails with the IRQF_DISABLED flag set,
18430          * then try again without the IRQF_DISABLED flag set. This
18431          * allows IRQ sharing to work even with other drivers that
18432          * do not set the IRQF_DISABLED flag.
18433          *
18434          * If IRQF_DISABLED is not set, then interrupts are enabled
18435          * before the driver interrupt function is called.
18436          */
18437         if (((ret = request_irq(shost->irq, advansys_interrupt,
18438                                 IRQF_DISABLED | (share_irq ==
18439                                                  TRUE ?
18440                                                  IRQF_SHARED :
18441                                                  0), "advansys", boardp)) != 0)
18442             &&
18443             ((ret =
18444               request_irq(shost->irq, advansys_interrupt,
18445                           (share_irq == TRUE ? IRQF_SHARED : 0),
18446                           "advansys", boardp)) != 0)) {
18447                 if (ret == -EBUSY) {
18448                         ASC_PRINT2
18449                             ("advansys_board_found: board %d: request_irq(): IRQ 0x%x already in use.\n",
18450                              boardp->id, shost->irq);
18451                 } else if (ret == -EINVAL) {
18452                         ASC_PRINT2
18453                             ("advansys_board_found: board %d: request_irq(): IRQ 0x%x not valid.\n",
18454                              boardp->id, shost->irq);
18455                 } else {
18456                         ASC_PRINT3
18457                             ("advansys_board_found: board %d: request_irq(): IRQ 0x%x failed with %d\n",
18458                              boardp->id, shost->irq, ret);
18459                 }
18460                 release_region(shost->io_port, boardp->asc_n_io_port);
18461                 iounmap(boardp->ioremap_addr);
18462                 if (shost->dma_channel != NO_ISA_DMA) {
18463                         free_dma(shost->dma_channel);
18464                 }
18465 #ifdef CONFIG_PROC_FS
18466                 kfree(boardp->prtbuf);
18467 #endif /* CONFIG_PROC_FS */
18468                 scsi_unregister(shost);
18469                 asc_board_count--;
18470                 return NULL;
18471         }
18472
18473         /*
18474          * Initialize board RISC chip and enable interrupts.
18475          */
18476         if (ASC_NARROW_BOARD(boardp)) {
18477                 ASC_DBG(2, "advansys_board_found: AscInitAsc1000Driver()\n");
18478                 warn_code = AscInitAsc1000Driver(asc_dvc_varp);
18479                 err_code = asc_dvc_varp->err_code;
18480
18481                 if (warn_code || err_code) {
18482                         ASC_PRINT4
18483                             ("advansys_board_found: board %d error: init_state 0x%x, warn 0x%x, error 0x%x\n",
18484                              boardp->id,
18485                              asc_dvc_varp->init_state, warn_code, err_code);
18486                 }
18487         } else {
18488                 ADV_CARR_T *carrp;
18489                 int req_cnt = 0;
18490                 adv_req_t *reqp = NULL;
18491                 int sg_cnt = 0;
18492
18493                 /*
18494                  * Allocate buffer carrier structures. The total size
18495                  * is about 4 KB, so allocate all at once.
18496                  */
18497                 carrp = (ADV_CARR_T *) kmalloc(ADV_CARRIER_BUFSIZE, GFP_ATOMIC);
18498                 ASC_DBG1(1, "advansys_board_found: carrp 0x%lx\n", (ulong)carrp);
18499
18500                 if (carrp == NULL) {
18501                         goto kmalloc_error;
18502                 }
18503
18504                 /*
18505                  * Allocate up to 'max_host_qng' request structures for
18506                  * the Wide board. The total size is about 16 KB, so
18507                  * allocate all at once. If the allocation fails decrement
18508                  * and try again.
18509                  */
18510                 for (req_cnt = adv_dvc_varp->max_host_qng;
18511                      req_cnt > 0; req_cnt--) {
18512
18513                         reqp = (adv_req_t *)
18514                             kmalloc(sizeof(adv_req_t) * req_cnt, GFP_ATOMIC);
18515
18516                         ASC_DBG3(1,
18517                                  "advansys_board_found: reqp 0x%lx, req_cnt %d, bytes %lu\n",
18518                                  (ulong)reqp, req_cnt,
18519                                  (ulong)sizeof(adv_req_t) * req_cnt);
18520
18521                         if (reqp != NULL) {
18522                                 break;
18523                         }
18524                 }
18525                 if (reqp == NULL) {
18526                         goto kmalloc_error;
18527                 }
18528
18529                 /*
18530                  * Allocate up to ADV_TOT_SG_BLOCK request structures for
18531                  * the Wide board. Each structure is about 136 bytes.
18532                  */
18533                 boardp->adv_sgblkp = NULL;
18534                 for (sg_cnt = 0; sg_cnt < ADV_TOT_SG_BLOCK; sg_cnt++) {
18535
18536                         sgp = (adv_sgblk_t *)
18537                             kmalloc(sizeof(adv_sgblk_t), GFP_ATOMIC);
18538
18539                         if (sgp == NULL) {
18540                                 break;
18541                         }
18542
18543                         sgp->next_sgblkp = boardp->adv_sgblkp;
18544                         boardp->adv_sgblkp = sgp;
18545
18546                 }
18547                 ASC_DBG3(1,
18548                          "advansys_board_found: sg_cnt %d * %u = %u bytes\n",
18549                          sg_cnt, sizeof(adv_sgblk_t),
18550                          (unsigned)(sizeof(adv_sgblk_t) * sg_cnt));
18551
18552                 /*
18553                  * If no request structures or scatter-gather structures could
18554                  * be allocated, then return an error. Otherwise continue with
18555                  * initialization.
18556                  */
18557  kmalloc_error:
18558                 if (carrp == NULL) {
18559                         ASC_PRINT1
18560                             ("advansys_board_found: board %d error: failed to kmalloc() carrier buffer.\n",
18561                              boardp->id);
18562                         err_code = ADV_ERROR;
18563                 } else if (reqp == NULL) {
18564                         kfree(carrp);
18565                         ASC_PRINT1
18566                             ("advansys_board_found: board %d error: failed to kmalloc() adv_req_t buffer.\n",
18567                              boardp->id);
18568                         err_code = ADV_ERROR;
18569                 } else if (boardp->adv_sgblkp == NULL) {
18570                         kfree(carrp);
18571                         kfree(reqp);
18572                         ASC_PRINT1
18573                             ("advansys_board_found: board %d error: failed to kmalloc() adv_sgblk_t buffers.\n",
18574                              boardp->id);
18575                         err_code = ADV_ERROR;
18576                 } else {
18577
18578                         /* Save carrier buffer pointer. */
18579                         boardp->orig_carrp = carrp;
18580
18581                         /*
18582                          * Save original pointer for kfree() in case the
18583                          * driver is built as a module and can be unloaded.
18584                          */
18585                         boardp->orig_reqp = reqp;
18586
18587                         adv_dvc_varp->carrier_buf = carrp;
18588
18589                         /*
18590                          * Point 'adv_reqp' to the request structures and
18591                          * link them together.
18592                          */
18593                         req_cnt--;
18594                         reqp[req_cnt].next_reqp = NULL;
18595                         for (; req_cnt > 0; req_cnt--) {
18596                                 reqp[req_cnt - 1].next_reqp = &reqp[req_cnt];
18597                         }
18598                         boardp->adv_reqp = &reqp[0];
18599
18600                         if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
18601                                 ASC_DBG(2,
18602                                         "advansys_board_found: AdvInitAsc3550Driver()\n");
18603                                 warn_code = AdvInitAsc3550Driver(adv_dvc_varp);
18604                         } else if (adv_dvc_varp->chip_type ==
18605                                    ADV_CHIP_ASC38C0800) {
18606                                 ASC_DBG(2,
18607                                         "advansys_board_found: AdvInitAsc38C0800Driver()\n");
18608                                 warn_code =
18609                                     AdvInitAsc38C0800Driver(adv_dvc_varp);
18610                         } else {
18611                                 ASC_DBG(2,
18612                                         "advansys_board_found: AdvInitAsc38C1600Driver()\n");
18613                                 warn_code =
18614                                     AdvInitAsc38C1600Driver(adv_dvc_varp);
18615                         }
18616                         err_code = adv_dvc_varp->err_code;
18617
18618                         if (warn_code || err_code) {
18619                                 ASC_PRINT3
18620                                     ("advansys_board_found: board %d error: warn 0x%x, error 0x%x\n",
18621                                      boardp->id, warn_code, err_code);
18622                         }
18623                 }
18624         }
18625
18626         if (err_code != 0) {
18627                 release_region(shost->io_port, boardp->asc_n_io_port);
18628                 if (ASC_WIDE_BOARD(boardp)) {
18629                         iounmap(boardp->ioremap_addr);
18630                         kfree(boardp->orig_carrp);
18631                         boardp->orig_carrp = NULL;
18632                         if (boardp->orig_reqp) {
18633                                 kfree(boardp->orig_reqp);
18634                                 boardp->orig_reqp = boardp->adv_reqp = NULL;
18635                         }
18636                         while ((sgp = boardp->adv_sgblkp) != NULL) {
18637                                 boardp->adv_sgblkp = sgp->next_sgblkp;
18638                                 kfree(sgp);
18639                         }
18640                 }
18641                 if (shost->dma_channel != NO_ISA_DMA) {
18642                         free_dma(shost->dma_channel);
18643                 }
18644 #ifdef CONFIG_PROC_FS
18645                 kfree(boardp->prtbuf);
18646 #endif /* CONFIG_PROC_FS */
18647                 free_irq(shost->irq, boardp);
18648                 scsi_unregister(shost);
18649                 asc_board_count--;
18650                 return NULL;
18651         }
18652         ASC_DBG_PRT_SCSI_HOST(2, shost);
18653
18654         return shost;
18655 }
18656
18657 /*
18658  * advansys_detect()
18659  *
18660  * Detect function for AdvanSys adapters.
18661  *
18662  * Argument is a pointer to the host driver's scsi_hosts entry.
18663  *
18664  * Return number of adapters found.
18665  *
18666  * Note: Because this function is called during system initialization
18667  * it must not call SCSI mid-level functions including scsi_malloc()
18668  * and scsi_free().
18669  */
18670 static int __init advansys_detect(struct scsi_host_template *tpnt)
18671 {
18672         static int detect_called = ASC_FALSE;
18673         int iop;
18674         int bus;
18675         int ioport = 0;
18676         struct device *dev = NULL;
18677 #ifdef CONFIG_PCI
18678         int pci_init_search = 0;
18679         struct pci_dev *pci_devicep[ASC_NUM_BOARD_SUPPORTED];
18680         int pci_card_cnt_max = 0;
18681         int pci_card_cnt = 0;
18682         struct pci_dev *pdev = NULL;
18683         int pci_device_id_cnt = 0;
18684         unsigned int pci_device_id[ASC_PCI_DEVICE_ID_CNT] = {
18685                 PCI_DEVICE_ID_ASP_1200A,
18686                 PCI_DEVICE_ID_ASP_ABP940,
18687                 PCI_DEVICE_ID_ASP_ABP940U,
18688                 PCI_DEVICE_ID_ASP_ABP940UW,
18689                 PCI_DEVICE_ID_38C0800_REV1,
18690                 PCI_DEVICE_ID_38C1600_REV1
18691         };
18692 #endif /* CONFIG_PCI */
18693
18694         if (detect_called == ASC_FALSE) {
18695                 detect_called = ASC_TRUE;
18696         } else {
18697                 printk
18698                     ("AdvanSys SCSI: advansys_detect() multiple calls ignored\n");
18699                 return 0;
18700         }
18701
18702         ASC_DBG(1, "advansys_detect: begin\n");
18703
18704         asc_board_count = 0;
18705
18706         /*
18707          * If I/O port probing has been modified, then verify and
18708          * clean-up the 'asc_ioport' list.
18709          */
18710         if (asc_iopflag == ASC_TRUE) {
18711                 for (ioport = 0; ioport < ASC_NUM_IOPORT_PROBE; ioport++) {
18712                         ASC_DBG2(1, "advansys_detect: asc_ioport[%d] 0x%x\n",
18713                                  ioport, asc_ioport[ioport]);
18714                         if (asc_ioport[ioport] != 0) {
18715                                 for (iop = 0; iop < ASC_IOADR_TABLE_MAX_IX;
18716                                      iop++) {
18717                                         if (_asc_def_iop_base[iop] ==
18718                                             asc_ioport[ioport]) {
18719                                                 break;
18720                                         }
18721                                 }
18722                                 if (iop == ASC_IOADR_TABLE_MAX_IX) {
18723                                         printk
18724                                             ("AdvanSys SCSI: specified I/O Port 0x%X is invalid\n",
18725                                              asc_ioport[ioport]);
18726                                         asc_ioport[ioport] = 0;
18727                                 }
18728                         }
18729                 }
18730                 ioport = 0;
18731         }
18732
18733         for (bus = 0; bus < ASC_NUM_BUS; bus++) {
18734
18735                 ASC_DBG2(1, "advansys_detect: bus search type %d (%s)\n",
18736                          bus, asc_bus_name[bus]);
18737                 iop = 0;
18738
18739                 while (asc_board_count < ASC_NUM_BOARD_SUPPORTED) {
18740
18741                         ASC_DBG1(2, "advansys_detect: asc_board_count %d\n",
18742                                  asc_board_count);
18743
18744                         switch (asc_bus[bus]) {
18745                         case ASC_IS_ISA:
18746                         case ASC_IS_VL:
18747 #ifdef CONFIG_ISA
18748                                 if (asc_iopflag == ASC_FALSE) {
18749                                         iop =
18750                                             AscSearchIOPortAddr(iop,
18751                                                                 asc_bus[bus]);
18752                                 } else {
18753                                         /*
18754                                          * ISA and VL I/O port scanning has either been
18755                                          * eliminated or limited to selected ports on
18756                                          * the LILO command line, /etc/lilo.conf, or
18757                                          * by setting variables when the module was loaded.
18758                                          */
18759                                         ASC_DBG(1,
18760                                                 "advansys_detect: I/O port scanning modified\n");
18761  ioport_try_again:
18762                                         iop = 0;
18763                                         for (; ioport < ASC_NUM_IOPORT_PROBE;
18764                                              ioport++) {
18765                                                 if ((iop =
18766                                                      asc_ioport[ioport]) != 0) {
18767                                                         break;
18768                                                 }
18769                                         }
18770                                         if (iop) {
18771                                                 ASC_DBG1(1,
18772                                                          "advansys_detect: probing I/O port 0x%x...\n",
18773                                                          iop);
18774                                                 if (!request_region
18775                                                     (iop, ASC_IOADR_GAP,
18776                                                      "advansys")) {
18777                                                         printk
18778                                                             ("AdvanSys SCSI: specified I/O Port 0x%X is busy\n",
18779                                                              iop);
18780                                                         /* Don't try this I/O port twice. */
18781                                                         asc_ioport[ioport] = 0;
18782                                                         goto ioport_try_again;
18783                                                 } else if (AscFindSignature(iop)
18784                                                            == ASC_FALSE) {
18785                                                         printk
18786                                                             ("AdvanSys SCSI: specified I/O Port 0x%X has no adapter\n",
18787                                                              iop);
18788                                                         /* Don't try this I/O port twice. */
18789                                                         release_region(iop,
18790                                                                        ASC_IOADR_GAP);
18791                                                         asc_ioport[ioport] = 0;
18792                                                         goto ioport_try_again;
18793                                                 } else {
18794                                                         /*
18795                                                          * If this isn't an ISA board, then it must be
18796                                                          * a VL board. If currently looking an ISA
18797                                                          * board is being looked for then try for
18798                                                          * another ISA board in 'asc_ioport'.
18799                                                          */
18800                                                         if (asc_bus[bus] ==
18801                                                             ASC_IS_ISA
18802                                                             &&
18803                                                             (AscGetChipVersion
18804                                                              (iop,
18805                                                               ASC_IS_ISA) &
18806                                                              ASC_CHIP_VER_ISA_BIT)
18807                                                             == 0) {
18808                                                                 /*
18809                                                                  * Don't clear 'asc_ioport[ioport]'. Try
18810                                                                  * this board again for VL. Increment
18811                                                                  * 'ioport' past this board.
18812                                                                  */
18813                                                                 ioport++;
18814                                                                 release_region
18815                                                                     (iop,
18816                                                                      ASC_IOADR_GAP);
18817                                                                 goto ioport_try_again;
18818                                                         }
18819                                                 }
18820                                                 /*
18821                                                  * This board appears good, don't try the I/O port
18822                                                  * again by clearing its value. Increment 'ioport'
18823                                                  * for the next iteration.
18824                                                  */
18825                                                 asc_ioport[ioport++] = 0;
18826                                         }
18827                                 }
18828 #endif /* CONFIG_ISA */
18829                                 break;
18830
18831                         case ASC_IS_EISA:
18832 #ifdef CONFIG_ISA
18833                                 iop = AscSearchIOPortAddr(iop, asc_bus[bus]);
18834 #endif /* CONFIG_ISA */
18835                                 break;
18836
18837                         case ASC_IS_PCI:
18838 #ifdef CONFIG_PCI
18839                                 if (pci_init_search == 0) {
18840                                         int i, j;
18841
18842                                         pci_init_search = 1;
18843
18844                                         /* Find all PCI cards. */
18845                                         while (pci_device_id_cnt <
18846                                                ASC_PCI_DEVICE_ID_CNT) {
18847                                                 if ((pdev =
18848                                                      pci_find_device
18849                                                      (PCI_VENDOR_ID_ASP,
18850                                                       pci_device_id
18851                                                       [pci_device_id_cnt],
18852                                                       pdev)) == NULL) {
18853                                                         pci_device_id_cnt++;
18854                                                 } else {
18855                                                         if (pci_enable_device
18856                                                             (pdev) == 0) {
18857                                                                 pci_devicep
18858                                                                     [pci_card_cnt_max++]
18859                                                                     = pdev;
18860                                                         }
18861                                                 }
18862                                         }
18863
18864                                         /*
18865                                          * Sort PCI cards in ascending order by PCI Bus, Slot,
18866                                          * and Device Number.
18867                                          */
18868                                         for (i = 0; i < pci_card_cnt_max - 1;
18869                                              i++) {
18870                                                 for (j = i + 1;
18871                                                      j < pci_card_cnt_max;
18872                                                      j++) {
18873                                                         if ((pci_devicep[j]->
18874                                                              bus->number <
18875                                                              pci_devicep[i]->
18876                                                              bus->number)
18877                                                             ||
18878                                                             ((pci_devicep[j]->
18879                                                               bus->number ==
18880                                                               pci_devicep[i]->
18881                                                               bus->number)
18882                                                              &&
18883                                                              (pci_devicep[j]->
18884                                                               devfn <
18885                                                               pci_devicep[i]->
18886                                                               devfn))) {
18887                                                                 pdev =
18888                                                                     pci_devicep
18889                                                                     [i];
18890                                                                 pci_devicep[i] =
18891                                                                     pci_devicep
18892                                                                     [j];
18893                                                                 pci_devicep[j] =
18894                                                                     pdev;
18895                                                         }
18896                                                 }
18897                                         }
18898
18899                                         pci_card_cnt = 0;
18900                                 } else {
18901                                         pci_card_cnt++;
18902                                 }
18903
18904                                 if (pci_card_cnt == pci_card_cnt_max) {
18905                                         iop = 0;
18906                                 } else {
18907                                         pdev = pci_devicep[pci_card_cnt];
18908
18909                                         ASC_DBG2(2,
18910                                                  "advansys_detect: devfn %d, bus number %d\n",
18911                                                  pdev->devfn,
18912                                                  pdev->bus->number);
18913                                         iop = pci_resource_start(pdev, 0);
18914                                         ASC_DBG2(1,
18915                                                  "advansys_detect: vendorID %X, deviceID %X\n",
18916                                                  pdev->vendor,
18917                                                  pdev->device);
18918                                         ASC_DBG2(2,
18919                                                  "advansys_detect: iop %X, irqLine %d\n",
18920                                                  iop, pdev->irq);
18921                                 }
18922                                 if (pdev)
18923                                         dev = &pdev->dev;
18924
18925 #endif /* CONFIG_PCI */
18926                                 break;
18927
18928                         default:
18929                                 ASC_PRINT1
18930                                     ("advansys_detect: unknown bus type: %d\n",
18931                                      asc_bus[bus]);
18932                                 break;
18933                         }
18934                         ASC_DBG1(1, "advansys_detect: iop 0x%x\n", iop);
18935
18936                         /*
18937                          * Adapter not found, try next bus type.
18938                          */
18939                         if (iop == 0) {
18940                                 break;
18941                         }
18942
18943                         advansys_board_found(iop, dev, asc_bus[bus]);
18944                 }
18945         }
18946
18947         ASC_DBG1(1, "advansys_detect: done: asc_board_count %d\n",
18948                  asc_board_count);
18949         return asc_board_count;
18950 }
18951
18952 /*
18953  * advansys_release()
18954  *
18955  * Release resources allocated for a single AdvanSys adapter.
18956  */
18957 static int advansys_release(struct Scsi_Host *shost)
18958 {
18959         asc_board_t *boardp;
18960
18961         ASC_DBG(1, "advansys_release: begin\n");
18962         boardp = ASC_BOARDP(shost);
18963         free_irq(shost->irq, boardp);
18964         if (shost->dma_channel != NO_ISA_DMA) {
18965                 ASC_DBG(1, "advansys_release: free_dma()\n");
18966                 free_dma(shost->dma_channel);
18967         }
18968         release_region(shost->io_port, boardp->asc_n_io_port);
18969         if (ASC_WIDE_BOARD(boardp)) {
18970                 adv_sgblk_t *sgp = NULL;
18971
18972                 iounmap(boardp->ioremap_addr);
18973                 kfree(boardp->orig_carrp);
18974                 boardp->orig_carrp = NULL;
18975                 if (boardp->orig_reqp) {
18976                         kfree(boardp->orig_reqp);
18977                         boardp->orig_reqp = boardp->adv_reqp = NULL;
18978                 }
18979                 while ((sgp = boardp->adv_sgblkp) != NULL) {
18980                         boardp->adv_sgblkp = sgp->next_sgblkp;
18981                         kfree(sgp);
18982                 }
18983         }
18984 #ifdef CONFIG_PROC_FS
18985         ASC_ASSERT(boardp->prtbuf != NULL);
18986         kfree(boardp->prtbuf);
18987 #endif /* CONFIG_PROC_FS */
18988         scsi_unregister(shost);
18989         ASC_DBG(1, "advansys_release: end\n");
18990         return 0;
18991 }
18992
18993 #ifdef CONFIG_PCI
18994 /* PCI Devices supported by this driver */
18995 static struct pci_device_id advansys_pci_tbl[] __devinitdata = {
18996         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_1200A,
18997          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
18998         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940,
18999          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
19000         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940U,
19001          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
19002         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940UW,
19003          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
19004         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_38C0800_REV1,
19005          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
19006         {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_38C1600_REV1,
19007          PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
19008         {}
19009 };
19010
19011 MODULE_DEVICE_TABLE(pci, advansys_pci_tbl);
19012 #endif /* CONFIG_PCI */
19013
19014 MODULE_LICENSE("GPL");