1#define DRV_NAME "advansys"
2#define ASC_VERSION "3.4"
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24#include <linux/module.h>
25#include <linux/string.h>
26#include <linux/kernel.h>
27#include <linux/types.h>
28#include <linux/ioport.h>
29#include <linux/interrupt.h>
30#include <linux/delay.h>
31#include <linux/slab.h>
32#include <linux/mm.h>
33#include <linux/proc_fs.h>
34#include <linux/init.h>
35#include <linux/blkdev.h>
36#include <linux/isa.h>
37#include <linux/eisa.h>
38#include <linux/pci.h>
39#include <linux/spinlock.h>
40#include <linux/dma-mapping.h>
41#include <linux/firmware.h>
42
43#include <asm/io.h>
44#include <asm/dma.h>
45
46#include <scsi/scsi_cmnd.h>
47#include <scsi/scsi_device.h>
48#include <scsi/scsi_tcq.h>
49#include <scsi/scsi.h>
50#include <scsi/scsi_host.h>
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71#warning this driver is still not properly converted to the DMA API
72
73
74#define ADVANSYS_STATS
75
76
77#undef ADVANSYS_DEBUG
78
79
80
81
82
83
84
85
86
87
88#define ASC_PADDR __u32
89#define ASC_VADDR __u32
90#define ASC_DCNT __u32
91#define ASC_SDCNT __s32
92
93typedef unsigned char uchar;
94
95#ifndef TRUE
96#define TRUE (1)
97#endif
98#ifndef FALSE
99#define FALSE (0)
100#endif
101
102#define ERR (-1)
103#define UW_ERR (uint)(0xFFFF)
104#define isodd_word(val) ((((uint)val) & (uint)0x0001) != 0)
105
106#define PCI_VENDOR_ID_ASP 0x10cd
107#define PCI_DEVICE_ID_ASP_1200A 0x1100
108#define PCI_DEVICE_ID_ASP_ABP940 0x1200
109#define PCI_DEVICE_ID_ASP_ABP940U 0x1300
110#define PCI_DEVICE_ID_ASP_ABP940UW 0x2300
111#define PCI_DEVICE_ID_38C0800_REV1 0x2500
112#define PCI_DEVICE_ID_38C1600_REV1 0x2700
113
114
115
116
117
118
119
120#define CC_VERY_LONG_SG_LIST 0
121#define ASC_SRB2SCSIQ(srb_ptr) (srb_ptr)
122
123#define PortAddr unsigned int
124#define inp(port) inb(port)
125#define outp(port, byte) outb((byte), (port))
126
127#define inpw(port) inw(port)
128#define outpw(port, word) outw((word), (port))
129
130#define ASC_MAX_SG_QUEUE 7
131#define ASC_MAX_SG_LIST 255
132
133#define ASC_CS_TYPE unsigned short
134
135#define ASC_IS_ISA (0x0001)
136#define ASC_IS_ISAPNP (0x0081)
137#define ASC_IS_EISA (0x0002)
138#define ASC_IS_PCI (0x0004)
139#define ASC_IS_PCI_ULTRA (0x0104)
140#define ASC_IS_PCMCIA (0x0008)
141#define ASC_IS_MCA (0x0020)
142#define ASC_IS_VL (0x0040)
143#define ASC_IS_WIDESCSI_16 (0x0100)
144#define ASC_IS_WIDESCSI_32 (0x0200)
145#define ASC_IS_BIG_ENDIAN (0x8000)
146
147#define ASC_CHIP_MIN_VER_VL (0x01)
148#define ASC_CHIP_MAX_VER_VL (0x07)
149#define ASC_CHIP_MIN_VER_PCI (0x09)
150#define ASC_CHIP_MAX_VER_PCI (0x0F)
151#define ASC_CHIP_VER_PCI_BIT (0x08)
152#define ASC_CHIP_MIN_VER_ISA (0x11)
153#define ASC_CHIP_MIN_VER_ISA_PNP (0x21)
154#define ASC_CHIP_MAX_VER_ISA (0x27)
155#define ASC_CHIP_VER_ISA_BIT (0x30)
156#define ASC_CHIP_VER_ISAPNP_BIT (0x20)
157#define ASC_CHIP_VER_ASYN_BUG (0x21)
158#define ASC_CHIP_VER_PCI 0x08
159#define ASC_CHIP_VER_PCI_ULTRA_3150 (ASC_CHIP_VER_PCI | 0x02)
160#define ASC_CHIP_VER_PCI_ULTRA_3050 (ASC_CHIP_VER_PCI | 0x03)
161#define ASC_CHIP_MIN_VER_EISA (0x41)
162#define ASC_CHIP_MAX_VER_EISA (0x47)
163#define ASC_CHIP_VER_EISA_BIT (0x40)
164#define ASC_CHIP_LATEST_VER_EISA ((ASC_CHIP_MIN_VER_EISA - 1) + 3)
165#define ASC_MAX_VL_DMA_COUNT (0x07FFFFFFL)
166#define ASC_MAX_PCI_DMA_COUNT (0xFFFFFFFFL)
167#define ASC_MAX_ISA_DMA_COUNT (0x00FFFFFFL)
168
169#define ASC_SCSI_ID_BITS 3
170#define ASC_SCSI_TIX_TYPE uchar
171#define ASC_ALL_DEVICE_BIT_SET 0xFF
172#define ASC_SCSI_BIT_ID_TYPE uchar
173#define ASC_MAX_TID 7
174#define ASC_MAX_LUN 7
175#define ASC_SCSI_WIDTH_BIT_SET 0xFF
176#define ASC_MAX_SENSE_LEN 32
177#define ASC_MIN_SENSE_LEN 14
178#define ASC_SCSI_RESET_HOLD_TIME_US 60
179
180
181
182
183
184#define ASC_MAX_CDB_LEN 12
185#define ADV_MAX_CDB_LEN 16
186
187#define MS_SDTR_LEN 0x03
188#define MS_WDTR_LEN 0x02
189
190#define ASC_SG_LIST_PER_Q 7
191#define QS_FREE 0x00
192#define QS_READY 0x01
193#define QS_DISC1 0x02
194#define QS_DISC2 0x04
195#define QS_BUSY 0x08
196#define QS_ABORTED 0x40
197#define QS_DONE 0x80
198#define QC_NO_CALLBACK 0x01
199#define QC_SG_SWAP_QUEUE 0x02
200#define QC_SG_HEAD 0x04
201#define QC_DATA_IN 0x08
202#define QC_DATA_OUT 0x10
203#define QC_URGENT 0x20
204#define QC_MSG_OUT 0x40
205#define QC_REQ_SENSE 0x80
206#define QCSG_SG_XFER_LIST 0x02
207#define QCSG_SG_XFER_MORE 0x04
208#define QCSG_SG_XFER_END 0x08
209#define QD_IN_PROGRESS 0x00
210#define QD_NO_ERROR 0x01
211#define QD_ABORTED_BY_HOST 0x02
212#define QD_WITH_ERROR 0x04
213#define QD_INVALID_REQUEST 0x80
214#define QD_INVALID_HOST_NUM 0x81
215#define QD_INVALID_DEVICE 0x82
216#define QD_ERR_INTERNAL 0xFF
217#define QHSTA_NO_ERROR 0x00
218#define QHSTA_M_SEL_TIMEOUT 0x11
219#define QHSTA_M_DATA_OVER_RUN 0x12
220#define QHSTA_M_DATA_UNDER_RUN 0x12
221#define QHSTA_M_UNEXPECTED_BUS_FREE 0x13
222#define QHSTA_M_BAD_BUS_PHASE_SEQ 0x14
223#define QHSTA_D_QDONE_SG_LIST_CORRUPTED 0x21
224#define QHSTA_D_ASC_DVC_ERROR_CODE_SET 0x22
225#define QHSTA_D_HOST_ABORT_FAILED 0x23
226#define QHSTA_D_EXE_SCSI_Q_FAILED 0x24
227#define QHSTA_D_EXE_SCSI_Q_BUSY_TIMEOUT 0x25
228#define QHSTA_D_ASPI_NO_BUF_POOL 0x26
229#define QHSTA_M_WTM_TIMEOUT 0x41
230#define QHSTA_M_BAD_CMPL_STATUS_IN 0x42
231#define QHSTA_M_NO_AUTO_REQ_SENSE 0x43
232#define QHSTA_M_AUTO_REQ_SENSE_FAIL 0x44
233#define QHSTA_M_TARGET_STATUS_BUSY 0x45
234#define QHSTA_M_BAD_TAG_CODE 0x46
235#define QHSTA_M_BAD_QUEUE_FULL_OR_BUSY 0x47
236#define QHSTA_M_HUNG_REQ_SCSI_BUS_RESET 0x48
237#define QHSTA_D_LRAM_CMP_ERROR 0x81
238#define QHSTA_M_MICRO_CODE_ERROR_HALT 0xA1
239#define ASC_FLAG_SCSIQ_REQ 0x01
240#define ASC_FLAG_BIOS_SCSIQ_REQ 0x02
241#define ASC_FLAG_BIOS_ASYNC_IO 0x04
242#define ASC_FLAG_SRB_LINEAR_ADDR 0x08
243#define ASC_FLAG_WIN16 0x10
244#define ASC_FLAG_WIN32 0x20
245#define ASC_FLAG_ISA_OVER_16MB 0x40
246#define ASC_FLAG_DOS_VM_CALLBACK 0x80
247#define ASC_TAG_FLAG_EXTRA_BYTES 0x10
248#define ASC_TAG_FLAG_DISABLE_DISCONNECT 0x04
249#define ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX 0x08
250#define ASC_TAG_FLAG_DISABLE_CHK_COND_INT_HOST 0x40
251#define ASC_SCSIQ_CPY_BEG 4
252#define ASC_SCSIQ_SGHD_CPY_BEG 2
253#define ASC_SCSIQ_B_FWD 0
254#define ASC_SCSIQ_B_BWD 1
255#define ASC_SCSIQ_B_STATUS 2
256#define ASC_SCSIQ_B_QNO 3
257#define ASC_SCSIQ_B_CNTL 4
258#define ASC_SCSIQ_B_SG_QUEUE_CNT 5
259#define ASC_SCSIQ_D_DATA_ADDR 8
260#define ASC_SCSIQ_D_DATA_CNT 12
261#define ASC_SCSIQ_B_SENSE_LEN 20
262#define ASC_SCSIQ_DONE_INFO_BEG 22
263#define ASC_SCSIQ_D_SRBPTR 22
264#define ASC_SCSIQ_B_TARGET_IX 26
265#define ASC_SCSIQ_B_CDB_LEN 28
266#define ASC_SCSIQ_B_TAG_CODE 29
267#define ASC_SCSIQ_W_VM_ID 30
268#define ASC_SCSIQ_DONE_STATUS 32
269#define ASC_SCSIQ_HOST_STATUS 33
270#define ASC_SCSIQ_SCSI_STATUS 34
271#define ASC_SCSIQ_CDB_BEG 36
272#define ASC_SCSIQ_DW_REMAIN_XFER_ADDR 56
273#define ASC_SCSIQ_DW_REMAIN_XFER_CNT 60
274#define ASC_SCSIQ_B_FIRST_SG_WK_QP 48
275#define ASC_SCSIQ_B_SG_WK_QP 49
276#define ASC_SCSIQ_B_SG_WK_IX 50
277#define ASC_SCSIQ_W_ALT_DC1 52
278#define ASC_SCSIQ_B_LIST_CNT 6
279#define ASC_SCSIQ_B_CUR_LIST_CNT 7
280#define ASC_SGQ_B_SG_CNTL 4
281#define ASC_SGQ_B_SG_HEAD_QP 5
282#define ASC_SGQ_B_SG_LIST_CNT 6
283#define ASC_SGQ_B_SG_CUR_LIST_CNT 7
284#define ASC_SGQ_LIST_BEG 8
285#define ASC_DEF_SCSI1_QNG 4
286#define ASC_MAX_SCSI1_QNG 4
287#define ASC_DEF_SCSI2_QNG 16
288#define ASC_MAX_SCSI2_QNG 32
289#define ASC_TAG_CODE_MASK 0x23
290#define ASC_STOP_REQ_RISC_STOP 0x01
291#define ASC_STOP_ACK_RISC_STOP 0x03
292#define ASC_STOP_CLEAN_UP_BUSY_Q 0x10
293#define ASC_STOP_CLEAN_UP_DISC_Q 0x20
294#define ASC_STOP_HOST_REQ_RISC_HALT 0x40
295#define ASC_TIDLUN_TO_IX(tid, lun) (ASC_SCSI_TIX_TYPE)((tid) + ((lun)<<ASC_SCSI_ID_BITS))
296#define ASC_TID_TO_TARGET_ID(tid) (ASC_SCSI_BIT_ID_TYPE)(0x01 << (tid))
297#define ASC_TIX_TO_TARGET_ID(tix) (0x01 << ((tix) & ASC_MAX_TID))
298#define ASC_TIX_TO_TID(tix) ((tix) & ASC_MAX_TID)
299#define ASC_TID_TO_TIX(tid) ((tid) & ASC_MAX_TID)
300#define ASC_TIX_TO_LUN(tix) (((tix) >> ASC_SCSI_ID_BITS) & ASC_MAX_LUN)
301#define ASC_QNO_TO_QADDR(q_no) ((ASC_QADR_BEG)+((int)(q_no) << 6))
302
303typedef struct asc_scsiq_1 {
304 uchar status;
305 uchar q_no;
306 uchar cntl;
307 uchar sg_queue_cnt;
308 uchar target_id;
309 uchar target_lun;
310 ASC_PADDR data_addr;
311 ASC_DCNT data_cnt;
312 ASC_PADDR sense_addr;
313 uchar sense_len;
314 uchar extra_bytes;
315} ASC_SCSIQ_1;
316
317typedef struct asc_scsiq_2 {
318 ASC_VADDR srb_ptr;
319 uchar target_ix;
320 uchar flag;
321 uchar cdb_len;
322 uchar tag_code;
323 ushort vm_id;
324} ASC_SCSIQ_2;
325
326typedef struct asc_scsiq_3 {
327 uchar done_stat;
328 uchar host_stat;
329 uchar scsi_stat;
330 uchar scsi_msg;
331} ASC_SCSIQ_3;
332
333typedef struct asc_scsiq_4 {
334 uchar cdb[ASC_MAX_CDB_LEN];
335 uchar y_first_sg_list_qp;
336 uchar y_working_sg_qp;
337 uchar y_working_sg_ix;
338 uchar y_res;
339 ushort x_req_count;
340 ushort x_reconnect_rtn;
341 ASC_PADDR x_saved_data_addr;
342 ASC_DCNT x_saved_data_cnt;
343} ASC_SCSIQ_4;
344
345typedef struct asc_q_done_info {
346 ASC_SCSIQ_2 d2;
347 ASC_SCSIQ_3 d3;
348 uchar q_status;
349 uchar q_no;
350 uchar cntl;
351 uchar sense_len;
352 uchar extra_bytes;
353 uchar res;
354 ASC_DCNT remain_bytes;
355} ASC_QDONE_INFO;
356
357typedef struct asc_sg_list {
358 ASC_PADDR addr;
359 ASC_DCNT bytes;
360} ASC_SG_LIST;
361
362typedef struct asc_sg_head {
363 ushort entry_cnt;
364 ushort queue_cnt;
365 ushort entry_to_copy;
366 ushort res;
367 ASC_SG_LIST sg_list[0];
368} ASC_SG_HEAD;
369
370typedef struct asc_scsi_q {
371 ASC_SCSIQ_1 q1;
372 ASC_SCSIQ_2 q2;
373 uchar *cdbptr;
374 ASC_SG_HEAD *sg_head;
375 ushort remain_sg_entry_cnt;
376 ushort next_sg_index;
377} ASC_SCSI_Q;
378
379typedef struct asc_scsi_req_q {
380 ASC_SCSIQ_1 r1;
381 ASC_SCSIQ_2 r2;
382 uchar *cdbptr;
383 ASC_SG_HEAD *sg_head;
384 uchar *sense_ptr;
385 ASC_SCSIQ_3 r3;
386 uchar cdb[ASC_MAX_CDB_LEN];
387 uchar sense[ASC_MIN_SENSE_LEN];
388} ASC_SCSI_REQ_Q;
389
390typedef struct asc_scsi_bios_req_q {
391 ASC_SCSIQ_1 r1;
392 ASC_SCSIQ_2 r2;
393 uchar *cdbptr;
394 ASC_SG_HEAD *sg_head;
395 uchar *sense_ptr;
396 ASC_SCSIQ_3 r3;
397 uchar cdb[ASC_MAX_CDB_LEN];
398 uchar sense[ASC_MIN_SENSE_LEN];
399} ASC_SCSI_BIOS_REQ_Q;
400
401typedef struct asc_risc_q {
402 uchar fwd;
403 uchar bwd;
404 ASC_SCSIQ_1 i1;
405 ASC_SCSIQ_2 i2;
406 ASC_SCSIQ_3 i3;
407 ASC_SCSIQ_4 i4;
408} ASC_RISC_Q;
409
410typedef struct asc_sg_list_q {
411 uchar seq_no;
412 uchar q_no;
413 uchar cntl;
414 uchar sg_head_qp;
415 uchar sg_list_cnt;
416 uchar sg_cur_list_cnt;
417} ASC_SG_LIST_Q;
418
419typedef struct asc_risc_sg_list_q {
420 uchar fwd;
421 uchar bwd;
422 ASC_SG_LIST_Q sg;
423 ASC_SG_LIST sg_list[7];
424} ASC_RISC_SG_LIST_Q;
425
426#define ASCQ_ERR_Q_STATUS 0x0D
427#define ASCQ_ERR_CUR_QNG 0x17
428#define ASCQ_ERR_SG_Q_LINKS 0x18
429#define ASCQ_ERR_ISR_RE_ENTRY 0x1A
430#define ASCQ_ERR_CRITICAL_RE_ENTRY 0x1B
431#define ASCQ_ERR_ISR_ON_CRITICAL 0x1C
432
433
434
435
436#define ASC_WARN_NO_ERROR 0x0000
437#define ASC_WARN_IO_PORT_ROTATE 0x0001
438#define ASC_WARN_EEPROM_CHKSUM 0x0002
439#define ASC_WARN_IRQ_MODIFIED 0x0004
440#define ASC_WARN_AUTO_CONFIG 0x0008
441#define ASC_WARN_CMD_QNG_CONFLICT 0x0010
442#define ASC_WARN_EEPROM_RECOVER 0x0020
443#define ASC_WARN_CFG_MSW_RECOVER 0x0040
444
445
446
447
448#define ASC_IERR_NO_CARRIER 0x0001
449#define ASC_IERR_MCODE_CHKSUM 0x0002
450#define ASC_IERR_SET_PC_ADDR 0x0004
451#define ASC_IERR_START_STOP_CHIP 0x0008
452#define ASC_IERR_ILLEGAL_CONNECTION 0x0010
453#define ASC_IERR_SINGLE_END_DEVICE 0x0020
454#define ASC_IERR_REVERSED_CABLE 0x0040
455#define ASC_IERR_SET_SCSI_ID 0x0080
456#define ASC_IERR_HVD_DEVICE 0x0100
457#define ASC_IERR_BAD_SIGNATURE 0x0200
458#define ASC_IERR_NO_BUS_TYPE 0x0400
459#define ASC_IERR_BIST_PRE_TEST 0x0800
460#define ASC_IERR_BIST_RAM_TEST 0x1000
461#define ASC_IERR_BAD_CHIPTYPE 0x2000
462
463#define ASC_DEF_MAX_TOTAL_QNG (0xF0)
464#define ASC_MIN_TAG_Q_PER_DVC (0x04)
465#define ASC_MIN_FREE_Q (0x02)
466#define ASC_MIN_TOTAL_QNG ((ASC_MAX_SG_QUEUE)+(ASC_MIN_FREE_Q))
467#define ASC_MAX_TOTAL_QNG 240
468#define ASC_MAX_PCI_ULTRA_INRAM_TOTAL_QNG 16
469#define ASC_MAX_PCI_ULTRA_INRAM_TAG_QNG 8
470#define ASC_MAX_PCI_INRAM_TOTAL_QNG 20
471#define ASC_MAX_INRAM_TAG_QNG 16
472#define ASC_IOADR_GAP 0x10
473#define ASC_SYN_MAX_OFFSET 0x0F
474#define ASC_DEF_SDTR_OFFSET 0x0F
475#define ASC_SDTR_ULTRA_PCI_10MB_INDEX 0x02
476#define ASYN_SDTR_DATA_FIX_PCI_REV_AB 0x41
477
478
479
480
481
482static const unsigned char asc_syn_xfer_period[8] = {
483 25, 30, 35, 40, 50, 60, 70, 85
484};
485
486static const unsigned char asc_syn_ultra_xfer_period[16] = {
487 12, 19, 25, 32, 38, 44, 50, 57, 63, 69, 75, 82, 88, 94, 100, 107
488};
489
490typedef struct ext_msg {
491 uchar msg_type;
492 uchar msg_len;
493 uchar msg_req;
494 union {
495 struct {
496 uchar sdtr_xfer_period;
497 uchar sdtr_req_ack_offset;
498 } sdtr;
499 struct {
500 uchar wdtr_width;
501 } wdtr;
502 struct {
503 uchar mdp_b3;
504 uchar mdp_b2;
505 uchar mdp_b1;
506 uchar mdp_b0;
507 } mdp;
508 } u_ext_msg;
509 uchar res;
510} EXT_MSG;
511
512#define xfer_period u_ext_msg.sdtr.sdtr_xfer_period
513#define req_ack_offset u_ext_msg.sdtr.sdtr_req_ack_offset
514#define wdtr_width u_ext_msg.wdtr.wdtr_width
515#define mdp_b3 u_ext_msg.mdp_b3
516#define mdp_b2 u_ext_msg.mdp_b2
517#define mdp_b1 u_ext_msg.mdp_b1
518#define mdp_b0 u_ext_msg.mdp_b0
519
520typedef struct asc_dvc_cfg {
521 ASC_SCSI_BIT_ID_TYPE can_tagged_qng;
522 ASC_SCSI_BIT_ID_TYPE cmd_qng_enabled;
523 ASC_SCSI_BIT_ID_TYPE disc_enable;
524 ASC_SCSI_BIT_ID_TYPE sdtr_enable;
525 uchar chip_scsi_id;
526 uchar isa_dma_speed;
527 uchar isa_dma_channel;
528 uchar chip_version;
529 ushort mcode_date;
530 ushort mcode_version;
531 uchar max_tag_qng[ASC_MAX_TID + 1];
532 uchar sdtr_period_offset[ASC_MAX_TID + 1];
533 uchar adapter_info[6];
534} ASC_DVC_CFG;
535
536#define ASC_DEF_DVC_CNTL 0xFFFF
537#define ASC_DEF_CHIP_SCSI_ID 7
538#define ASC_DEF_ISA_DMA_SPEED 4
539#define ASC_INIT_STATE_BEG_GET_CFG 0x0001
540#define ASC_INIT_STATE_END_GET_CFG 0x0002
541#define ASC_INIT_STATE_BEG_SET_CFG 0x0004
542#define ASC_INIT_STATE_END_SET_CFG 0x0008
543#define ASC_INIT_STATE_BEG_LOAD_MC 0x0010
544#define ASC_INIT_STATE_END_LOAD_MC 0x0020
545#define ASC_INIT_STATE_BEG_INQUIRY 0x0040
546#define ASC_INIT_STATE_END_INQUIRY 0x0080
547#define ASC_INIT_RESET_SCSI_DONE 0x0100
548#define ASC_INIT_STATE_WITHOUT_EEP 0x8000
549#define ASC_BUG_FIX_IF_NOT_DWB 0x0001
550#define ASC_BUG_FIX_ASYN_USE_SYN 0x0002
551#define ASC_MIN_TAGGED_CMD 7
552#define ASC_MAX_SCSI_RESET_WAIT 30
553#define ASC_OVERRUN_BSIZE 64
554
555struct asc_dvc_var;
556
557typedef struct asc_dvc_var {
558 PortAddr iop_base;
559 ushort err_code;
560 ushort dvc_cntl;
561 ushort bug_fix_cntl;
562 ushort bus_type;
563 ASC_SCSI_BIT_ID_TYPE init_sdtr;
564 ASC_SCSI_BIT_ID_TYPE sdtr_done;
565 ASC_SCSI_BIT_ID_TYPE use_tagged_qng;
566 ASC_SCSI_BIT_ID_TYPE unit_not_ready;
567 ASC_SCSI_BIT_ID_TYPE queue_full_or_busy;
568 ASC_SCSI_BIT_ID_TYPE start_motor;
569 uchar *overrun_buf;
570 dma_addr_t overrun_dma;
571 uchar scsi_reset_wait;
572 uchar chip_no;
573 char is_in_int;
574 uchar max_total_qng;
575 uchar cur_total_qng;
576 uchar in_critical_cnt;
577 uchar last_q_shortage;
578 ushort init_state;
579 uchar cur_dvc_qng[ASC_MAX_TID + 1];
580 uchar max_dvc_qng[ASC_MAX_TID + 1];
581 ASC_SCSI_Q *scsiq_busy_head[ASC_MAX_TID + 1];
582 ASC_SCSI_Q *scsiq_busy_tail[ASC_MAX_TID + 1];
583 const uchar *sdtr_period_tbl;
584 ASC_DVC_CFG *cfg;
585 ASC_SCSI_BIT_ID_TYPE pci_fix_asyn_xfer_always;
586 char redo_scam;
587 ushort res2;
588 uchar dos_int13_table[ASC_MAX_TID + 1];
589 ASC_DCNT max_dma_count;
590 ASC_SCSI_BIT_ID_TYPE no_scam;
591 ASC_SCSI_BIT_ID_TYPE pci_fix_asyn_xfer;
592 uchar min_sdtr_index;
593 uchar max_sdtr_index;
594 struct asc_board *drv_ptr;
595 int ptr_map_count;
596 void **ptr_map;
597 ASC_DCNT uc_break;
598} ASC_DVC_VAR;
599
600typedef struct asc_dvc_inq_info {
601 uchar type[ASC_MAX_TID + 1][ASC_MAX_LUN + 1];
602} ASC_DVC_INQ_INFO;
603
604typedef struct asc_cap_info {
605 ASC_DCNT lba;
606 ASC_DCNT blk_size;
607} ASC_CAP_INFO;
608
609typedef struct asc_cap_info_array {
610 ASC_CAP_INFO cap_info[ASC_MAX_TID + 1][ASC_MAX_LUN + 1];
611} ASC_CAP_INFO_ARRAY;
612
613#define ASC_MCNTL_NO_SEL_TIMEOUT (ushort)0x0001
614#define ASC_MCNTL_NULL_TARGET (ushort)0x0002
615#define ASC_CNTL_INITIATOR (ushort)0x0001
616#define ASC_CNTL_BIOS_GT_1GB (ushort)0x0002
617#define ASC_CNTL_BIOS_GT_2_DISK (ushort)0x0004
618#define ASC_CNTL_BIOS_REMOVABLE (ushort)0x0008
619#define ASC_CNTL_NO_SCAM (ushort)0x0010
620#define ASC_CNTL_INT_MULTI_Q (ushort)0x0080
621#define ASC_CNTL_NO_LUN_SUPPORT (ushort)0x0040
622#define ASC_CNTL_NO_VERIFY_COPY (ushort)0x0100
623#define ASC_CNTL_RESET_SCSI (ushort)0x0200
624#define ASC_CNTL_INIT_INQUIRY (ushort)0x0400
625#define ASC_CNTL_INIT_VERBOSE (ushort)0x0800
626#define ASC_CNTL_SCSI_PARITY (ushort)0x1000
627#define ASC_CNTL_BURST_MODE (ushort)0x2000
628#define ASC_CNTL_SDTR_ENABLE_ULTRA (ushort)0x4000
629#define ASC_EEP_DVC_CFG_BEG_VL 2
630#define ASC_EEP_MAX_DVC_ADDR_VL 15
631#define ASC_EEP_DVC_CFG_BEG 32
632#define ASC_EEP_MAX_DVC_ADDR 45
633#define ASC_EEP_MAX_RETRY 20
634
635
636
637
638
639
640
641
642#define ASC_EEP_GET_CHIP_ID(cfg) ((cfg)->id_speed & 0x0f)
643#define ASC_EEP_GET_DMA_SPD(cfg) (((cfg)->id_speed & 0xf0) >> 4)
644#define ASC_EEP_SET_CHIP_ID(cfg, sid) \
645 ((cfg)->id_speed = ((cfg)->id_speed & 0xf0) | ((sid) & ASC_MAX_TID))
646#define ASC_EEP_SET_DMA_SPD(cfg, spd) \
647 ((cfg)->id_speed = ((cfg)->id_speed & 0x0f) | ((spd) & 0x0f) << 4)
648
649typedef struct asceep_config {
650 ushort cfg_lsw;
651 ushort cfg_msw;
652 uchar init_sdtr;
653 uchar disc_enable;
654 uchar use_cmd_qng;
655 uchar start_motor;
656 uchar max_total_qng;
657 uchar max_tag_qng;
658 uchar bios_scan;
659 uchar power_up_wait;
660 uchar no_scam;
661 uchar id_speed;
662
663 uchar dos_int13_table[ASC_MAX_TID + 1];
664 uchar adapter_info[6];
665 ushort cntl;
666 ushort chksum;
667} ASCEEP_CONFIG;
668
669#define ASC_EEP_CMD_READ 0x80
670#define ASC_EEP_CMD_WRITE 0x40
671#define ASC_EEP_CMD_WRITE_ABLE 0x30
672#define ASC_EEP_CMD_WRITE_DISABLE 0x00
673#define ASCV_MSGOUT_BEG 0x0000
674#define ASCV_MSGOUT_SDTR_PERIOD (ASCV_MSGOUT_BEG+3)
675#define ASCV_MSGOUT_SDTR_OFFSET (ASCV_MSGOUT_BEG+4)
676#define ASCV_BREAK_SAVED_CODE (ushort)0x0006
677#define ASCV_MSGIN_BEG (ASCV_MSGOUT_BEG+8)
678#define ASCV_MSGIN_SDTR_PERIOD (ASCV_MSGIN_BEG+3)
679#define ASCV_MSGIN_SDTR_OFFSET (ASCV_MSGIN_BEG+4)
680#define ASCV_SDTR_DATA_BEG (ASCV_MSGIN_BEG+8)
681#define ASCV_SDTR_DONE_BEG (ASCV_SDTR_DATA_BEG+8)
682#define ASCV_MAX_DVC_QNG_BEG (ushort)0x0020
683#define ASCV_BREAK_ADDR (ushort)0x0028
684#define ASCV_BREAK_NOTIFY_COUNT (ushort)0x002A
685#define ASCV_BREAK_CONTROL (ushort)0x002C
686#define ASCV_BREAK_HIT_COUNT (ushort)0x002E
687
688#define ASCV_ASCDVC_ERR_CODE_W (ushort)0x0030
689#define ASCV_MCODE_CHKSUM_W (ushort)0x0032
690#define ASCV_MCODE_SIZE_W (ushort)0x0034
691#define ASCV_STOP_CODE_B (ushort)0x0036
692#define ASCV_DVC_ERR_CODE_B (ushort)0x0037
693#define ASCV_OVERRUN_PADDR_D (ushort)0x0038
694#define ASCV_OVERRUN_BSIZE_D (ushort)0x003C
695#define ASCV_HALTCODE_W (ushort)0x0040
696#define ASCV_CHKSUM_W (ushort)0x0042
697#define ASCV_MC_DATE_W (ushort)0x0044
698#define ASCV_MC_VER_W (ushort)0x0046
699#define ASCV_NEXTRDY_B (ushort)0x0048
700#define ASCV_DONENEXT_B (ushort)0x0049
701#define ASCV_USE_TAGGED_QNG_B (ushort)0x004A
702#define ASCV_SCSIBUSY_B (ushort)0x004B
703#define ASCV_Q_DONE_IN_PROGRESS_B (ushort)0x004C
704#define ASCV_CURCDB_B (ushort)0x004D
705#define ASCV_RCLUN_B (ushort)0x004E
706#define ASCV_BUSY_QHEAD_B (ushort)0x004F
707#define ASCV_DISC1_QHEAD_B (ushort)0x0050
708#define ASCV_DISC_ENABLE_B (ushort)0x0052
709#define ASCV_CAN_TAGGED_QNG_B (ushort)0x0053
710#define ASCV_HOSTSCSI_ID_B (ushort)0x0055
711#define ASCV_MCODE_CNTL_B (ushort)0x0056
712#define ASCV_NULL_TARGET_B (ushort)0x0057
713#define ASCV_FREE_Q_HEAD_W (ushort)0x0058
714#define ASCV_DONE_Q_TAIL_W (ushort)0x005A
715#define ASCV_FREE_Q_HEAD_B (ushort)(ASCV_FREE_Q_HEAD_W+1)
716#define ASCV_DONE_Q_TAIL_B (ushort)(ASCV_DONE_Q_TAIL_W+1)
717#define ASCV_HOST_FLAG_B (ushort)0x005D
718#define ASCV_TOTAL_READY_Q_B (ushort)0x0064
719#define ASCV_VER_SERIAL_B (ushort)0x0065
720#define ASCV_HALTCODE_SAVED_W (ushort)0x0066
721#define ASCV_WTM_FLAG_B (ushort)0x0068
722#define ASCV_RISC_FLAG_B (ushort)0x006A
723#define ASCV_REQ_SG_LIST_QP (ushort)0x006B
724#define ASC_HOST_FLAG_IN_ISR 0x01
725#define ASC_HOST_FLAG_ACK_INT 0x02
726#define ASC_RISC_FLAG_GEN_INT 0x01
727#define ASC_RISC_FLAG_REQ_SG_LIST 0x02
728#define IOP_CTRL (0x0F)
729#define IOP_STATUS (0x0E)
730#define IOP_INT_ACK IOP_STATUS
731#define IOP_REG_IFC (0x0D)
732#define IOP_SYN_OFFSET (0x0B)
733#define IOP_EXTRA_CONTROL (0x0D)
734#define IOP_REG_PC (0x0C)
735#define IOP_RAM_ADDR (0x0A)
736#define IOP_RAM_DATA (0x08)
737#define IOP_EEP_DATA (0x06)
738#define IOP_EEP_CMD (0x07)
739#define IOP_VERSION (0x03)
740#define IOP_CONFIG_HIGH (0x04)
741#define IOP_CONFIG_LOW (0x02)
742#define IOP_SIG_BYTE (0x01)
743#define IOP_SIG_WORD (0x00)
744#define IOP_REG_DC1 (0x0E)
745#define IOP_REG_DC0 (0x0C)
746#define IOP_REG_SB (0x0B)
747#define IOP_REG_DA1 (0x0A)
748#define IOP_REG_DA0 (0x08)
749#define IOP_REG_SC (0x09)
750#define IOP_DMA_SPEED (0x07)
751#define IOP_REG_FLAG (0x07)
752#define IOP_FIFO_H (0x06)
753#define IOP_FIFO_L (0x04)
754#define IOP_REG_ID (0x05)
755#define IOP_REG_QP (0x03)
756#define IOP_REG_IH (0x02)
757#define IOP_REG_IX (0x01)
758#define IOP_REG_AX (0x00)
759#define IFC_REG_LOCK (0x00)
760#define IFC_REG_UNLOCK (0x09)
761#define IFC_WR_EN_FILTER (0x10)
762#define IFC_RD_NO_EEPROM (0x10)
763#define IFC_SLEW_RATE (0x20)
764#define IFC_ACT_NEG (0x40)
765#define IFC_INP_FILTER (0x80)
766#define IFC_INIT_DEFAULT (IFC_ACT_NEG | IFC_REG_UNLOCK)
767#define SC_SEL (uchar)(0x80)
768#define SC_BSY (uchar)(0x40)
769#define SC_ACK (uchar)(0x20)
770#define SC_REQ (uchar)(0x10)
771#define SC_ATN (uchar)(0x08)
772#define SC_IO (uchar)(0x04)
773#define SC_CD (uchar)(0x02)
774#define SC_MSG (uchar)(0x01)
775#define SEC_SCSI_CTL (uchar)(0x80)
776#define SEC_ACTIVE_NEGATE (uchar)(0x40)
777#define SEC_SLEW_RATE (uchar)(0x20)
778#define SEC_ENABLE_FILTER (uchar)(0x10)
779#define ASC_HALT_EXTMSG_IN (ushort)0x8000
780#define ASC_HALT_CHK_CONDITION (ushort)0x8100
781#define ASC_HALT_SS_QUEUE_FULL (ushort)0x8200
782#define ASC_HALT_DISABLE_ASYN_USE_SYN_FIX (ushort)0x8300
783#define ASC_HALT_ENABLE_ASYN_USE_SYN_FIX (ushort)0x8400
784#define ASC_HALT_SDTR_REJECTED (ushort)0x4000
785#define ASC_HALT_HOST_COPY_SG_LIST_TO_RISC ( ushort )0x2000
786#define ASC_MAX_QNO 0xF8
787#define ASC_DATA_SEC_BEG (ushort)0x0080
788#define ASC_DATA_SEC_END (ushort)0x0080
789#define ASC_CODE_SEC_BEG (ushort)0x0080
790#define ASC_CODE_SEC_END (ushort)0x0080
791#define ASC_QADR_BEG (0x4000)
792#define ASC_QADR_USED (ushort)(ASC_MAX_QNO * 64)
793#define ASC_QADR_END (ushort)0x7FFF
794#define ASC_QLAST_ADR (ushort)0x7FC0
795#define ASC_QBLK_SIZE 0x40
796#define ASC_BIOS_DATA_QBEG 0xF8
797#define ASC_MIN_ACTIVE_QNO 0x01
798#define ASC_QLINK_END 0xFF
799#define ASC_EEPROM_WORDS 0x10
800#define ASC_MAX_MGS_LEN 0x10
801#define ASC_BIOS_ADDR_DEF 0xDC00
802#define ASC_BIOS_SIZE 0x3800
803#define ASC_BIOS_RAM_OFF 0x3800
804#define ASC_BIOS_RAM_SIZE 0x800
805#define ASC_BIOS_MIN_ADDR 0xC000
806#define ASC_BIOS_MAX_ADDR 0xEC00
807#define ASC_BIOS_BANK_SIZE 0x0400
808#define ASC_MCODE_START_ADDR 0x0080
809#define ASC_CFG0_HOST_INT_ON 0x0020
810#define ASC_CFG0_BIOS_ON 0x0040
811#define ASC_CFG0_VERA_BURST_ON 0x0080
812#define ASC_CFG0_SCSI_PARITY_ON 0x0800
813#define ASC_CFG1_SCSI_TARGET_ON 0x0080
814#define ASC_CFG1_LRAM_8BITS_ON 0x0800
815#define ASC_CFG_MSW_CLR_MASK 0x3080
816#define CSW_TEST1 (ASC_CS_TYPE)0x8000
817#define CSW_AUTO_CONFIG (ASC_CS_TYPE)0x4000
818#define CSW_RESERVED1 (ASC_CS_TYPE)0x2000
819#define CSW_IRQ_WRITTEN (ASC_CS_TYPE)0x1000
820#define CSW_33MHZ_SELECTED (ASC_CS_TYPE)0x0800
821#define CSW_TEST2 (ASC_CS_TYPE)0x0400
822#define CSW_TEST3 (ASC_CS_TYPE)0x0200
823#define CSW_RESERVED2 (ASC_CS_TYPE)0x0100
824#define CSW_DMA_DONE (ASC_CS_TYPE)0x0080
825#define CSW_FIFO_RDY (ASC_CS_TYPE)0x0040
826#define CSW_EEP_READ_DONE (ASC_CS_TYPE)0x0020
827#define CSW_HALTED (ASC_CS_TYPE)0x0010
828#define CSW_SCSI_RESET_ACTIVE (ASC_CS_TYPE)0x0008
829#define CSW_PARITY_ERR (ASC_CS_TYPE)0x0004
830#define CSW_SCSI_RESET_LATCH (ASC_CS_TYPE)0x0002
831#define CSW_INT_PENDING (ASC_CS_TYPE)0x0001
832#define CIW_CLR_SCSI_RESET_INT (ASC_CS_TYPE)0x1000
833#define CIW_INT_ACK (ASC_CS_TYPE)0x0100
834#define CIW_TEST1 (ASC_CS_TYPE)0x0200
835#define CIW_TEST2 (ASC_CS_TYPE)0x0400
836#define CIW_SEL_33MHZ (ASC_CS_TYPE)0x0800
837#define CIW_IRQ_ACT (ASC_CS_TYPE)0x1000
838#define CC_CHIP_RESET (uchar)0x80
839#define CC_SCSI_RESET (uchar)0x40
840#define CC_HALT (uchar)0x20
841#define CC_SINGLE_STEP (uchar)0x10
842#define CC_DMA_ABLE (uchar)0x08
843#define CC_TEST (uchar)0x04
844#define CC_BANK_ONE (uchar)0x02
845#define CC_DIAG (uchar)0x01
846#define ASC_1000_ID0W 0x04C1
847#define ASC_1000_ID0W_FIX 0x00C1
848#define ASC_1000_ID1B 0x25
849#define ASC_EISA_REV_IOP_MASK (0x0C83)
850#define ASC_EISA_CFG_IOP_MASK (0x0C86)
851#define ASC_GET_EISA_SLOT(iop) (PortAddr)((iop) & 0xF000)
852#define INS_HALTINT (ushort)0x6281
853#define INS_HALT (ushort)0x6280
854#define INS_SINT (ushort)0x6200
855#define INS_RFLAG_WTM (ushort)0x7380
856#define ASC_MC_SAVE_CODE_WSIZE 0x500
857#define ASC_MC_SAVE_DATA_WSIZE 0x40
858
859typedef struct asc_mc_saved {
860 ushort data[ASC_MC_SAVE_DATA_WSIZE];
861 ushort code[ASC_MC_SAVE_CODE_WSIZE];
862} ASC_MC_SAVED;
863
864#define AscGetQDoneInProgress(port) AscReadLramByte((port), ASCV_Q_DONE_IN_PROGRESS_B)
865#define AscPutQDoneInProgress(port, val) AscWriteLramByte((port), ASCV_Q_DONE_IN_PROGRESS_B, val)
866#define AscGetVarFreeQHead(port) AscReadLramWord((port), ASCV_FREE_Q_HEAD_W)
867#define AscGetVarDoneQTail(port) AscReadLramWord((port), ASCV_DONE_Q_TAIL_W)
868#define AscPutVarFreeQHead(port, val) AscWriteLramWord((port), ASCV_FREE_Q_HEAD_W, val)
869#define AscPutVarDoneQTail(port, val) AscWriteLramWord((port), ASCV_DONE_Q_TAIL_W, val)
870#define AscGetRiscVarFreeQHead(port) AscReadLramByte((port), ASCV_NEXTRDY_B)
871#define AscGetRiscVarDoneQTail(port) AscReadLramByte((port), ASCV_DONENEXT_B)
872#define AscPutRiscVarFreeQHead(port, val) AscWriteLramByte((port), ASCV_NEXTRDY_B, val)
873#define AscPutRiscVarDoneQTail(port, val) AscWriteLramByte((port), ASCV_DONENEXT_B, val)
874#define AscPutMCodeSDTRDoneAtID(port, id, data) AscWriteLramByte((port), (ushort)((ushort)ASCV_SDTR_DONE_BEG+(ushort)id), (data))
875#define AscGetMCodeSDTRDoneAtID(port, id) AscReadLramByte((port), (ushort)((ushort)ASCV_SDTR_DONE_BEG+(ushort)id))
876#define AscPutMCodeInitSDTRAtID(port, id, data) AscWriteLramByte((port), (ushort)((ushort)ASCV_SDTR_DATA_BEG+(ushort)id), data)
877#define AscGetMCodeInitSDTRAtID(port, id) AscReadLramByte((port), (ushort)((ushort)ASCV_SDTR_DATA_BEG+(ushort)id))
878#define AscGetChipSignatureByte(port) (uchar)inp((port)+IOP_SIG_BYTE)
879#define AscGetChipSignatureWord(port) (ushort)inpw((port)+IOP_SIG_WORD)
880#define AscGetChipVerNo(port) (uchar)inp((port)+IOP_VERSION)
881#define AscGetChipCfgLsw(port) (ushort)inpw((port)+IOP_CONFIG_LOW)
882#define AscGetChipCfgMsw(port) (ushort)inpw((port)+IOP_CONFIG_HIGH)
883#define AscSetChipCfgLsw(port, data) outpw((port)+IOP_CONFIG_LOW, data)
884#define AscSetChipCfgMsw(port, data) outpw((port)+IOP_CONFIG_HIGH, data)
885#define AscGetChipEEPCmd(port) (uchar)inp((port)+IOP_EEP_CMD)
886#define AscSetChipEEPCmd(port, data) outp((port)+IOP_EEP_CMD, data)
887#define AscGetChipEEPData(port) (ushort)inpw((port)+IOP_EEP_DATA)
888#define AscSetChipEEPData(port, data) outpw((port)+IOP_EEP_DATA, data)
889#define AscGetChipLramAddr(port) (ushort)inpw((PortAddr)((port)+IOP_RAM_ADDR))
890#define AscSetChipLramAddr(port, addr) outpw((PortAddr)((port)+IOP_RAM_ADDR), addr)
891#define AscGetChipLramData(port) (ushort)inpw((port)+IOP_RAM_DATA)
892#define AscSetChipLramData(port, data) outpw((port)+IOP_RAM_DATA, data)
893#define AscGetChipIFC(port) (uchar)inp((port)+IOP_REG_IFC)
894#define AscSetChipIFC(port, data) outp((port)+IOP_REG_IFC, data)
895#define AscGetChipStatus(port) (ASC_CS_TYPE)inpw((port)+IOP_STATUS)
896#define AscSetChipStatus(port, cs_val) outpw((port)+IOP_STATUS, cs_val)
897#define AscGetChipControl(port) (uchar)inp((port)+IOP_CTRL)
898#define AscSetChipControl(port, cc_val) outp((port)+IOP_CTRL, cc_val)
899#define AscGetChipSyn(port) (uchar)inp((port)+IOP_SYN_OFFSET)
900#define AscSetChipSyn(port, data) outp((port)+IOP_SYN_OFFSET, data)
901#define AscSetPCAddr(port, data) outpw((port)+IOP_REG_PC, data)
902#define AscGetPCAddr(port) (ushort)inpw((port)+IOP_REG_PC)
903#define AscIsIntPending(port) (AscGetChipStatus(port) & (CSW_INT_PENDING | CSW_SCSI_RESET_LATCH))
904#define AscGetChipScsiID(port) ((AscGetChipCfgLsw(port) >> 8) & ASC_MAX_TID)
905#define AscGetExtraControl(port) (uchar)inp((port)+IOP_EXTRA_CONTROL)
906#define AscSetExtraControl(port, data) outp((port)+IOP_EXTRA_CONTROL, data)
907#define AscReadChipAX(port) (ushort)inpw((port)+IOP_REG_AX)
908#define AscWriteChipAX(port, data) outpw((port)+IOP_REG_AX, data)
909#define AscReadChipIX(port) (uchar)inp((port)+IOP_REG_IX)
910#define AscWriteChipIX(port, data) outp((port)+IOP_REG_IX, data)
911#define AscReadChipIH(port) (ushort)inpw((port)+IOP_REG_IH)
912#define AscWriteChipIH(port, data) outpw((port)+IOP_REG_IH, data)
913#define AscReadChipQP(port) (uchar)inp((port)+IOP_REG_QP)
914#define AscWriteChipQP(port, data) outp((port)+IOP_REG_QP, data)
915#define AscReadChipFIFO_L(port) (ushort)inpw((port)+IOP_REG_FIFO_L)
916#define AscWriteChipFIFO_L(port, data) outpw((port)+IOP_REG_FIFO_L, data)
917#define AscReadChipFIFO_H(port) (ushort)inpw((port)+IOP_REG_FIFO_H)
918#define AscWriteChipFIFO_H(port, data) outpw((port)+IOP_REG_FIFO_H, data)
919#define AscReadChipDmaSpeed(port) (uchar)inp((port)+IOP_DMA_SPEED)
920#define AscWriteChipDmaSpeed(port, data) outp((port)+IOP_DMA_SPEED, data)
921#define AscReadChipDA0(port) (ushort)inpw((port)+IOP_REG_DA0)
922#define AscWriteChipDA0(port) outpw((port)+IOP_REG_DA0, data)
923#define AscReadChipDA1(port) (ushort)inpw((port)+IOP_REG_DA1)
924#define AscWriteChipDA1(port) outpw((port)+IOP_REG_DA1, data)
925#define AscReadChipDC0(port) (ushort)inpw((port)+IOP_REG_DC0)
926#define AscWriteChipDC0(port) outpw((port)+IOP_REG_DC0, data)
927#define AscReadChipDC1(port) (ushort)inpw((port)+IOP_REG_DC1)
928#define AscWriteChipDC1(port) outpw((port)+IOP_REG_DC1, data)
929#define AscReadChipDvcID(port) (uchar)inp((port)+IOP_REG_ID)
930#define AscWriteChipDvcID(port, data) outp((port)+IOP_REG_ID, data)
931
932
933
934
935
936
937
938
939
940
941#define ADV_PADDR __u32
942#define ADV_VADDR __u32
943#define ADV_DCNT __u32
944#define ADV_SDCNT __s32
945
946
947
948
949
950
951
952
953
954#define ADV_VADDR_TO_U32 virt_to_bus
955#define ADV_U32_TO_VADDR bus_to_virt
956
957#define AdvPortAddr void __iomem *
958
959
960
961
962#define ADV_MEM_READB(addr) readb(addr)
963#define ADV_MEM_READW(addr) readw(addr)
964#define ADV_MEM_WRITEB(addr, byte) writeb(byte, addr)
965#define ADV_MEM_WRITEW(addr, word) writew(word, addr)
966#define ADV_MEM_WRITEDW(addr, dword) writel(dword, addr)
967
968#define ADV_CARRIER_COUNT (ASC_DEF_MAX_HOST_QNG + 15)
969
970
971
972
973
974
975
976
977
978
979#define ADV_TOT_SG_BLOCK ASC_DEF_MAX_HOST_QNG
980
981
982
983
984#define ADV_MAX_SG_LIST 255
985#define NO_OF_SG_PER_BLOCK 15
986
987#define ADV_EEP_DVC_CFG_BEGIN (0x00)
988#define ADV_EEP_DVC_CFG_END (0x15)
989#define ADV_EEP_DVC_CTL_BEGIN (0x16)
990#define ADV_EEP_MAX_WORD_ADDR (0x1E)
991
992#define ADV_EEP_DELAY_MS 100
993
994#define ADV_EEPROM_BIG_ENDIAN 0x8000
995#define ADV_EEPROM_BIOS_ENABLE 0x4000
996
997
998
999
1000
1001#define ADV_EEPROM_TERM_POL 0x2000
1002#define ADV_EEPROM_CIS_LD 0x2000
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014#define ADV_EEPROM_INTAB 0x0800
1015
1016typedef struct adveep_3550_config {
1017
1018
1019 ushort cfg_lsw;
1020
1021
1022
1023 ushort cfg_msw;
1024 ushort disc_enable;
1025 ushort wdtr_able;
1026 ushort sdtr_able;
1027 ushort start_motor;
1028 ushort tagqng_able;
1029 ushort bios_scan;
1030 ushort scam_tolerant;
1031
1032 uchar adapter_scsi_id;
1033 uchar bios_boot_delay;
1034
1035 uchar scsi_reset_delay;
1036 uchar bios_id_lun;
1037
1038
1039
1040 uchar termination;
1041
1042
1043
1044
1045
1046 uchar reserved1;
1047
1048 ushort bios_ctrl;
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065 ushort ultra_able;
1066 ushort reserved2;
1067 uchar max_host_qng;
1068 uchar max_dvc_qng;
1069 ushort dvc_cntl;
1070 ushort bug_fix;
1071 ushort serial_number_word1;
1072 ushort serial_number_word2;
1073 ushort serial_number_word3;
1074 ushort check_sum;
1075 uchar oem_name[16];
1076 ushort dvc_err_code;
1077 ushort adv_err_code;
1078 ushort adv_err_addr;
1079 ushort saved_dvc_err_code;
1080 ushort saved_adv_err_code;
1081 ushort saved_adv_err_addr;
1082 ushort num_of_err;
1083} ADVEEP_3550_CONFIG;
1084
1085typedef struct adveep_38C0800_config {
1086
1087
1088 ushort cfg_lsw;
1089
1090
1091
1092 ushort cfg_msw;
1093 ushort disc_enable;
1094 ushort wdtr_able;
1095 ushort sdtr_speed1;
1096 ushort start_motor;
1097 ushort tagqng_able;
1098 ushort bios_scan;
1099 ushort scam_tolerant;
1100
1101 uchar adapter_scsi_id;
1102 uchar bios_boot_delay;
1103
1104 uchar scsi_reset_delay;
1105 uchar bios_id_lun;
1106
1107
1108
1109 uchar termination_se;
1110
1111
1112
1113
1114
1115 uchar termination_lvd;
1116
1117
1118
1119
1120
1121 ushort bios_ctrl;
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138 ushort sdtr_speed2;
1139 ushort sdtr_speed3;
1140 uchar max_host_qng;
1141 uchar max_dvc_qng;
1142 ushort dvc_cntl;
1143 ushort sdtr_speed4;
1144 ushort serial_number_word1;
1145 ushort serial_number_word2;
1146 ushort serial_number_word3;
1147 ushort check_sum;
1148 uchar oem_name[16];
1149 ushort dvc_err_code;
1150 ushort adv_err_code;
1151 ushort adv_err_addr;
1152 ushort saved_dvc_err_code;
1153 ushort saved_adv_err_code;
1154 ushort saved_adv_err_addr;
1155 ushort reserved36;
1156 ushort reserved37;
1157 ushort reserved38;
1158 ushort reserved39;
1159 ushort reserved40;
1160 ushort reserved41;
1161 ushort reserved42;
1162 ushort reserved43;
1163 ushort reserved44;
1164 ushort reserved45;
1165 ushort reserved46;
1166 ushort reserved47;
1167 ushort reserved48;
1168 ushort reserved49;
1169 ushort reserved50;
1170 ushort reserved51;
1171 ushort reserved52;
1172 ushort reserved53;
1173 ushort reserved54;
1174 ushort reserved55;
1175 ushort cisptr_lsw;
1176 ushort cisprt_msw;
1177 ushort subsysvid;
1178 ushort subsysid;
1179 ushort reserved60;
1180 ushort reserved61;
1181 ushort reserved62;
1182 ushort reserved63;
1183} ADVEEP_38C0800_CONFIG;
1184
1185typedef struct adveep_38C1600_config {
1186
1187
1188 ushort cfg_lsw;
1189
1190
1191
1192
1193
1194 ushort cfg_msw;
1195 ushort disc_enable;
1196 ushort wdtr_able;
1197 ushort sdtr_speed1;
1198 ushort start_motor;
1199 ushort tagqng_able;
1200 ushort bios_scan;
1201 ushort scam_tolerant;
1202
1203 uchar adapter_scsi_id;
1204 uchar bios_boot_delay;
1205
1206 uchar scsi_reset_delay;
1207 uchar bios_id_lun;
1208
1209
1210
1211 uchar termination_se;
1212
1213
1214
1215
1216
1217 uchar termination_lvd;
1218
1219
1220
1221
1222
1223 ushort bios_ctrl;
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240 ushort sdtr_speed2;
1241 ushort sdtr_speed3;
1242 uchar max_host_qng;
1243 uchar max_dvc_qng;
1244 ushort dvc_cntl;
1245 ushort sdtr_speed4;
1246 ushort serial_number_word1;
1247 ushort serial_number_word2;
1248 ushort serial_number_word3;
1249 ushort check_sum;
1250 uchar oem_name[16];
1251 ushort dvc_err_code;
1252 ushort adv_err_code;
1253 ushort adv_err_addr;
1254 ushort saved_dvc_err_code;
1255 ushort saved_adv_err_code;
1256 ushort saved_adv_err_addr;
1257 ushort reserved36;
1258 ushort reserved37;
1259 ushort reserved38;
1260 ushort reserved39;
1261 ushort reserved40;
1262 ushort reserved41;
1263 ushort reserved42;
1264 ushort reserved43;
1265 ushort reserved44;
1266 ushort reserved45;
1267 ushort reserved46;
1268 ushort reserved47;
1269 ushort reserved48;
1270 ushort reserved49;
1271 ushort reserved50;
1272 ushort reserved51;
1273 ushort reserved52;
1274 ushort reserved53;
1275 ushort reserved54;
1276 ushort reserved55;
1277 ushort cisptr_lsw;
1278 ushort cisprt_msw;
1279 ushort subsysvid;
1280 ushort subsysid;
1281 ushort reserved60;
1282 ushort reserved61;
1283 ushort reserved62;
1284 ushort reserved63;
1285} ADVEEP_38C1600_CONFIG;
1286
1287
1288
1289
1290#define ASC_EEP_CMD_DONE 0x0200
1291
1292
1293#define BIOS_CTRL_BIOS 0x0001
1294#define BIOS_CTRL_EXTENDED_XLAT 0x0002
1295#define BIOS_CTRL_GT_2_DISK 0x0004
1296#define BIOS_CTRL_BIOS_REMOVABLE 0x0008
1297#define BIOS_CTRL_BOOTABLE_CD 0x0010
1298#define BIOS_CTRL_MULTIPLE_LUN 0x0040
1299#define BIOS_CTRL_DISPLAY_MSG 0x0080
1300#define BIOS_CTRL_NO_SCAM 0x0100
1301#define BIOS_CTRL_RESET_SCSI_BUS 0x0200
1302#define BIOS_CTRL_INIT_VERBOSE 0x0800
1303#define BIOS_CTRL_SCSI_PARITY 0x1000
1304#define BIOS_CTRL_AIPP_DIS 0x2000
1305
1306#define ADV_3550_MEMSIZE 0x2000
1307
1308#define ADV_38C0800_MEMSIZE 0x4000
1309
1310
1311
1312
1313
1314
1315
1316
1317#define ADV_38C1600_MEMSIZE 0x4000
1318
1319
1320
1321
1322#define IOPB_INTR_STATUS_REG 0x00
1323#define IOPB_CHIP_ID_1 0x01
1324#define IOPB_INTR_ENABLES 0x02
1325#define IOPB_CHIP_TYPE_REV 0x03
1326#define IOPB_RES_ADDR_4 0x04
1327#define IOPB_RES_ADDR_5 0x05
1328#define IOPB_RAM_DATA 0x06
1329#define IOPB_RES_ADDR_7 0x07
1330#define IOPB_FLAG_REG 0x08
1331#define IOPB_RES_ADDR_9 0x09
1332#define IOPB_RISC_CSR 0x0A
1333#define IOPB_RES_ADDR_B 0x0B
1334#define IOPB_RES_ADDR_C 0x0C
1335#define IOPB_RES_ADDR_D 0x0D
1336#define IOPB_SOFT_OVER_WR 0x0E
1337#define IOPB_RES_ADDR_F 0x0F
1338#define IOPB_MEM_CFG 0x10
1339#define IOPB_RES_ADDR_11 0x11
1340#define IOPB_GPIO_DATA 0x12
1341#define IOPB_RES_ADDR_13 0x13
1342#define IOPB_FLASH_PAGE 0x14
1343#define IOPB_RES_ADDR_15 0x15
1344#define IOPB_GPIO_CNTL 0x16
1345#define IOPB_RES_ADDR_17 0x17
1346#define IOPB_FLASH_DATA 0x18
1347#define IOPB_RES_ADDR_19 0x19
1348#define IOPB_RES_ADDR_1A 0x1A
1349#define IOPB_RES_ADDR_1B 0x1B
1350#define IOPB_RES_ADDR_1C 0x1C
1351#define IOPB_RES_ADDR_1D 0x1D
1352#define IOPB_RES_ADDR_1E 0x1E
1353#define IOPB_RES_ADDR_1F 0x1F
1354#define IOPB_DMA_CFG0 0x20
1355#define IOPB_DMA_CFG1 0x21
1356#define IOPB_TICKLE 0x22
1357#define IOPB_DMA_REG_WR 0x23
1358#define IOPB_SDMA_STATUS 0x24
1359#define IOPB_SCSI_BYTE_CNT 0x25
1360#define IOPB_HOST_BYTE_CNT 0x26
1361#define IOPB_BYTE_LEFT_TO_XFER 0x27
1362#define IOPB_BYTE_TO_XFER_0 0x28
1363#define IOPB_BYTE_TO_XFER_1 0x29
1364#define IOPB_BYTE_TO_XFER_2 0x2A
1365#define IOPB_BYTE_TO_XFER_3 0x2B
1366#define IOPB_ACC_GRP 0x2C
1367#define IOPB_RES_ADDR_2D 0x2D
1368#define IOPB_DEV_ID 0x2E
1369#define IOPB_RES_ADDR_2F 0x2F
1370#define IOPB_SCSI_DATA 0x30
1371#define IOPB_RES_ADDR_31 0x31
1372#define IOPB_RES_ADDR_32 0x32
1373#define IOPB_SCSI_DATA_HSHK 0x33
1374#define IOPB_SCSI_CTRL 0x34
1375#define IOPB_RES_ADDR_35 0x35
1376#define IOPB_RES_ADDR_36 0x36
1377#define IOPB_RES_ADDR_37 0x37
1378#define IOPB_RAM_BIST 0x38
1379#define IOPB_PLL_TEST 0x39
1380#define IOPB_PCI_INT_CFG 0x3A
1381#define IOPB_RES_ADDR_3B 0x3B
1382#define IOPB_RFIFO_CNT 0x3C
1383#define IOPB_RES_ADDR_3D 0x3D
1384#define IOPB_RES_ADDR_3E 0x3E
1385#define IOPB_RES_ADDR_3F 0x3F
1386
1387
1388
1389
1390#define IOPW_CHIP_ID_0 0x00
1391#define IOPW_CTRL_REG 0x02
1392#define IOPW_RAM_ADDR 0x04
1393#define IOPW_RAM_DATA 0x06
1394#define IOPW_RES_ADDR_08 0x08
1395#define IOPW_RISC_CSR 0x0A
1396#define IOPW_SCSI_CFG0 0x0C
1397#define IOPW_SCSI_CFG1 0x0E
1398#define IOPW_RES_ADDR_10 0x10
1399#define IOPW_SEL_MASK 0x12
1400#define IOPW_RES_ADDR_14 0x14
1401#define IOPW_FLASH_ADDR 0x16
1402#define IOPW_RES_ADDR_18 0x18
1403#define IOPW_EE_CMD 0x1A
1404#define IOPW_EE_DATA 0x1C
1405#define IOPW_SFIFO_CNT 0x1E
1406#define IOPW_RES_ADDR_20 0x20
1407#define IOPW_Q_BASE 0x22
1408#define IOPW_QP 0x24
1409#define IOPW_IX 0x26
1410#define IOPW_SP 0x28
1411#define IOPW_PC 0x2A
1412#define IOPW_RES_ADDR_2C 0x2C
1413#define IOPW_RES_ADDR_2E 0x2E
1414#define IOPW_SCSI_DATA 0x30
1415#define IOPW_SCSI_DATA_HSHK 0x32
1416#define IOPW_SCSI_CTRL 0x34
1417#define IOPW_HSHK_CFG 0x36
1418#define IOPW_SXFR_STATUS 0x36
1419#define IOPW_SXFR_CNTL 0x38
1420#define IOPW_SXFR_CNTH 0x3A
1421#define IOPW_RES_ADDR_3C 0x3C
1422#define IOPW_RFIFO_DATA 0x3E
1423
1424
1425
1426
1427#define IOPDW_RES_ADDR_0 0x00
1428#define IOPDW_RAM_DATA 0x04
1429#define IOPDW_RES_ADDR_8 0x08
1430#define IOPDW_RES_ADDR_C 0x0C
1431#define IOPDW_RES_ADDR_10 0x10
1432#define IOPDW_COMMA 0x14
1433#define IOPDW_COMMB 0x18
1434#define IOPDW_RES_ADDR_1C 0x1C
1435#define IOPDW_SDMA_ADDR0 0x20
1436#define IOPDW_SDMA_ADDR1 0x24
1437#define IOPDW_SDMA_COUNT 0x28
1438#define IOPDW_SDMA_ERROR 0x2C
1439#define IOPDW_RDMA_ADDR0 0x30
1440#define IOPDW_RDMA_ADDR1 0x34
1441#define IOPDW_RDMA_COUNT 0x38
1442#define IOPDW_RDMA_ERROR 0x3C
1443
1444#define ADV_CHIP_ID_BYTE 0x25
1445#define ADV_CHIP_ID_WORD 0x04C1
1446
1447#define ADV_INTR_ENABLE_HOST_INTR 0x01
1448#define ADV_INTR_ENABLE_SEL_INTR 0x02
1449#define ADV_INTR_ENABLE_DPR_INTR 0x04
1450#define ADV_INTR_ENABLE_RTA_INTR 0x08
1451#define ADV_INTR_ENABLE_RMA_INTR 0x10
1452#define ADV_INTR_ENABLE_RST_INTR 0x20
1453#define ADV_INTR_ENABLE_DPE_INTR 0x40
1454#define ADV_INTR_ENABLE_GLOBAL_INTR 0x80
1455
1456#define ADV_INTR_STATUS_INTRA 0x01
1457#define ADV_INTR_STATUS_INTRB 0x02
1458#define ADV_INTR_STATUS_INTRC 0x04
1459
1460#define ADV_RISC_CSR_STOP (0x0000)
1461#define ADV_RISC_TEST_COND (0x2000)
1462#define ADV_RISC_CSR_RUN (0x4000)
1463#define ADV_RISC_CSR_SINGLE_STEP (0x8000)
1464
1465#define ADV_CTRL_REG_HOST_INTR 0x0100
1466#define ADV_CTRL_REG_SEL_INTR 0x0200
1467#define ADV_CTRL_REG_DPR_INTR 0x0400
1468#define ADV_CTRL_REG_RTA_INTR 0x0800
1469#define ADV_CTRL_REG_RMA_INTR 0x1000
1470#define ADV_CTRL_REG_RES_BIT14 0x2000
1471#define ADV_CTRL_REG_DPE_INTR 0x4000
1472#define ADV_CTRL_REG_POWER_DONE 0x8000
1473#define ADV_CTRL_REG_ANY_INTR 0xFF00
1474
1475#define ADV_CTRL_REG_CMD_RESET 0x00C6
1476#define ADV_CTRL_REG_CMD_WR_IO_REG 0x00C5
1477#define ADV_CTRL_REG_CMD_RD_IO_REG 0x00C4
1478#define ADV_CTRL_REG_CMD_WR_PCI_CFG_SPACE 0x00C3
1479#define ADV_CTRL_REG_CMD_RD_PCI_CFG_SPACE 0x00C2
1480
1481#define ADV_TICKLE_NOP 0x00
1482#define ADV_TICKLE_A 0x01
1483#define ADV_TICKLE_B 0x02
1484#define ADV_TICKLE_C 0x03
1485
1486#define AdvIsIntPending(port) \
1487 (AdvReadWordRegister(port, IOPW_CTRL_REG) & ADV_CTRL_REG_HOST_INTR)
1488
1489
1490
1491
1492#define TIMER_MODEAB 0xC000
1493#define PARITY_EN 0x2000
1494#define EVEN_PARITY 0x1000
1495#define WD_LONG 0x0800
1496#define QUEUE_128 0x0400
1497#define PRIM_MODE 0x0100
1498#define SCAM_EN 0x0080
1499#define SEL_TMO_LONG 0x0040
1500#define CFRM_ID 0x0020
1501#define OUR_ID_EN 0x0010
1502#define OUR_ID 0x000F
1503
1504
1505
1506
1507#define BIG_ENDIAN 0x8000
1508#define TERM_POL 0x2000
1509#define SLEW_RATE 0x1000
1510#define FILTER_SEL 0x0C00
1511#define FLTR_DISABLE 0x0000
1512#define FLTR_11_TO_20NS 0x0800
1513#define FLTR_21_TO_39NS 0x0C00
1514#define ACTIVE_DBL 0x0200
1515#define DIFF_MODE 0x0100
1516#define DIFF_SENSE 0x0080
1517#define TERM_CTL_SEL 0x0040
1518#define TERM_CTL 0x0030
1519#define TERM_CTL_H 0x0020
1520#define TERM_CTL_L 0x0010
1521#define CABLE_DETECT 0x000F
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532
1533
1534#define DIS_TERM_DRV 0x4000
1535#define HVD_LVD_SE 0x1C00
1536#define HVD 0x1000
1537#define LVD 0x0800
1538#define SE 0x0400
1539#define TERM_LVD 0x00C0
1540#define TERM_LVD_HI 0x0080
1541#define TERM_LVD_LO 0x0040
1542#define TERM_SE 0x0030
1543#define TERM_SE_HI 0x0020
1544#define TERM_SE_LO 0x0010
1545#define C_DET_LVD 0x000C
1546#define C_DET3 0x0008
1547#define C_DET2 0x0004
1548#define C_DET_SE 0x0003
1549#define C_DET1 0x0002
1550#define C_DET0 0x0001
1551
1552#define CABLE_ILLEGAL_A 0x7
1553
1554
1555#define CABLE_ILLEGAL_B 0xB
1556
1557
1558
1559
1560
1561#define BIOS_EN 0x40
1562#define FAST_EE_CLK 0x20
1563#define RAM_SZ 0x1C
1564#define RAM_SZ_2KB 0x00
1565#define RAM_SZ_4KB 0x04
1566#define RAM_SZ_8KB 0x08
1567#define RAM_SZ_16KB 0x0C
1568#define RAM_SZ_32KB 0x10
1569#define RAM_SZ_64KB 0x14
1570
1571
1572
1573
1574
1575
1576#define BC_THRESH_ENB 0x80
1577#define FIFO_THRESH 0x70
1578#define FIFO_THRESH_16B 0x00
1579#define FIFO_THRESH_32B 0x20
1580#define FIFO_THRESH_48B 0x30
1581#define FIFO_THRESH_64B 0x40
1582#define FIFO_THRESH_80B 0x50
1583#define FIFO_THRESH_96B 0x60
1584#define FIFO_THRESH_112B 0x70
1585#define START_CTL 0x0C
1586#define START_CTL_TH 0x00
1587#define START_CTL_ID 0x04
1588#define START_CTL_THID 0x08
1589#define START_CTL_EMFU 0x0C
1590#define READ_CMD 0x03
1591#define READ_CMD_MR 0x00
1592#define READ_CMD_MRL 0x02
1593#define READ_CMD_MRM 0x03
1594
1595
1596
1597
1598#define RAM_TEST_MODE 0x80
1599#define PRE_TEST_MODE 0x40
1600#define NORMAL_MODE 0x00
1601#define RAM_TEST_DONE 0x10
1602#define RAM_TEST_STATUS 0x0F
1603#define RAM_TEST_HOST_ERROR 0x08
1604#define RAM_TEST_INTRAM_ERROR 0x04
1605#define RAM_TEST_RISC_ERROR 0x02
1606#define RAM_TEST_SCSI_ERROR 0x01
1607#define RAM_TEST_SUCCESS 0x00
1608#define PRE_TEST_VALUE 0x05
1609#define NORMAL_VALUE 0x00
1610
1611
1612
1613
1614
1615
1616
1617#define INTAB_LD 0x80
1618
1619
1620
1621
1622
1623
1624
1625#define TOTEMPOLE 0x02
1626
1627
1628
1629
1630
1631
1632
1633
1634
1635
1636#define INTAB 0x01
1637
1638
1639
1640
1641#define ADV_TRUE 1
1642#define ADV_FALSE 0
1643#define ADV_SUCCESS 1
1644#define ADV_BUSY 0
1645#define ADV_ERROR (-1)
1646
1647
1648
1649
1650#define ASC_WARN_BUSRESET_ERROR 0x0001
1651#define ASC_WARN_EEPROM_CHKSUM 0x0002
1652#define ASC_WARN_EEPROM_TERMINATION 0x0004
1653#define ASC_WARN_ERROR 0xFFFF
1654
1655#define ADV_MAX_TID 15
1656#define ADV_MAX_LUN 7
1657
1658
1659
1660
1661#define ASC_MC_CODE_BEGIN_ADDR 0x0028
1662#define ASC_MC_CODE_END_ADDR 0x002A
1663#define ASC_MC_CODE_CHK_SUM 0x002C
1664#define ASC_MC_VERSION_DATE 0x0038
1665#define ASC_MC_VERSION_NUM 0x003A
1666#define ASC_MC_BIOSMEM 0x0040
1667#define ASC_MC_BIOSLEN 0x0050
1668#define ASC_MC_BIOS_SIGNATURE 0x0058
1669#define ASC_MC_BIOS_VERSION 0x005A
1670#define ASC_MC_SDTR_SPEED1 0x0090
1671#define ASC_MC_SDTR_SPEED2 0x0092
1672#define ASC_MC_SDTR_SPEED3 0x0094
1673#define ASC_MC_SDTR_SPEED4 0x0096
1674#define ASC_MC_CHIP_TYPE 0x009A
1675#define ASC_MC_INTRB_CODE 0x009B
1676#define ASC_MC_WDTR_ABLE 0x009C
1677#define ASC_MC_SDTR_ABLE 0x009E
1678#define ASC_MC_TAGQNG_ABLE 0x00A0
1679#define ASC_MC_DISC_ENABLE 0x00A2
1680#define ASC_MC_IDLE_CMD_STATUS 0x00A4
1681#define ASC_MC_IDLE_CMD 0x00A6
1682#define ASC_MC_IDLE_CMD_PARAMETER 0x00A8
1683#define ASC_MC_DEFAULT_SCSI_CFG0 0x00AC
1684#define ASC_MC_DEFAULT_SCSI_CFG1 0x00AE
1685#define ASC_MC_DEFAULT_MEM_CFG 0x00B0
1686#define ASC_MC_DEFAULT_SEL_MASK 0x00B2
1687#define ASC_MC_SDTR_DONE 0x00B6
1688#define ASC_MC_NUMBER_OF_QUEUED_CMD 0x00C0
1689#define ASC_MC_NUMBER_OF_MAX_CMD 0x00D0
1690#define ASC_MC_DEVICE_HSHK_CFG_TABLE 0x0100
1691#define ASC_MC_CONTROL_FLAG 0x0122
1692#define ASC_MC_WDTR_DONE 0x0124
1693#define ASC_MC_CAM_MODE_MASK 0x015E
1694#define ASC_MC_ICQ 0x0160
1695#define ASC_MC_IRQ 0x0164
1696#define ASC_MC_PPR_ABLE 0x017A
1697
1698
1699
1700
1701#define BIOS_CODESEG 0x54
1702#define BIOS_CODELEN 0x56
1703#define BIOS_SIGNATURE 0x58
1704#define BIOS_VERSION 0x5A
1705
1706
1707
1708
1709
1710
1711
1712#define CONTROL_FLAG_IGNORE_PERR 0x0001
1713#define CONTROL_FLAG_ENABLE_AIPP 0x0002
1714
1715
1716
1717
1718#define HSHK_CFG_WIDE_XFR 0x8000
1719#define HSHK_CFG_RATE 0x0F00
1720#define HSHK_CFG_OFFSET 0x001F
1721
1722#define ASC_DEF_MAX_HOST_QNG 0xFD
1723#define ASC_DEF_MIN_HOST_QNG 0x10
1724#define ASC_DEF_MAX_DVC_QNG 0x3F
1725#define ASC_DEF_MIN_DVC_QNG 0x04
1726
1727#define ASC_QC_DATA_CHECK 0x01
1728#define ASC_QC_DATA_OUT 0x02
1729#define ASC_QC_START_MOTOR 0x04
1730#define ASC_QC_NO_OVERRUN 0x08
1731#define ASC_QC_FREEZE_TIDQ 0x10
1732
1733#define ASC_QSC_NO_DISC 0x01
1734#define ASC_QSC_NO_TAGMSG 0x02
1735#define ASC_QSC_NO_SYNC 0x04
1736#define ASC_QSC_NO_WIDE 0x08
1737#define ASC_QSC_REDO_DTR 0x10
1738
1739
1740
1741
1742#define ASC_QSC_HEAD_TAG 0x40
1743#define ASC_QSC_ORDERED_TAG 0x80
1744
1745
1746
1747
1748
1749typedef struct adv_carr_t {
1750 ADV_VADDR carr_va;
1751 ADV_PADDR carr_pa;
1752 ADV_VADDR areq_vpa;
1753
1754
1755
1756
1757
1758
1759 ADV_VADDR next_vpa;
1760} ADV_CARR_T;
1761
1762
1763
1764
1765#define ASC_NEXT_VPA_MASK 0xFFFFFFF0
1766
1767#define ASC_RQ_DONE 0x00000001
1768#define ASC_RQ_GOOD 0x00000002
1769#define ASC_CQ_STOPPER 0x00000000
1770
1771#define ASC_GET_CARRP(carrp) ((carrp) & ASC_NEXT_VPA_MASK)
1772
1773#define ADV_CARRIER_NUM_PAGE_CROSSING \
1774 (((ADV_CARRIER_COUNT * sizeof(ADV_CARR_T)) + (PAGE_SIZE - 1))/PAGE_SIZE)
1775
1776#define ADV_CARRIER_BUFSIZE \
1777 ((ADV_CARRIER_COUNT + ADV_CARRIER_NUM_PAGE_CROSSING) * sizeof(ADV_CARR_T))
1778
1779
1780
1781
1782
1783
1784
1785#define ADV_POLL_REQUEST 0x01
1786#define ADV_SCSIQ_DONE 0x02
1787#define ADV_DONT_RETRY 0x08
1788
1789#define ADV_CHIP_ASC3550 0x01
1790#define ADV_CHIP_ASC38C0800 0x02
1791#define ADV_CHIP_ASC38C1600 0x03
1792
1793
1794
1795
1796
1797
1798
1799
1800
1801
1802
1803
1804typedef struct adv_dvc_cfg {
1805 ushort disc_enable;
1806 uchar chip_version;
1807 uchar termination;
1808 ushort control_flag;
1809 ushort mcode_date;
1810 ushort mcode_version;
1811 ushort serial1;
1812 ushort serial2;
1813 ushort serial3;
1814} ADV_DVC_CFG;
1815
1816struct adv_dvc_var;
1817struct adv_scsi_req_q;
1818
1819typedef struct asc_sg_block {
1820 uchar reserved1;
1821 uchar reserved2;
1822 uchar reserved3;
1823 uchar sg_cnt;
1824 ADV_PADDR sg_ptr;
1825 struct {
1826 ADV_PADDR sg_addr;
1827 ADV_DCNT sg_count;
1828 } sg_list[NO_OF_SG_PER_BLOCK];
1829} ADV_SG_BLOCK;
1830
1831
1832
1833
1834
1835
1836
1837
1838
1839
1840
1841
1842typedef struct adv_scsi_req_q {
1843 uchar cntl;
1844 uchar target_cmd;
1845 uchar target_id;
1846 uchar target_lun;
1847 ADV_PADDR data_addr;
1848 ADV_DCNT data_cnt;
1849 ADV_PADDR sense_addr;
1850 ADV_PADDR carr_pa;
1851 uchar mflag;
1852 uchar sense_len;
1853 uchar cdb_len;
1854 uchar scsi_cntl;
1855 uchar done_status;
1856 uchar scsi_status;
1857 uchar host_status;
1858 uchar sg_working_ix;
1859 uchar cdb[12];
1860 ADV_PADDR sg_real_addr;
1861 ADV_PADDR scsiq_rptr;
1862 uchar cdb16[4];
1863 ADV_VADDR scsiq_ptr;
1864 ADV_VADDR carr_va;
1865
1866
1867
1868
1869 ADV_VADDR srb_ptr;
1870 ADV_SG_BLOCK *sg_list_ptr;
1871 char *vdata_addr;
1872 uchar a_flag;
1873 uchar pad[2];
1874} ADV_SCSI_REQ_Q;
1875
1876
1877
1878
1879
1880
1881
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891typedef struct adv_sgblk {
1892 ADV_SG_BLOCK sg_block;
1893 uchar align[32];
1894 struct adv_sgblk *next_sgblkp;
1895} adv_sgblk_t;
1896
1897typedef struct adv_req {
1898 ADV_SCSI_REQ_Q scsi_req_q;
1899 uchar align[32];
1900 struct scsi_cmnd *cmndp;
1901 adv_sgblk_t *sgblkp;
1902 struct adv_req *next_reqp;
1903} adv_req_t;
1904
1905
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917typedef struct adv_dvc_var {
1918 AdvPortAddr iop_base;
1919 ushort err_code;
1920 ushort bios_ctrl;
1921 ushort wdtr_able;
1922 ushort sdtr_able;
1923 ushort ultra_able;
1924 ushort sdtr_speed1;
1925 ushort sdtr_speed2;
1926 ushort sdtr_speed3;
1927 ushort sdtr_speed4;
1928 ushort tagqng_able;
1929 ushort ppr_able;
1930 uchar max_dvc_qng;
1931 ushort start_motor;
1932 uchar scsi_reset_wait;
1933 uchar chip_no;
1934 uchar max_host_qng;
1935 ushort no_scam;
1936 struct asc_board *drv_ptr;
1937 uchar chip_scsi_id;
1938 uchar chip_type;
1939 uchar bist_err_code;
1940 ADV_CARR_T *carrier_buf;
1941 ADV_CARR_T *carr_freelist;
1942 ADV_CARR_T *icq_sp;
1943 ADV_CARR_T *irq_sp;
1944 ushort carr_pending_cnt;
1945 struct adv_req *orig_reqp;
1946
1947
1948
1949
1950 ADV_DVC_CFG *cfg;
1951} ADV_DVC_VAR;
1952
1953
1954
1955
1956#define IDLE_CMD_COMPLETED 0
1957#define IDLE_CMD_STOP_CHIP 0x0001
1958#define IDLE_CMD_STOP_CHIP_SEND_INT 0x0002
1959#define IDLE_CMD_SEND_INT 0x0004
1960#define IDLE_CMD_ABORT 0x0008
1961#define IDLE_CMD_DEVICE_RESET 0x0010
1962#define IDLE_CMD_SCSI_RESET_START 0x0020
1963#define IDLE_CMD_SCSI_RESET_END 0x0040
1964#define IDLE_CMD_SCSIREQ 0x0080
1965
1966#define IDLE_CMD_STATUS_SUCCESS 0x0001
1967#define IDLE_CMD_STATUS_FAILURE 0x0002
1968
1969
1970
1971
1972#define ADV_NOWAIT 0x01
1973
1974
1975
1976
1977#define SCSI_WAIT_100_MSEC 100UL
1978#define SCSI_US_PER_MSEC 1000
1979#define SCSI_MAX_RETRY 10
1980
1981#define ADV_ASYNC_RDMA_FAILURE 0x01
1982#define ADV_ASYNC_SCSI_BUS_RESET_DET 0x02
1983#define ADV_ASYNC_CARRIER_READY_FAILURE 0x03
1984#define ADV_RDMA_IN_CARR_AND_Q_INVALID 0x04
1985
1986#define ADV_HOST_SCSI_BUS_RESET 0x80
1987
1988
1989#define AdvReadByteRegister(iop_base, reg_off) \
1990 (ADV_MEM_READB((iop_base) + (reg_off)))
1991
1992
1993#define AdvWriteByteRegister(iop_base, reg_off, byte) \
1994 (ADV_MEM_WRITEB((iop_base) + (reg_off), (byte)))
1995
1996
1997#define AdvReadWordRegister(iop_base, reg_off) \
1998 (ADV_MEM_READW((iop_base) + (reg_off)))
1999
2000
2001#define AdvWriteWordRegister(iop_base, reg_off, word) \
2002 (ADV_MEM_WRITEW((iop_base) + (reg_off), (word)))
2003
2004
2005#define AdvWriteDWordRegister(iop_base, reg_off, dword) \
2006 (ADV_MEM_WRITEDW((iop_base) + (reg_off), (dword)))
2007
2008
2009#define AdvReadByteLram(iop_base, addr, byte) \
2010do { \
2011 ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)); \
2012 (byte) = ADV_MEM_READB((iop_base) + IOPB_RAM_DATA); \
2013} while (0)
2014
2015
2016#define AdvWriteByteLram(iop_base, addr, byte) \
2017 (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
2018 ADV_MEM_WRITEB((iop_base) + IOPB_RAM_DATA, (byte)))
2019
2020
2021#define AdvReadWordLram(iop_base, addr, word) \
2022do { \
2023 ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)); \
2024 (word) = (ADV_MEM_READW((iop_base) + IOPW_RAM_DATA)); \
2025} while (0)
2026
2027
2028#define AdvWriteWordLram(iop_base, addr, word) \
2029 (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
2030 ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, (word)))
2031
2032
2033
2034#define AdvWriteDWordLramNoSwap(iop_base, addr, dword) \
2035 ((ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr)), \
2036 ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, \
2037 cpu_to_le16((ushort) ((dword) & 0xFFFF)))), \
2038 (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_ADDR, (addr) + 2), \
2039 ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, \
2040 cpu_to_le16((ushort) ((dword >> 16) & 0xFFFF)))))
2041
2042
2043#define AdvReadWordAutoIncLram(iop_base) \
2044 (ADV_MEM_READW((iop_base) + IOPW_RAM_DATA))
2045
2046
2047#define AdvWriteWordAutoIncLram(iop_base, word) \
2048 (ADV_MEM_WRITEW((iop_base) + IOPW_RAM_DATA, (word)))
2049
2050
2051
2052
2053
2054
2055
2056#define AdvFindSignature(iop_base) \
2057 (((AdvReadByteRegister((iop_base), IOPB_CHIP_ID_1) == \
2058 ADV_CHIP_ID_BYTE) && \
2059 (AdvReadWordRegister((iop_base), IOPW_CHIP_ID_0) == \
2060 ADV_CHIP_ID_WORD)) ? ADV_TRUE : ADV_FALSE)
2061
2062
2063
2064
2065
2066
2067#define AdvGetChipVersion(iop_base, bus_type) \
2068 AdvReadByteRegister((iop_base), IOPB_CHIP_TYPE_REV)
2069
2070
2071
2072
2073
2074
2075
2076
2077
2078
2079
2080
2081
2082#define AdvAbortQueue(asc_dvc, scsiq) \
2083 AdvSendIdleCmd((asc_dvc), (ushort) IDLE_CMD_ABORT, \
2084 (ADV_DCNT) (scsiq))
2085
2086
2087
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097#define AdvResetDevice(asc_dvc, target_id) \
2098 AdvSendIdleCmd((asc_dvc), (ushort) IDLE_CMD_DEVICE_RESET, \
2099 (ADV_DCNT) (target_id))
2100
2101
2102
2103
2104#define ADV_SCSI_BIT_ID_TYPE ushort
2105
2106
2107
2108
2109#define ADV_SCAN_LUN 0x01
2110#define ADV_CAPINFO_NOLUN 0x02
2111
2112
2113
2114
2115#define ADV_TID_TO_TIDMASK(tid) (0x01 << ((tid) & ADV_MAX_TID))
2116
2117
2118
2119
2120
2121#define QD_NO_STATUS 0x00
2122#define QD_NO_ERROR 0x01
2123#define QD_ABORTED_BY_HOST 0x02
2124#define QD_WITH_ERROR 0x04
2125
2126#define QHSTA_NO_ERROR 0x00
2127#define QHSTA_M_SEL_TIMEOUT 0x11
2128#define QHSTA_M_DATA_OVER_RUN 0x12
2129#define QHSTA_M_UNEXPECTED_BUS_FREE 0x13
2130#define QHSTA_M_QUEUE_ABORTED 0x15
2131#define QHSTA_M_SXFR_SDMA_ERR 0x16
2132#define QHSTA_M_SXFR_SXFR_PERR 0x17
2133#define QHSTA_M_RDMA_PERR 0x18
2134#define QHSTA_M_SXFR_OFF_UFLW 0x19
2135#define QHSTA_M_SXFR_OFF_OFLW 0x20
2136#define QHSTA_M_SXFR_WD_TMO 0x21
2137#define QHSTA_M_SXFR_DESELECTED 0x22
2138
2139#define QHSTA_M_SXFR_XFR_OFLW 0x12
2140#define QHSTA_M_SXFR_XFR_PH_ERR 0x24
2141#define QHSTA_M_SXFR_UNKNOWN_ERROR 0x25
2142#define QHSTA_M_SCSI_BUS_RESET 0x30
2143#define QHSTA_M_SCSI_BUS_RESET_UNSOL 0x31
2144#define QHSTA_M_BUS_DEVICE_RESET 0x32
2145#define QHSTA_M_DIRECTION_ERR 0x35
2146#define QHSTA_M_DIRECTION_ERR_HUNG 0x36
2147#define QHSTA_M_WTM_TIMEOUT 0x41
2148#define QHSTA_M_BAD_CMPL_STATUS_IN 0x42
2149#define QHSTA_M_NO_AUTO_REQ_SENSE 0x43
2150#define QHSTA_M_AUTO_REQ_SENSE_FAIL 0x44
2151#define QHSTA_M_INVALID_DEVICE 0x45
2152#define QHSTA_M_FROZEN_TIDQ 0x46
2153#define QHSTA_M_SGBACKUP_ERROR 0x47
2154
2155
2156#define ADV_8BALIGN(addr) (((ulong) (addr) + 0x7) & ~0x7)
2157#define ADV_16BALIGN(addr) (((ulong) (addr) + 0xF) & ~0xF)
2158#define ADV_32BALIGN(addr) (((ulong) (addr) + 0x1F) & ~0x1F)
2159
2160
2161
2162
2163
2164
2165
2166
2167
2168#define ADV_SG_LIST_MAX_BYTE_SIZE \
2169 (sizeof(ADV_SG_BLOCK) * \
2170 ((ADV_MAX_SG_LIST + (NO_OF_SG_PER_BLOCK - 1))/NO_OF_SG_PER_BLOCK))
2171
2172
2173#define ASC_IS_WIDE_BOARD 0x04
2174
2175#define ASC_NARROW_BOARD(boardp) (((boardp)->flags & ASC_IS_WIDE_BOARD) == 0)
2176
2177#define NO_ISA_DMA 0xff
2178
2179#define ASC_INFO_SIZE 128
2180
2181#ifdef CONFIG_PROC_FS
2182
2183#define ASC_PRTBUF_SIZE 2048
2184#define ASC_PRTLINE_SIZE 160
2185
2186#define ASC_PRT_NEXT() \
2187 if (cp) { \
2188 totlen += len; \
2189 leftlen -= len; \
2190 if (leftlen == 0) { \
2191 return totlen; \
2192 } \
2193 cp += len; \
2194 }
2195#endif
2196
2197
2198#define ASC_TRUE 1
2199#define ASC_FALSE 0
2200#define ASC_NOERROR 1
2201#define ASC_BUSY 0
2202#define ASC_ERROR (-1)
2203
2204
2205#define STATUS_BYTE(byte) (byte)
2206#define MSG_BYTE(byte) ((byte) << 8)
2207#define HOST_BYTE(byte) ((byte) << 16)
2208#define DRIVER_BYTE(byte) ((byte) << 24)
2209
2210#define ASC_STATS(shost, counter) ASC_STATS_ADD(shost, counter, 1)
2211#ifndef ADVANSYS_STATS
2212#define ASC_STATS_ADD(shost, counter, count)
2213#else
2214#define ASC_STATS_ADD(shost, counter, count) \
2215 (((struct asc_board *) shost_priv(shost))->asc_stats.counter += (count))
2216#endif
2217
2218
2219#define ASC_TENTHS(num, den) \
2220 (((10 * ((num)/(den))) > (((num) * 10)/(den))) ? \
2221 0 : ((((num) * 10)/(den)) - (10 * ((num)/(den)))))
2222
2223
2224
2225
2226#define ASC_PRINT(s) \
2227 { \
2228 printk("advansys: "); \
2229 printk(s); \
2230 }
2231
2232#define ASC_PRINT1(s, a1) \
2233 { \
2234 printk("advansys: "); \
2235 printk((s), (a1)); \
2236 }
2237
2238#define ASC_PRINT2(s, a1, a2) \
2239 { \
2240 printk("advansys: "); \
2241 printk((s), (a1), (a2)); \
2242 }
2243
2244#define ASC_PRINT3(s, a1, a2, a3) \
2245 { \
2246 printk("advansys: "); \
2247 printk((s), (a1), (a2), (a3)); \
2248 }
2249
2250#define ASC_PRINT4(s, a1, a2, a3, a4) \
2251 { \
2252 printk("advansys: "); \
2253 printk((s), (a1), (a2), (a3), (a4)); \
2254 }
2255
2256#ifndef ADVANSYS_DEBUG
2257
2258#define ASC_DBG(lvl, s...)
2259#define ASC_DBG_PRT_SCSI_HOST(lvl, s)
2260#define ASC_DBG_PRT_ASC_SCSI_Q(lvl, scsiqp)
2261#define ASC_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp)
2262#define ASC_DBG_PRT_ASC_QDONE_INFO(lvl, qdone)
2263#define ADV_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp)
2264#define ASC_DBG_PRT_HEX(lvl, name, start, length)
2265#define ASC_DBG_PRT_CDB(lvl, cdb, len)
2266#define ASC_DBG_PRT_SENSE(lvl, sense, len)
2267#define ASC_DBG_PRT_INQUIRY(lvl, inq, len)
2268
2269#else
2270
2271
2272
2273
2274
2275
2276
2277
2278#define ASC_DBG(lvl, format, arg...) { \
2279 if (asc_dbglvl >= (lvl)) \
2280 printk(KERN_DEBUG "%s: %s: " format, DRV_NAME, \
2281 __func__ , ## arg); \
2282}
2283
2284#define ASC_DBG_PRT_SCSI_HOST(lvl, s) \
2285 { \
2286 if (asc_dbglvl >= (lvl)) { \
2287 asc_prt_scsi_host(s); \
2288 } \
2289 }
2290
2291#define ASC_DBG_PRT_ASC_SCSI_Q(lvl, scsiqp) \
2292 { \
2293 if (asc_dbglvl >= (lvl)) { \
2294 asc_prt_asc_scsi_q(scsiqp); \
2295 } \
2296 }
2297
2298#define ASC_DBG_PRT_ASC_QDONE_INFO(lvl, qdone) \
2299 { \
2300 if (asc_dbglvl >= (lvl)) { \
2301 asc_prt_asc_qdone_info(qdone); \
2302 } \
2303 }
2304
2305#define ASC_DBG_PRT_ADV_SCSI_REQ_Q(lvl, scsiqp) \
2306 { \
2307 if (asc_dbglvl >= (lvl)) { \
2308 asc_prt_adv_scsi_req_q(scsiqp); \
2309 } \
2310 }
2311
2312#define ASC_DBG_PRT_HEX(lvl, name, start, length) \
2313 { \
2314 if (asc_dbglvl >= (lvl)) { \
2315 asc_prt_hex((name), (start), (length)); \
2316 } \
2317 }
2318
2319#define ASC_DBG_PRT_CDB(lvl, cdb, len) \
2320 ASC_DBG_PRT_HEX((lvl), "CDB", (uchar *) (cdb), (len));
2321
2322#define ASC_DBG_PRT_SENSE(lvl, sense, len) \
2323 ASC_DBG_PRT_HEX((lvl), "SENSE", (uchar *) (sense), (len));
2324
2325#define ASC_DBG_PRT_INQUIRY(lvl, inq, len) \
2326 ASC_DBG_PRT_HEX((lvl), "INQUIRY", (uchar *) (inq), (len));
2327#endif
2328
2329#ifdef ADVANSYS_STATS
2330
2331
2332struct asc_stats {
2333
2334 ADV_DCNT queuecommand;
2335 ADV_DCNT reset;
2336 ADV_DCNT biosparam;
2337 ADV_DCNT interrupt;
2338 ADV_DCNT callback;
2339 ADV_DCNT done;
2340 ADV_DCNT build_error;
2341 ADV_DCNT adv_build_noreq;
2342 ADV_DCNT adv_build_nosg;
2343
2344 ADV_DCNT exe_noerror;
2345 ADV_DCNT exe_busy;
2346 ADV_DCNT exe_error;
2347 ADV_DCNT exe_unknown;
2348
2349 ADV_DCNT xfer_cnt;
2350 ADV_DCNT xfer_elem;
2351 ADV_DCNT xfer_sect;
2352};
2353#endif
2354
2355
2356
2357
2358
2359
2360
2361
2362struct asc_board {
2363 struct device *dev;
2364 uint flags;
2365 unsigned int irq;
2366 union {
2367 ASC_DVC_VAR asc_dvc_var;
2368 ADV_DVC_VAR adv_dvc_var;
2369 } dvc_var;
2370 union {
2371 ASC_DVC_CFG asc_dvc_cfg;
2372 ADV_DVC_CFG adv_dvc_cfg;
2373 } dvc_cfg;
2374 ushort asc_n_io_port;
2375 ADV_SCSI_BIT_ID_TYPE init_tidmask;
2376 ushort reqcnt[ADV_MAX_TID + 1];
2377 ADV_SCSI_BIT_ID_TYPE queue_full;
2378 ushort queue_full_cnt[ADV_MAX_TID + 1];
2379 union {
2380 ASCEEP_CONFIG asc_eep;
2381 ADVEEP_3550_CONFIG adv_3550_eep;
2382 ADVEEP_38C0800_CONFIG adv_38C0800_eep;
2383 ADVEEP_38C1600_CONFIG adv_38C1600_eep;
2384 } eep_config;
2385 ulong last_reset;
2386
2387 char *prtbuf;
2388#ifdef ADVANSYS_STATS
2389 struct asc_stats asc_stats;
2390#endif
2391
2392
2393
2394 uchar sdtr_data[ASC_MAX_TID + 1];
2395
2396
2397
2398 void __iomem *ioremap_addr;
2399 ushort ioport;
2400 adv_req_t *adv_reqp;
2401 adv_sgblk_t *adv_sgblkp;
2402 ushort bios_signature;
2403 ushort bios_version;
2404 ushort bios_codeseg;
2405 ushort bios_codelen;
2406};
2407
2408#define asc_dvc_to_board(asc_dvc) container_of(asc_dvc, struct asc_board, \
2409 dvc_var.asc_dvc_var)
2410#define adv_dvc_to_board(adv_dvc) container_of(adv_dvc, struct asc_board, \
2411 dvc_var.adv_dvc_var)
2412#define adv_dvc_to_pdev(adv_dvc) to_pci_dev(adv_dvc_to_board(adv_dvc)->dev)
2413
2414#ifdef ADVANSYS_DEBUG
2415static int asc_dbglvl = 3;
2416
2417
2418
2419
2420static void asc_prt_asc_dvc_var(ASC_DVC_VAR *h)
2421{
2422 printk("ASC_DVC_VAR at addr 0x%lx\n", (ulong)h);
2423
2424 printk(" iop_base 0x%x, err_code 0x%x, dvc_cntl 0x%x, bug_fix_cntl "
2425 "%d,\n", h->iop_base, h->err_code, h->dvc_cntl, h->bug_fix_cntl);
2426
2427 printk(" bus_type %d, init_sdtr 0x%x,\n", h->bus_type,
2428 (unsigned)h->init_sdtr);
2429
2430 printk(" sdtr_done 0x%x, use_tagged_qng 0x%x, unit_not_ready 0x%x, "
2431 "chip_no 0x%x,\n", (unsigned)h->sdtr_done,
2432 (unsigned)h->use_tagged_qng, (unsigned)h->unit_not_ready,
2433 (unsigned)h->chip_no);
2434
2435 printk(" queue_full_or_busy 0x%x, start_motor 0x%x, scsi_reset_wait "
2436 "%u,\n", (unsigned)h->queue_full_or_busy,
2437 (unsigned)h->start_motor, (unsigned)h->scsi_reset_wait);
2438
2439 printk(" is_in_int %u, max_total_qng %u, cur_total_qng %u, "
2440 "in_critical_cnt %u,\n", (unsigned)h->is_in_int,
2441 (unsigned)h->max_total_qng, (unsigned)h->cur_total_qng,
2442 (unsigned)h->in_critical_cnt);
2443
2444 printk(" last_q_shortage %u, init_state 0x%x, no_scam 0x%x, "
2445 "pci_fix_asyn_xfer 0x%x,\n", (unsigned)h->last_q_shortage,
2446 (unsigned)h->init_state, (unsigned)h->no_scam,
2447 (unsigned)h->pci_fix_asyn_xfer);
2448
2449 printk(" cfg 0x%lx\n", (ulong)h->cfg);
2450}
2451
2452
2453
2454
2455static void asc_prt_asc_dvc_cfg(ASC_DVC_CFG *h)
2456{
2457 printk("ASC_DVC_CFG at addr 0x%lx\n", (ulong)h);
2458
2459 printk(" can_tagged_qng 0x%x, cmd_qng_enabled 0x%x,\n",
2460 h->can_tagged_qng, h->cmd_qng_enabled);
2461 printk(" disc_enable 0x%x, sdtr_enable 0x%x,\n",
2462 h->disc_enable, h->sdtr_enable);
2463
2464 printk(" chip_scsi_id %d, isa_dma_speed %d, isa_dma_channel %d, "
2465 "chip_version %d,\n", h->chip_scsi_id, h->isa_dma_speed,
2466 h->isa_dma_channel, h->chip_version);
2467
2468 printk(" mcode_date 0x%x, mcode_version %d\n",
2469 h->mcode_date, h->mcode_version);
2470}
2471
2472
2473
2474
2475
2476
2477static void asc_prt_adv_dvc_var(ADV_DVC_VAR *h)
2478{
2479 printk(" ADV_DVC_VAR at addr 0x%lx\n", (ulong)h);
2480
2481 printk(" iop_base 0x%lx, err_code 0x%x, ultra_able 0x%x\n",
2482 (ulong)h->iop_base, h->err_code, (unsigned)h->ultra_able);
2483
2484 printk(" sdtr_able 0x%x, wdtr_able 0x%x\n",
2485 (unsigned)h->sdtr_able, (unsigned)h->wdtr_able);
2486
2487 printk(" start_motor 0x%x, scsi_reset_wait 0x%x\n",
2488 (unsigned)h->start_motor, (unsigned)h->scsi_reset_wait);
2489
2490 printk(" max_host_qng %u, max_dvc_qng %u, carr_freelist 0x%lxn\n",
2491 (unsigned)h->max_host_qng, (unsigned)h->max_dvc_qng,
2492 (ulong)h->carr_freelist);
2493
2494 printk(" icq_sp 0x%lx, irq_sp 0x%lx\n",
2495 (ulong)h->icq_sp, (ulong)h->irq_sp);
2496
2497 printk(" no_scam 0x%x, tagqng_able 0x%x\n",
2498 (unsigned)h->no_scam, (unsigned)h->tagqng_able);
2499
2500 printk(" chip_scsi_id 0x%x, cfg 0x%lx\n",
2501 (unsigned)h->chip_scsi_id, (ulong)h->cfg);
2502}
2503
2504
2505
2506
2507
2508
2509static void asc_prt_adv_dvc_cfg(ADV_DVC_CFG *h)
2510{
2511 printk(" ADV_DVC_CFG at addr 0x%lx\n", (ulong)h);
2512
2513 printk(" disc_enable 0x%x, termination 0x%x\n",
2514 h->disc_enable, h->termination);
2515
2516 printk(" chip_version 0x%x, mcode_date 0x%x\n",
2517 h->chip_version, h->mcode_date);
2518
2519 printk(" mcode_version 0x%x, control_flag 0x%x\n",
2520 h->mcode_version, h->control_flag);
2521}
2522
2523
2524
2525
2526static void asc_prt_scsi_host(struct Scsi_Host *s)
2527{
2528 struct asc_board *boardp = shost_priv(s);
2529
2530 printk("Scsi_Host at addr 0x%p, device %s\n", s, dev_name(boardp->dev));
2531 printk(" host_busy %u, host_no %d, last_reset %d,\n",
2532 s->host_busy, s->host_no, (unsigned)s->last_reset);
2533
2534 printk(" base 0x%lx, io_port 0x%lx, irq %d,\n",
2535 (ulong)s->base, (ulong)s->io_port, boardp->irq);
2536
2537 printk(" dma_channel %d, this_id %d, can_queue %d,\n",
2538 s->dma_channel, s->this_id, s->can_queue);
2539
2540 printk(" cmd_per_lun %d, sg_tablesize %d, unchecked_isa_dma %d\n",
2541 s->cmd_per_lun, s->sg_tablesize, s->unchecked_isa_dma);
2542
2543 if (ASC_NARROW_BOARD(boardp)) {
2544 asc_prt_asc_dvc_var(&boardp->dvc_var.asc_dvc_var);
2545 asc_prt_asc_dvc_cfg(&boardp->dvc_cfg.asc_dvc_cfg);
2546 } else {
2547 asc_prt_adv_dvc_var(&boardp->dvc_var.adv_dvc_var);
2548 asc_prt_adv_dvc_cfg(&boardp->dvc_cfg.adv_dvc_cfg);
2549 }
2550}
2551
2552
2553
2554
2555
2556
2557
2558static void asc_prt_hex(char *f, uchar *s, int l)
2559{
2560 int i;
2561 int j;
2562 int k;
2563 int m;
2564
2565 printk("%s: (%d bytes)\n", f, l);
2566
2567 for (i = 0; i < l; i += 32) {
2568
2569
2570 if ((k = (l - i) / 4) >= 8) {
2571 k = 8;
2572 m = 0;
2573 } else {
2574 m = (l - i) % 4;
2575 }
2576
2577 for (j = 0; j < k; j++) {
2578 printk(" %2.2X%2.2X%2.2X%2.2X",
2579 (unsigned)s[i + (j * 4)],
2580 (unsigned)s[i + (j * 4) + 1],
2581 (unsigned)s[i + (j * 4) + 2],
2582 (unsigned)s[i + (j * 4) + 3]);
2583 }
2584
2585 switch (m) {
2586 case 0:
2587 default:
2588 break;
2589 case 1:
2590 printk(" %2.2X", (unsigned)s[i + (j * 4)]);
2591 break;
2592 case 2:
2593 printk(" %2.2X%2.2X",
2594 (unsigned)s[i + (j * 4)],
2595 (unsigned)s[i + (j * 4) + 1]);
2596 break;
2597 case 3:
2598 printk(" %2.2X%2.2X%2.2X",
2599 (unsigned)s[i + (j * 4) + 1],
2600 (unsigned)s[i + (j * 4) + 2],
2601 (unsigned)s[i + (j * 4) + 3]);
2602 break;
2603 }
2604
2605 printk("\n");
2606 }
2607}
2608
2609
2610
2611
2612static void asc_prt_asc_scsi_q(ASC_SCSI_Q *q)
2613{
2614 ASC_SG_HEAD *sgp;
2615 int i;
2616
2617 printk("ASC_SCSI_Q at addr 0x%lx\n", (ulong)q);
2618
2619 printk
2620 (" target_ix 0x%x, target_lun %u, srb_ptr 0x%lx, tag_code 0x%x,\n",
2621 q->q2.target_ix, q->q1.target_lun, (ulong)q->q2.srb_ptr,
2622 q->q2.tag_code);
2623
2624 printk
2625 (" data_addr 0x%lx, data_cnt %lu, sense_addr 0x%lx, sense_len %u,\n",
2626 (ulong)le32_to_cpu(q->q1.data_addr),
2627 (ulong)le32_to_cpu(q->q1.data_cnt),
2628 (ulong)le32_to_cpu(q->q1.sense_addr), q->q1.sense_len);
2629
2630 printk(" cdbptr 0x%lx, cdb_len %u, sg_head 0x%lx, sg_queue_cnt %u\n",
2631 (ulong)q->cdbptr, q->q2.cdb_len,
2632 (ulong)q->sg_head, q->q1.sg_queue_cnt);
2633
2634 if (q->sg_head) {
2635 sgp = q->sg_head;
2636 printk("ASC_SG_HEAD at addr 0x%lx\n", (ulong)sgp);
2637 printk(" entry_cnt %u, queue_cnt %u\n", sgp->entry_cnt,
2638 sgp->queue_cnt);
2639 for (i = 0; i < sgp->entry_cnt; i++) {
2640 printk(" [%u]: addr 0x%lx, bytes %lu\n",
2641 i, (ulong)le32_to_cpu(sgp->sg_list[i].addr),
2642 (ulong)le32_to_cpu(sgp->sg_list[i].bytes));
2643 }
2644
2645 }
2646}
2647
2648
2649
2650
2651static void asc_prt_asc_qdone_info(ASC_QDONE_INFO *q)
2652{
2653 printk("ASC_QDONE_INFO at addr 0x%lx\n", (ulong)q);
2654 printk(" srb_ptr 0x%lx, target_ix %u, cdb_len %u, tag_code %u,\n",
2655 (ulong)q->d2.srb_ptr, q->d2.target_ix, q->d2.cdb_len,
2656 q->d2.tag_code);
2657 printk
2658 (" done_stat 0x%x, host_stat 0x%x, scsi_stat 0x%x, scsi_msg 0x%x\n",
2659 q->d3.done_stat, q->d3.host_stat, q->d3.scsi_stat, q->d3.scsi_msg);
2660}
2661
2662
2663
2664
2665
2666
2667static void asc_prt_adv_sgblock(int sgblockno, ADV_SG_BLOCK *b)
2668{
2669 int i;
2670
2671 printk(" ASC_SG_BLOCK at addr 0x%lx (sgblockno %d)\n",
2672 (ulong)b, sgblockno);
2673 printk(" sg_cnt %u, sg_ptr 0x%lx\n",
2674 b->sg_cnt, (ulong)le32_to_cpu(b->sg_ptr));
2675 BUG_ON(b->sg_cnt > NO_OF_SG_PER_BLOCK);
2676 if (b->sg_ptr != 0)
2677 BUG_ON(b->sg_cnt != NO_OF_SG_PER_BLOCK);
2678 for (i = 0; i < b->sg_cnt; i++) {
2679 printk(" [%u]: sg_addr 0x%lx, sg_count 0x%lx\n",
2680 i, (ulong)b->sg_list[i].sg_addr,
2681 (ulong)b->sg_list[i].sg_count);
2682 }
2683}
2684
2685
2686
2687
2688
2689
2690static void asc_prt_adv_scsi_req_q(ADV_SCSI_REQ_Q *q)
2691{
2692 int sg_blk_cnt;
2693 struct asc_sg_block *sg_ptr;
2694
2695 printk("ADV_SCSI_REQ_Q at addr 0x%lx\n", (ulong)q);
2696
2697 printk(" target_id %u, target_lun %u, srb_ptr 0x%lx, a_flag 0x%x\n",
2698 q->target_id, q->target_lun, (ulong)q->srb_ptr, q->a_flag);
2699
2700 printk(" cntl 0x%x, data_addr 0x%lx, vdata_addr 0x%lx\n",
2701 q->cntl, (ulong)le32_to_cpu(q->data_addr), (ulong)q->vdata_addr);
2702
2703 printk(" data_cnt %lu, sense_addr 0x%lx, sense_len %u,\n",
2704 (ulong)le32_to_cpu(q->data_cnt),
2705 (ulong)le32_to_cpu(q->sense_addr), q->sense_len);
2706
2707 printk
2708 (" cdb_len %u, done_status 0x%x, host_status 0x%x, scsi_status 0x%x\n",
2709 q->cdb_len, q->done_status, q->host_status, q->scsi_status);
2710
2711 printk(" sg_working_ix 0x%x, target_cmd %u\n",
2712 q->sg_working_ix, q->target_cmd);
2713
2714 printk(" scsiq_rptr 0x%lx, sg_real_addr 0x%lx, sg_list_ptr 0x%lx\n",
2715 (ulong)le32_to_cpu(q->scsiq_rptr),
2716 (ulong)le32_to_cpu(q->sg_real_addr), (ulong)q->sg_list_ptr);
2717
2718
2719 if (q->sg_list_ptr != NULL) {
2720 sg_blk_cnt = 0;
2721 while (1) {
2722
2723
2724
2725
2726
2727
2728
2729 sg_ptr =
2730 &(((ADV_SG_BLOCK *)(q->sg_list_ptr))[sg_blk_cnt]);
2731 asc_prt_adv_sgblock(sg_blk_cnt, sg_ptr);
2732 if (sg_ptr->sg_ptr == 0) {
2733 break;
2734 }
2735 sg_blk_cnt++;
2736 }
2737 }
2738}
2739#endif
2740
2741
2742
2743
2744
2745
2746
2747
2748
2749
2750
2751#define BAD_SRB 0
2752static u32 advansys_ptr_to_srb(struct asc_dvc_var *asc_dvc, void *ptr)
2753{
2754 int i;
2755 void **new_ptr;
2756
2757 for (i = 0; i < asc_dvc->ptr_map_count; i++) {
2758 if (!asc_dvc->ptr_map[i])
2759 goto out;
2760 }
2761
2762 if (asc_dvc->ptr_map_count == 0)
2763 asc_dvc->ptr_map_count = 1;
2764 else
2765 asc_dvc->ptr_map_count *= 2;
2766
2767 new_ptr = krealloc(asc_dvc->ptr_map,
2768 asc_dvc->ptr_map_count * sizeof(void *), GFP_ATOMIC);
2769 if (!new_ptr)
2770 return BAD_SRB;
2771 asc_dvc->ptr_map = new_ptr;
2772 out:
2773 ASC_DBG(3, "Putting ptr %p into array offset %d\n", ptr, i);
2774 asc_dvc->ptr_map[i] = ptr;
2775 return i + 1;
2776}
2777
2778static void * advansys_srb_to_ptr(struct asc_dvc_var *asc_dvc, u32 srb)
2779{
2780 void *ptr;
2781
2782 srb--;
2783 if (srb >= asc_dvc->ptr_map_count) {
2784 printk("advansys: bad SRB %u, max %u\n", srb,
2785 asc_dvc->ptr_map_count);
2786 return NULL;
2787 }
2788 ptr = asc_dvc->ptr_map[srb];
2789 asc_dvc->ptr_map[srb] = NULL;
2790 ASC_DBG(3, "Returning ptr %p from array offset %d\n", ptr, srb);
2791 return ptr;
2792}
2793
2794
2795
2796
2797
2798
2799
2800
2801
2802
2803static const char *advansys_info(struct Scsi_Host *shost)
2804{
2805 static char info[ASC_INFO_SIZE];
2806 struct asc_board *boardp = shost_priv(shost);
2807 ASC_DVC_VAR *asc_dvc_varp;
2808 ADV_DVC_VAR *adv_dvc_varp;
2809 char *busname;
2810 char *widename = NULL;
2811
2812 if (ASC_NARROW_BOARD(boardp)) {
2813 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
2814 ASC_DBG(1, "begin\n");
2815 if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
2816 if ((asc_dvc_varp->bus_type & ASC_IS_ISAPNP) ==
2817 ASC_IS_ISAPNP) {
2818 busname = "ISA PnP";
2819 } else {
2820 busname = "ISA";
2821 }
2822 sprintf(info,
2823 "AdvanSys SCSI %s: %s: IO 0x%lX-0x%lX, IRQ 0x%X, DMA 0x%X",
2824 ASC_VERSION, busname,
2825 (ulong)shost->io_port,
2826 (ulong)shost->io_port + ASC_IOADR_GAP - 1,
2827 boardp->irq, shost->dma_channel);
2828 } else {
2829 if (asc_dvc_varp->bus_type & ASC_IS_VL) {
2830 busname = "VL";
2831 } else if (asc_dvc_varp->bus_type & ASC_IS_EISA) {
2832 busname = "EISA";
2833 } else if (asc_dvc_varp->bus_type & ASC_IS_PCI) {
2834 if ((asc_dvc_varp->bus_type & ASC_IS_PCI_ULTRA)
2835 == ASC_IS_PCI_ULTRA) {
2836 busname = "PCI Ultra";
2837 } else {
2838 busname = "PCI";
2839 }
2840 } else {
2841 busname = "?";
2842 shost_printk(KERN_ERR, shost, "unknown bus "
2843 "type %d\n", asc_dvc_varp->bus_type);
2844 }
2845 sprintf(info,
2846 "AdvanSys SCSI %s: %s: IO 0x%lX-0x%lX, IRQ 0x%X",
2847 ASC_VERSION, busname, (ulong)shost->io_port,
2848 (ulong)shost->io_port + ASC_IOADR_GAP - 1,
2849 boardp->irq);
2850 }
2851 } else {
2852
2853
2854
2855
2856
2857
2858
2859 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
2860 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
2861 widename = "Ultra-Wide";
2862 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
2863 widename = "Ultra2-Wide";
2864 } else {
2865 widename = "Ultra3-Wide";
2866 }
2867 sprintf(info,
2868 "AdvanSys SCSI %s: PCI %s: PCIMEM 0x%lX-0x%lX, IRQ 0x%X",
2869 ASC_VERSION, widename, (ulong)adv_dvc_varp->iop_base,
2870 (ulong)adv_dvc_varp->iop_base + boardp->asc_n_io_port - 1, boardp->irq);
2871 }
2872 BUG_ON(strlen(info) >= ASC_INFO_SIZE);
2873 ASC_DBG(1, "end\n");
2874 return info;
2875}
2876
2877#ifdef CONFIG_PROC_FS
2878
2879
2880
2881
2882
2883
2884
2885
2886
2887
2888
2889static int asc_prt_line(char *buf, int buflen, char *fmt, ...)
2890{
2891 va_list args;
2892 int ret;
2893 char s[ASC_PRTLINE_SIZE];
2894
2895 va_start(args, fmt);
2896 ret = vsprintf(s, fmt, args);
2897 BUG_ON(ret >= ASC_PRTLINE_SIZE);
2898 if (buf == NULL) {
2899 (void)printk(s);
2900 ret = 0;
2901 } else {
2902 ret = min(buflen, ret);
2903 memcpy(buf, s, ret);
2904 }
2905 va_end(args);
2906 return ret;
2907}
2908
2909
2910
2911
2912
2913
2914
2915
2916
2917
2918
2919
2920static int asc_prt_board_devices(struct Scsi_Host *shost, char *cp, int cplen)
2921{
2922 struct asc_board *boardp = shost_priv(shost);
2923 int leftlen;
2924 int totlen;
2925 int len;
2926 int chip_scsi_id;
2927 int i;
2928
2929 leftlen = cplen;
2930 totlen = len = 0;
2931
2932 len = asc_prt_line(cp, leftlen,
2933 "\nDevice Information for AdvanSys SCSI Host %d:\n",
2934 shost->host_no);
2935 ASC_PRT_NEXT();
2936
2937 if (ASC_NARROW_BOARD(boardp)) {
2938 chip_scsi_id = boardp->dvc_cfg.asc_dvc_cfg.chip_scsi_id;
2939 } else {
2940 chip_scsi_id = boardp->dvc_var.adv_dvc_var.chip_scsi_id;
2941 }
2942
2943 len = asc_prt_line(cp, leftlen, "Target IDs Detected:");
2944 ASC_PRT_NEXT();
2945 for (i = 0; i <= ADV_MAX_TID; i++) {
2946 if (boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) {
2947 len = asc_prt_line(cp, leftlen, " %X,", i);
2948 ASC_PRT_NEXT();
2949 }
2950 }
2951 len = asc_prt_line(cp, leftlen, " (%X=Host Adapter)\n", chip_scsi_id);
2952 ASC_PRT_NEXT();
2953
2954 return totlen;
2955}
2956
2957
2958
2959
2960static int asc_prt_adv_bios(struct Scsi_Host *shost, char *cp, int cplen)
2961{
2962 struct asc_board *boardp = shost_priv(shost);
2963 int leftlen;
2964 int totlen;
2965 int len;
2966 ushort major, minor, letter;
2967
2968 leftlen = cplen;
2969 totlen = len = 0;
2970
2971 len = asc_prt_line(cp, leftlen, "\nROM BIOS Version: ");
2972 ASC_PRT_NEXT();
2973
2974
2975
2976
2977
2978 if (boardp->bios_signature != 0x55AA) {
2979 len = asc_prt_line(cp, leftlen, "Disabled or Pre-3.1\n");
2980 ASC_PRT_NEXT();
2981 len = asc_prt_line(cp, leftlen,
2982 "BIOS either disabled or Pre-3.1. If it is pre-3.1, then a newer version\n");
2983 ASC_PRT_NEXT();
2984 len = asc_prt_line(cp, leftlen,
2985 "can be found at the ConnectCom FTP site: ftp://ftp.connectcom.net/pub\n");
2986 ASC_PRT_NEXT();
2987 } else {
2988 major = (boardp->bios_version >> 12) & 0xF;
2989 minor = (boardp->bios_version >> 8) & 0xF;
2990 letter = (boardp->bios_version & 0xFF);
2991
2992 len = asc_prt_line(cp, leftlen, "%d.%d%c\n",
2993 major, minor,
2994 letter >= 26 ? '?' : letter + 'A');
2995 ASC_PRT_NEXT();
2996
2997
2998
2999
3000
3001
3002 if (major < 3 || (major <= 3 && minor < 1) ||
3003 (major <= 3 && minor <= 1 && letter < ('I' - 'A'))) {
3004 len = asc_prt_line(cp, leftlen,
3005 "Newer version of ROM BIOS is available at the ConnectCom FTP site:\n");
3006 ASC_PRT_NEXT();
3007 len = asc_prt_line(cp, leftlen,
3008 "ftp://ftp.connectcom.net/pub\n");
3009 ASC_PRT_NEXT();
3010 }
3011 }
3012
3013 return totlen;
3014}
3015
3016
3017
3018
3019
3020
3021
3022
3023
3024
3025
3026
3027
3028
3029
3030
3031
3032
3033
3034
3035
3036
3037
3038
3039static int asc_get_eeprom_string(ushort *serialnum, uchar *cp)
3040{
3041 ushort w, num;
3042
3043 if ((serialnum[1] & 0xFE00) != ((ushort)0xAA << 8)) {
3044 return ASC_FALSE;
3045 } else {
3046
3047
3048
3049 w = serialnum[0];
3050
3051
3052 if ((*cp = 'A' + ((w & 0xE000) >> 13)) == 'H') {
3053
3054 *cp += 0x8;
3055 }
3056 cp++;
3057
3058
3059 *cp++ = 'A' + ((w & 0x1C00) >> 10);
3060
3061
3062 num = w & 0x3FF;
3063 *cp++ = '0' + (num / 100);
3064 num %= 100;
3065 *cp++ = '0' + (num / 10);
3066
3067
3068 *cp++ = 'A' + (num % 10);
3069
3070
3071
3072
3073 w = serialnum[1];
3074
3075
3076
3077
3078
3079
3080
3081 if (serialnum[2] & 0x8000) {
3082 *cp++ = '8' + ((w & 0x1C0) >> 6);
3083 } else {
3084 *cp++ = '0' + ((w & 0x1C0) >> 6);
3085 }
3086
3087
3088 num = w & 0x003F;
3089 *cp++ = '0' + num / 10;
3090 num %= 10;
3091 *cp++ = '0' + num;
3092
3093
3094
3095
3096 w = serialnum[2] & 0x7FFF;
3097
3098
3099 *cp++ = 'A' + (w / 1000);
3100
3101
3102 num = w % 1000;
3103 *cp++ = '0' + num / 100;
3104 num %= 100;
3105 *cp++ = '0' + num / 10;
3106 num %= 10;
3107 *cp++ = '0' + num;
3108
3109 *cp = '\0';
3110 return ASC_TRUE;
3111 }
3112}
3113
3114
3115
3116
3117
3118
3119
3120
3121
3122
3123
3124
3125static int asc_prt_asc_board_eeprom(struct Scsi_Host *shost, char *cp, int cplen)
3126{
3127 struct asc_board *boardp = shost_priv(shost);
3128 ASC_DVC_VAR *asc_dvc_varp;
3129 int leftlen;
3130 int totlen;
3131 int len;
3132 ASCEEP_CONFIG *ep;
3133 int i;
3134#ifdef CONFIG_ISA
3135 int isa_dma_speed[] = { 10, 8, 7, 6, 5, 4, 3, 2 };
3136#endif
3137 uchar serialstr[13];
3138
3139 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
3140 ep = &boardp->eep_config.asc_eep;
3141
3142 leftlen = cplen;
3143 totlen = len = 0;
3144
3145 len = asc_prt_line(cp, leftlen,
3146 "\nEEPROM Settings for AdvanSys SCSI Host %d:\n",
3147 shost->host_no);
3148 ASC_PRT_NEXT();
3149
3150 if (asc_get_eeprom_string((ushort *)&ep->adapter_info[0], serialstr)
3151 == ASC_TRUE) {
3152 len =
3153 asc_prt_line(cp, leftlen, " Serial Number: %s\n",
3154 serialstr);
3155 ASC_PRT_NEXT();
3156 } else {
3157 if (ep->adapter_info[5] == 0xBB) {
3158 len = asc_prt_line(cp, leftlen,
3159 " Default Settings Used for EEPROM-less Adapter.\n");
3160 ASC_PRT_NEXT();
3161 } else {
3162 len = asc_prt_line(cp, leftlen,
3163 " Serial Number Signature Not Present.\n");
3164 ASC_PRT_NEXT();
3165 }
3166 }
3167
3168 len = asc_prt_line(cp, leftlen,
3169 " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
3170 ASC_EEP_GET_CHIP_ID(ep), ep->max_total_qng,
3171 ep->max_tag_qng);
3172 ASC_PRT_NEXT();
3173
3174 len = asc_prt_line(cp, leftlen,
3175 " cntl 0x%x, no_scam 0x%x\n", ep->cntl, ep->no_scam);
3176 ASC_PRT_NEXT();
3177
3178 len = asc_prt_line(cp, leftlen, " Target ID: ");
3179 ASC_PRT_NEXT();
3180 for (i = 0; i <= ASC_MAX_TID; i++) {
3181 len = asc_prt_line(cp, leftlen, " %d", i);
3182 ASC_PRT_NEXT();
3183 }
3184 len = asc_prt_line(cp, leftlen, "\n");
3185 ASC_PRT_NEXT();
3186
3187 len = asc_prt_line(cp, leftlen, " Disconnects: ");
3188 ASC_PRT_NEXT();
3189 for (i = 0; i <= ASC_MAX_TID; i++) {
3190 len = asc_prt_line(cp, leftlen, " %c",
3191 (ep->
3192 disc_enable & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3193 'N');
3194 ASC_PRT_NEXT();
3195 }
3196 len = asc_prt_line(cp, leftlen, "\n");
3197 ASC_PRT_NEXT();
3198
3199 len = asc_prt_line(cp, leftlen, " Command Queuing: ");
3200 ASC_PRT_NEXT();
3201 for (i = 0; i <= ASC_MAX_TID; i++) {
3202 len = asc_prt_line(cp, leftlen, " %c",
3203 (ep->
3204 use_cmd_qng & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3205 'N');
3206 ASC_PRT_NEXT();
3207 }
3208 len = asc_prt_line(cp, leftlen, "\n");
3209 ASC_PRT_NEXT();
3210
3211 len = asc_prt_line(cp, leftlen, " Start Motor: ");
3212 ASC_PRT_NEXT();
3213 for (i = 0; i <= ASC_MAX_TID; i++) {
3214 len = asc_prt_line(cp, leftlen, " %c",
3215 (ep->
3216 start_motor & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3217 'N');
3218 ASC_PRT_NEXT();
3219 }
3220 len = asc_prt_line(cp, leftlen, "\n");
3221 ASC_PRT_NEXT();
3222
3223 len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
3224 ASC_PRT_NEXT();
3225 for (i = 0; i <= ASC_MAX_TID; i++) {
3226 len = asc_prt_line(cp, leftlen, " %c",
3227 (ep->
3228 init_sdtr & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3229 'N');
3230 ASC_PRT_NEXT();
3231 }
3232 len = asc_prt_line(cp, leftlen, "\n");
3233 ASC_PRT_NEXT();
3234
3235#ifdef CONFIG_ISA
3236 if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
3237 len = asc_prt_line(cp, leftlen,
3238 " Host ISA DMA speed: %d MB/S\n",
3239 isa_dma_speed[ASC_EEP_GET_DMA_SPD(ep)]);
3240 ASC_PRT_NEXT();
3241 }
3242#endif
3243
3244 return totlen;
3245}
3246
3247
3248
3249
3250
3251
3252
3253
3254
3255
3256
3257
3258static int asc_prt_adv_board_eeprom(struct Scsi_Host *shost, char *cp, int cplen)
3259{
3260 struct asc_board *boardp = shost_priv(shost);
3261 ADV_DVC_VAR *adv_dvc_varp;
3262 int leftlen;
3263 int totlen;
3264 int len;
3265 int i;
3266 char *termstr;
3267 uchar serialstr[13];
3268 ADVEEP_3550_CONFIG *ep_3550 = NULL;
3269 ADVEEP_38C0800_CONFIG *ep_38C0800 = NULL;
3270 ADVEEP_38C1600_CONFIG *ep_38C1600 = NULL;
3271 ushort word;
3272 ushort *wordp;
3273 ushort sdtr_speed = 0;
3274
3275 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
3276 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3277 ep_3550 = &boardp->eep_config.adv_3550_eep;
3278 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3279 ep_38C0800 = &boardp->eep_config.adv_38C0800_eep;
3280 } else {
3281 ep_38C1600 = &boardp->eep_config.adv_38C1600_eep;
3282 }
3283
3284 leftlen = cplen;
3285 totlen = len = 0;
3286
3287 len = asc_prt_line(cp, leftlen,
3288 "\nEEPROM Settings for AdvanSys SCSI Host %d:\n",
3289 shost->host_no);
3290 ASC_PRT_NEXT();
3291
3292 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3293 wordp = &ep_3550->serial_number_word1;
3294 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3295 wordp = &ep_38C0800->serial_number_word1;
3296 } else {
3297 wordp = &ep_38C1600->serial_number_word1;
3298 }
3299
3300 if (asc_get_eeprom_string(wordp, serialstr) == ASC_TRUE) {
3301 len =
3302 asc_prt_line(cp, leftlen, " Serial Number: %s\n",
3303 serialstr);
3304 ASC_PRT_NEXT();
3305 } else {
3306 len = asc_prt_line(cp, leftlen,
3307 " Serial Number Signature Not Present.\n");
3308 ASC_PRT_NEXT();
3309 }
3310
3311 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3312 len = asc_prt_line(cp, leftlen,
3313 " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
3314 ep_3550->adapter_scsi_id,
3315 ep_3550->max_host_qng, ep_3550->max_dvc_qng);
3316 ASC_PRT_NEXT();
3317 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3318 len = asc_prt_line(cp, leftlen,
3319 " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
3320 ep_38C0800->adapter_scsi_id,
3321 ep_38C0800->max_host_qng,
3322 ep_38C0800->max_dvc_qng);
3323 ASC_PRT_NEXT();
3324 } else {
3325 len = asc_prt_line(cp, leftlen,
3326 " Host SCSI ID: %u, Host Queue Size: %u, Device Queue Size: %u\n",
3327 ep_38C1600->adapter_scsi_id,
3328 ep_38C1600->max_host_qng,
3329 ep_38C1600->max_dvc_qng);
3330 ASC_PRT_NEXT();
3331 }
3332 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3333 word = ep_3550->termination;
3334 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3335 word = ep_38C0800->termination_lvd;
3336 } else {
3337 word = ep_38C1600->termination_lvd;
3338 }
3339 switch (word) {
3340 case 1:
3341 termstr = "Low Off/High Off";
3342 break;
3343 case 2:
3344 termstr = "Low Off/High On";
3345 break;
3346 case 3:
3347 termstr = "Low On/High On";
3348 break;
3349 default:
3350 case 0:
3351 termstr = "Automatic";
3352 break;
3353 }
3354
3355 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3356 len = asc_prt_line(cp, leftlen,
3357 " termination: %u (%s), bios_ctrl: 0x%x\n",
3358 ep_3550->termination, termstr,
3359 ep_3550->bios_ctrl);
3360 ASC_PRT_NEXT();
3361 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3362 len = asc_prt_line(cp, leftlen,
3363 " termination: %u (%s), bios_ctrl: 0x%x\n",
3364 ep_38C0800->termination_lvd, termstr,
3365 ep_38C0800->bios_ctrl);
3366 ASC_PRT_NEXT();
3367 } else {
3368 len = asc_prt_line(cp, leftlen,
3369 " termination: %u (%s), bios_ctrl: 0x%x\n",
3370 ep_38C1600->termination_lvd, termstr,
3371 ep_38C1600->bios_ctrl);
3372 ASC_PRT_NEXT();
3373 }
3374
3375 len = asc_prt_line(cp, leftlen, " Target ID: ");
3376 ASC_PRT_NEXT();
3377 for (i = 0; i <= ADV_MAX_TID; i++) {
3378 len = asc_prt_line(cp, leftlen, " %X", i);
3379 ASC_PRT_NEXT();
3380 }
3381 len = asc_prt_line(cp, leftlen, "\n");
3382 ASC_PRT_NEXT();
3383
3384 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3385 word = ep_3550->disc_enable;
3386 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3387 word = ep_38C0800->disc_enable;
3388 } else {
3389 word = ep_38C1600->disc_enable;
3390 }
3391 len = asc_prt_line(cp, leftlen, " Disconnects: ");
3392 ASC_PRT_NEXT();
3393 for (i = 0; i <= ADV_MAX_TID; i++) {
3394 len = asc_prt_line(cp, leftlen, " %c",
3395 (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
3396 ASC_PRT_NEXT();
3397 }
3398 len = asc_prt_line(cp, leftlen, "\n");
3399 ASC_PRT_NEXT();
3400
3401 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3402 word = ep_3550->tagqng_able;
3403 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3404 word = ep_38C0800->tagqng_able;
3405 } else {
3406 word = ep_38C1600->tagqng_able;
3407 }
3408 len = asc_prt_line(cp, leftlen, " Command Queuing: ");
3409 ASC_PRT_NEXT();
3410 for (i = 0; i <= ADV_MAX_TID; i++) {
3411 len = asc_prt_line(cp, leftlen, " %c",
3412 (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
3413 ASC_PRT_NEXT();
3414 }
3415 len = asc_prt_line(cp, leftlen, "\n");
3416 ASC_PRT_NEXT();
3417
3418 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3419 word = ep_3550->start_motor;
3420 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3421 word = ep_38C0800->start_motor;
3422 } else {
3423 word = ep_38C1600->start_motor;
3424 }
3425 len = asc_prt_line(cp, leftlen, " Start Motor: ");
3426 ASC_PRT_NEXT();
3427 for (i = 0; i <= ADV_MAX_TID; i++) {
3428 len = asc_prt_line(cp, leftlen, " %c",
3429 (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
3430 ASC_PRT_NEXT();
3431 }
3432 len = asc_prt_line(cp, leftlen, "\n");
3433 ASC_PRT_NEXT();
3434
3435 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3436 len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
3437 ASC_PRT_NEXT();
3438 for (i = 0; i <= ADV_MAX_TID; i++) {
3439 len = asc_prt_line(cp, leftlen, " %c",
3440 (ep_3550->
3441 sdtr_able & ADV_TID_TO_TIDMASK(i)) ?
3442 'Y' : 'N');
3443 ASC_PRT_NEXT();
3444 }
3445 len = asc_prt_line(cp, leftlen, "\n");
3446 ASC_PRT_NEXT();
3447 }
3448
3449 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3450 len = asc_prt_line(cp, leftlen, " Ultra Transfer: ");
3451 ASC_PRT_NEXT();
3452 for (i = 0; i <= ADV_MAX_TID; i++) {
3453 len = asc_prt_line(cp, leftlen, " %c",
3454 (ep_3550->
3455 ultra_able & ADV_TID_TO_TIDMASK(i))
3456 ? 'Y' : 'N');
3457 ASC_PRT_NEXT();
3458 }
3459 len = asc_prt_line(cp, leftlen, "\n");
3460 ASC_PRT_NEXT();
3461 }
3462
3463 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
3464 word = ep_3550->wdtr_able;
3465 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
3466 word = ep_38C0800->wdtr_able;
3467 } else {
3468 word = ep_38C1600->wdtr_able;
3469 }
3470 len = asc_prt_line(cp, leftlen, " Wide Transfer: ");
3471 ASC_PRT_NEXT();
3472 for (i = 0; i <= ADV_MAX_TID; i++) {
3473 len = asc_prt_line(cp, leftlen, " %c",
3474 (word & ADV_TID_TO_TIDMASK(i)) ? 'Y' : 'N');
3475 ASC_PRT_NEXT();
3476 }
3477 len = asc_prt_line(cp, leftlen, "\n");
3478 ASC_PRT_NEXT();
3479
3480 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800 ||
3481 adv_dvc_varp->chip_type == ADV_CHIP_ASC38C1600) {
3482 len = asc_prt_line(cp, leftlen,
3483 " Synchronous Transfer Speed (Mhz):\n ");
3484 ASC_PRT_NEXT();
3485 for (i = 0; i <= ADV_MAX_TID; i++) {
3486 char *speed_str;
3487
3488 if (i == 0) {
3489 sdtr_speed = adv_dvc_varp->sdtr_speed1;
3490 } else if (i == 4) {
3491 sdtr_speed = adv_dvc_varp->sdtr_speed2;
3492 } else if (i == 8) {
3493 sdtr_speed = adv_dvc_varp->sdtr_speed3;
3494 } else if (i == 12) {
3495 sdtr_speed = adv_dvc_varp->sdtr_speed4;
3496 }
3497 switch (sdtr_speed & ADV_MAX_TID) {
3498 case 0:
3499 speed_str = "Off";
3500 break;
3501 case 1:
3502 speed_str = " 5";
3503 break;
3504 case 2:
3505 speed_str = " 10";
3506 break;
3507 case 3:
3508 speed_str = " 20";
3509 break;
3510 case 4:
3511 speed_str = " 40";
3512 break;
3513 case 5:
3514 speed_str = " 80";
3515 break;
3516 default:
3517 speed_str = "Unk";
3518 break;
3519 }
3520 len = asc_prt_line(cp, leftlen, "%X:%s ", i, speed_str);
3521 ASC_PRT_NEXT();
3522 if (i == 7) {
3523 len = asc_prt_line(cp, leftlen, "\n ");
3524 ASC_PRT_NEXT();
3525 }
3526 sdtr_speed >>= 4;
3527 }
3528 len = asc_prt_line(cp, leftlen, "\n");
3529 ASC_PRT_NEXT();
3530 }
3531
3532 return totlen;
3533}
3534
3535
3536
3537
3538
3539
3540
3541
3542
3543
3544static int asc_prt_driver_conf(struct Scsi_Host *shost, char *cp, int cplen)
3545{
3546 struct asc_board *boardp = shost_priv(shost);
3547 int leftlen;
3548 int totlen;
3549 int len;
3550 int chip_scsi_id;
3551
3552 leftlen = cplen;
3553 totlen = len = 0;
3554
3555 len = asc_prt_line(cp, leftlen,
3556 "\nLinux Driver Configuration and Information for AdvanSys SCSI Host %d:\n",
3557 shost->host_no);
3558 ASC_PRT_NEXT();
3559
3560 len = asc_prt_line(cp, leftlen,
3561 " host_busy %u, last_reset %u, max_id %u, max_lun %u, max_channel %u\n",
3562 shost->host_busy, shost->last_reset, shost->max_id,
3563 shost->max_lun, shost->max_channel);
3564 ASC_PRT_NEXT();
3565
3566 len = asc_prt_line(cp, leftlen,
3567 " unique_id %d, can_queue %d, this_id %d, sg_tablesize %u, cmd_per_lun %u\n",
3568 shost->unique_id, shost->can_queue, shost->this_id,
3569 shost->sg_tablesize, shost->cmd_per_lun);
3570 ASC_PRT_NEXT();
3571
3572 len = asc_prt_line(cp, leftlen,
3573 " unchecked_isa_dma %d, use_clustering %d\n",
3574 shost->unchecked_isa_dma, shost->use_clustering);
3575 ASC_PRT_NEXT();
3576
3577 len = asc_prt_line(cp, leftlen,
3578 " flags 0x%x, last_reset 0x%x, jiffies 0x%x, asc_n_io_port 0x%x\n",
3579 boardp->flags, boardp->last_reset, jiffies,
3580 boardp->asc_n_io_port);
3581 ASC_PRT_NEXT();
3582
3583 len = asc_prt_line(cp, leftlen, " io_port 0x%x\n", shost->io_port);
3584 ASC_PRT_NEXT();
3585
3586 if (ASC_NARROW_BOARD(boardp)) {
3587 chip_scsi_id = boardp->dvc_cfg.asc_dvc_cfg.chip_scsi_id;
3588 } else {
3589 chip_scsi_id = boardp->dvc_var.adv_dvc_var.chip_scsi_id;
3590 }
3591
3592 return totlen;
3593}
3594
3595
3596
3597
3598
3599
3600
3601
3602
3603
3604
3605
3606static int asc_prt_asc_board_info(struct Scsi_Host *shost, char *cp, int cplen)
3607{
3608 struct asc_board *boardp = shost_priv(shost);
3609 int chip_scsi_id;
3610 int leftlen;
3611 int totlen;
3612 int len;
3613 ASC_DVC_VAR *v;
3614 ASC_DVC_CFG *c;
3615 int i;
3616 int renegotiate = 0;
3617
3618 v = &boardp->dvc_var.asc_dvc_var;
3619 c = &boardp->dvc_cfg.asc_dvc_cfg;
3620 chip_scsi_id = c->chip_scsi_id;
3621
3622 leftlen = cplen;
3623 totlen = len = 0;
3624
3625 len = asc_prt_line(cp, leftlen,
3626 "\nAsc Library Configuration and Statistics for AdvanSys SCSI Host %d:\n",
3627 shost->host_no);
3628 ASC_PRT_NEXT();
3629
3630 len = asc_prt_line(cp, leftlen, " chip_version %u, mcode_date 0x%x, "
3631 "mcode_version 0x%x, err_code %u\n",
3632 c->chip_version, c->mcode_date, c->mcode_version,
3633 v->err_code);
3634 ASC_PRT_NEXT();
3635
3636
3637 len = asc_prt_line(cp, leftlen,
3638 " Total Command Pending: %d\n", v->cur_total_qng);
3639 ASC_PRT_NEXT();
3640
3641 len = asc_prt_line(cp, leftlen, " Command Queuing:");
3642 ASC_PRT_NEXT();
3643 for (i = 0; i <= ASC_MAX_TID; i++) {
3644 if ((chip_scsi_id == i) ||
3645 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3646 continue;
3647 }
3648 len = asc_prt_line(cp, leftlen, " %X:%c",
3649 i,
3650 (v->
3651 use_tagged_qng & ADV_TID_TO_TIDMASK(i)) ?
3652 'Y' : 'N');
3653 ASC_PRT_NEXT();
3654 }
3655 len = asc_prt_line(cp, leftlen, "\n");
3656 ASC_PRT_NEXT();
3657
3658
3659 len = asc_prt_line(cp, leftlen, " Command Queue Pending:");
3660 ASC_PRT_NEXT();
3661 for (i = 0; i <= ASC_MAX_TID; i++) {
3662 if ((chip_scsi_id == i) ||
3663 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3664 continue;
3665 }
3666 len = asc_prt_line(cp, leftlen, " %X:%u", i, v->cur_dvc_qng[i]);
3667 ASC_PRT_NEXT();
3668 }
3669 len = asc_prt_line(cp, leftlen, "\n");
3670 ASC_PRT_NEXT();
3671
3672
3673 len = asc_prt_line(cp, leftlen, " Command Queue Limit:");
3674 ASC_PRT_NEXT();
3675 for (i = 0; i <= ASC_MAX_TID; i++) {
3676 if ((chip_scsi_id == i) ||
3677 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3678 continue;
3679 }
3680 len = asc_prt_line(cp, leftlen, " %X:%u", i, v->max_dvc_qng[i]);
3681 ASC_PRT_NEXT();
3682 }
3683 len = asc_prt_line(cp, leftlen, "\n");
3684 ASC_PRT_NEXT();
3685
3686
3687 len = asc_prt_line(cp, leftlen, " Command Queue Full:");
3688 ASC_PRT_NEXT();
3689 for (i = 0; i <= ASC_MAX_TID; i++) {
3690 if ((chip_scsi_id == i) ||
3691 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3692 continue;
3693 }
3694 if (boardp->queue_full & ADV_TID_TO_TIDMASK(i)) {
3695 len = asc_prt_line(cp, leftlen, " %X:Y-%d",
3696 i, boardp->queue_full_cnt[i]);
3697 } else {
3698 len = asc_prt_line(cp, leftlen, " %X:N", i);
3699 }
3700 ASC_PRT_NEXT();
3701 }
3702 len = asc_prt_line(cp, leftlen, "\n");
3703 ASC_PRT_NEXT();
3704
3705 len = asc_prt_line(cp, leftlen, " Synchronous Transfer:");
3706 ASC_PRT_NEXT();
3707 for (i = 0; i <= ASC_MAX_TID; i++) {
3708 if ((chip_scsi_id == i) ||
3709 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3710 continue;
3711 }
3712 len = asc_prt_line(cp, leftlen, " %X:%c",
3713 i,
3714 (v->
3715 sdtr_done & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3716 'N');
3717 ASC_PRT_NEXT();
3718 }
3719 len = asc_prt_line(cp, leftlen, "\n");
3720 ASC_PRT_NEXT();
3721
3722 for (i = 0; i <= ASC_MAX_TID; i++) {
3723 uchar syn_period_ix;
3724
3725 if ((chip_scsi_id == i) ||
3726 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0) ||
3727 ((v->init_sdtr & ADV_TID_TO_TIDMASK(i)) == 0)) {
3728 continue;
3729 }
3730
3731 len = asc_prt_line(cp, leftlen, " %X:", i);
3732 ASC_PRT_NEXT();
3733
3734 if ((boardp->sdtr_data[i] & ASC_SYN_MAX_OFFSET) == 0) {
3735 len = asc_prt_line(cp, leftlen, " Asynchronous");
3736 ASC_PRT_NEXT();
3737 } else {
3738 syn_period_ix =
3739 (boardp->sdtr_data[i] >> 4) & (v->max_sdtr_index -
3740 1);
3741
3742 len = asc_prt_line(cp, leftlen,
3743 " Transfer Period Factor: %d (%d.%d Mhz),",
3744 v->sdtr_period_tbl[syn_period_ix],
3745 250 /
3746 v->sdtr_period_tbl[syn_period_ix],
3747 ASC_TENTHS(250,
3748 v->
3749 sdtr_period_tbl
3750 [syn_period_ix]));
3751 ASC_PRT_NEXT();
3752
3753 len = asc_prt_line(cp, leftlen, " REQ/ACK Offset: %d",
3754 boardp->
3755 sdtr_data[i] & ASC_SYN_MAX_OFFSET);
3756 ASC_PRT_NEXT();
3757 }
3758
3759 if ((v->sdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
3760 len = asc_prt_line(cp, leftlen, "*\n");
3761 renegotiate = 1;
3762 } else {
3763 len = asc_prt_line(cp, leftlen, "\n");
3764 }
3765 ASC_PRT_NEXT();
3766 }
3767
3768 if (renegotiate) {
3769 len = asc_prt_line(cp, leftlen,
3770 " * = Re-negotiation pending before next command.\n");
3771 ASC_PRT_NEXT();
3772 }
3773
3774 return totlen;
3775}
3776
3777
3778
3779
3780
3781
3782
3783
3784
3785
3786
3787
3788static int asc_prt_adv_board_info(struct Scsi_Host *shost, char *cp, int cplen)
3789{
3790 struct asc_board *boardp = shost_priv(shost);
3791 int leftlen;
3792 int totlen;
3793 int len;
3794 int i;
3795 ADV_DVC_VAR *v;
3796 ADV_DVC_CFG *c;
3797 AdvPortAddr iop_base;
3798 ushort chip_scsi_id;
3799 ushort lramword;
3800 uchar lrambyte;
3801 ushort tagqng_able;
3802 ushort sdtr_able, wdtr_able;
3803 ushort wdtr_done, sdtr_done;
3804 ushort period = 0;
3805 int renegotiate = 0;
3806
3807 v = &boardp->dvc_var.adv_dvc_var;
3808 c = &boardp->dvc_cfg.adv_dvc_cfg;
3809 iop_base = v->iop_base;
3810 chip_scsi_id = v->chip_scsi_id;
3811
3812 leftlen = cplen;
3813 totlen = len = 0;
3814
3815 len = asc_prt_line(cp, leftlen,
3816 "\nAdv Library Configuration and Statistics for AdvanSys SCSI Host %d:\n",
3817 shost->host_no);
3818 ASC_PRT_NEXT();
3819
3820 len = asc_prt_line(cp, leftlen,
3821 " iop_base 0x%lx, cable_detect: %X, err_code %u\n",
3822 v->iop_base,
3823 AdvReadWordRegister(iop_base,
3824 IOPW_SCSI_CFG1) & CABLE_DETECT,
3825 v->err_code);
3826 ASC_PRT_NEXT();
3827
3828 len = asc_prt_line(cp, leftlen, " chip_version %u, mcode_date 0x%x, "
3829 "mcode_version 0x%x\n", c->chip_version,
3830 c->mcode_date, c->mcode_version);
3831 ASC_PRT_NEXT();
3832
3833 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
3834 len = asc_prt_line(cp, leftlen, " Queuing Enabled:");
3835 ASC_PRT_NEXT();
3836 for (i = 0; i <= ADV_MAX_TID; i++) {
3837 if ((chip_scsi_id == i) ||
3838 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3839 continue;
3840 }
3841
3842 len = asc_prt_line(cp, leftlen, " %X:%c",
3843 i,
3844 (tagqng_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3845 'N');
3846 ASC_PRT_NEXT();
3847 }
3848 len = asc_prt_line(cp, leftlen, "\n");
3849 ASC_PRT_NEXT();
3850
3851 len = asc_prt_line(cp, leftlen, " Queue Limit:");
3852 ASC_PRT_NEXT();
3853 for (i = 0; i <= ADV_MAX_TID; i++) {
3854 if ((chip_scsi_id == i) ||
3855 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3856 continue;
3857 }
3858
3859 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + i,
3860 lrambyte);
3861
3862 len = asc_prt_line(cp, leftlen, " %X:%d", i, lrambyte);
3863 ASC_PRT_NEXT();
3864 }
3865 len = asc_prt_line(cp, leftlen, "\n");
3866 ASC_PRT_NEXT();
3867
3868 len = asc_prt_line(cp, leftlen, " Command Pending:");
3869 ASC_PRT_NEXT();
3870 for (i = 0; i <= ADV_MAX_TID; i++) {
3871 if ((chip_scsi_id == i) ||
3872 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3873 continue;
3874 }
3875
3876 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_QUEUED_CMD + i,
3877 lrambyte);
3878
3879 len = asc_prt_line(cp, leftlen, " %X:%d", i, lrambyte);
3880 ASC_PRT_NEXT();
3881 }
3882 len = asc_prt_line(cp, leftlen, "\n");
3883 ASC_PRT_NEXT();
3884
3885 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
3886 len = asc_prt_line(cp, leftlen, " Wide Enabled:");
3887 ASC_PRT_NEXT();
3888 for (i = 0; i <= ADV_MAX_TID; i++) {
3889 if ((chip_scsi_id == i) ||
3890 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3891 continue;
3892 }
3893
3894 len = asc_prt_line(cp, leftlen, " %X:%c",
3895 i,
3896 (wdtr_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3897 'N');
3898 ASC_PRT_NEXT();
3899 }
3900 len = asc_prt_line(cp, leftlen, "\n");
3901 ASC_PRT_NEXT();
3902
3903 AdvReadWordLram(iop_base, ASC_MC_WDTR_DONE, wdtr_done);
3904 len = asc_prt_line(cp, leftlen, " Transfer Bit Width:");
3905 ASC_PRT_NEXT();
3906 for (i = 0; i <= ADV_MAX_TID; i++) {
3907 if ((chip_scsi_id == i) ||
3908 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3909 continue;
3910 }
3911
3912 AdvReadWordLram(iop_base,
3913 ASC_MC_DEVICE_HSHK_CFG_TABLE + (2 * i),
3914 lramword);
3915
3916 len = asc_prt_line(cp, leftlen, " %X:%d",
3917 i, (lramword & 0x8000) ? 16 : 8);
3918 ASC_PRT_NEXT();
3919
3920 if ((wdtr_able & ADV_TID_TO_TIDMASK(i)) &&
3921 (wdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
3922 len = asc_prt_line(cp, leftlen, "*");
3923 ASC_PRT_NEXT();
3924 renegotiate = 1;
3925 }
3926 }
3927 len = asc_prt_line(cp, leftlen, "\n");
3928 ASC_PRT_NEXT();
3929
3930 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
3931 len = asc_prt_line(cp, leftlen, " Synchronous Enabled:");
3932 ASC_PRT_NEXT();
3933 for (i = 0; i <= ADV_MAX_TID; i++) {
3934 if ((chip_scsi_id == i) ||
3935 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0)) {
3936 continue;
3937 }
3938
3939 len = asc_prt_line(cp, leftlen, " %X:%c",
3940 i,
3941 (sdtr_able & ADV_TID_TO_TIDMASK(i)) ? 'Y' :
3942 'N');
3943 ASC_PRT_NEXT();
3944 }
3945 len = asc_prt_line(cp, leftlen, "\n");
3946 ASC_PRT_NEXT();
3947
3948 AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE, sdtr_done);
3949 for (i = 0; i <= ADV_MAX_TID; i++) {
3950
3951 AdvReadWordLram(iop_base,
3952 ASC_MC_DEVICE_HSHK_CFG_TABLE + (2 * i),
3953 lramword);
3954 lramword &= ~0x8000;
3955
3956 if ((chip_scsi_id == i) ||
3957 ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(i)) == 0) ||
3958 ((sdtr_able & ADV_TID_TO_TIDMASK(i)) == 0)) {
3959 continue;
3960 }
3961
3962 len = asc_prt_line(cp, leftlen, " %X:", i);
3963 ASC_PRT_NEXT();
3964
3965 if ((lramword & 0x1F) == 0) {
3966 len = asc_prt_line(cp, leftlen, " Asynchronous");
3967 ASC_PRT_NEXT();
3968 } else {
3969 len =
3970 asc_prt_line(cp, leftlen,
3971 " Transfer Period Factor: ");
3972 ASC_PRT_NEXT();
3973
3974 if ((lramword & 0x1F00) == 0x1100) {
3975 len =
3976 asc_prt_line(cp, leftlen, "9 (80.0 Mhz),");
3977 ASC_PRT_NEXT();
3978 } else if ((lramword & 0x1F00) == 0x1000) {
3979 len =
3980 asc_prt_line(cp, leftlen, "10 (40.0 Mhz),");
3981 ASC_PRT_NEXT();
3982 } else {
3983
3984 period = (((lramword >> 8) * 25) + 50) / 4;
3985
3986 if (period == 0) {
3987 len =
3988 asc_prt_line(cp, leftlen,
3989 "%d (? Mhz), ");
3990 ASC_PRT_NEXT();
3991 } else {
3992 len = asc_prt_line(cp, leftlen,
3993 "%d (%d.%d Mhz),",
3994 period, 250 / period,
3995 ASC_TENTHS(250,
3996 period));
3997 ASC_PRT_NEXT();
3998 }
3999 }
4000
4001 len = asc_prt_line(cp, leftlen, " REQ/ACK Offset: %d",
4002 lramword & 0x1F);
4003 ASC_PRT_NEXT();
4004 }
4005
4006 if ((sdtr_done & ADV_TID_TO_TIDMASK(i)) == 0) {
4007 len = asc_prt_line(cp, leftlen, "*\n");
4008 renegotiate = 1;
4009 } else {
4010 len = asc_prt_line(cp, leftlen, "\n");
4011 }
4012 ASC_PRT_NEXT();
4013 }
4014
4015 if (renegotiate) {
4016 len = asc_prt_line(cp, leftlen,
4017 " * = Re-negotiation pending before next command.\n");
4018 ASC_PRT_NEXT();
4019 }
4020
4021 return totlen;
4022}
4023
4024
4025
4026
4027
4028
4029
4030static int
4031asc_proc_copy(off_t advoffset, off_t offset, char *curbuf, int leftlen,
4032 char *cp, int cplen)
4033{
4034 int cnt = 0;
4035
4036 ASC_DBG(2, "offset %d, advoffset %d, cplen %d\n",
4037 (unsigned)offset, (unsigned)advoffset, cplen);
4038 if (offset <= advoffset) {
4039
4040 cnt = min(cplen, leftlen);
4041 ASC_DBG(2, "curbuf 0x%lx, cp 0x%lx, cnt %d\n",
4042 (ulong)curbuf, (ulong)cp, cnt);
4043 memcpy(curbuf, cp, cnt);
4044 } else if (offset < advoffset + cplen) {
4045
4046 cnt = (advoffset + cplen) - offset;
4047 cp = (cp + cplen) - cnt;
4048 cnt = min(cnt, leftlen);
4049 ASC_DBG(2, "curbuf 0x%lx, cp 0x%lx, cnt %d\n",
4050 (ulong)curbuf, (ulong)cp, cnt);
4051 memcpy(curbuf, cp, cnt);
4052 }
4053 return cnt;
4054}
4055
4056#ifdef ADVANSYS_STATS
4057
4058
4059
4060
4061
4062
4063
4064
4065
4066static int asc_prt_board_stats(struct Scsi_Host *shost, char *cp, int cplen)
4067{
4068 struct asc_board *boardp = shost_priv(shost);
4069 struct asc_stats *s = &boardp->asc_stats;
4070
4071 int leftlen = cplen;
4072 int len, totlen = 0;
4073
4074 len = asc_prt_line(cp, leftlen,
4075 "\nLinux Driver Statistics for AdvanSys SCSI Host %d:\n",
4076 shost->host_no);
4077 ASC_PRT_NEXT();
4078
4079 len = asc_prt_line(cp, leftlen,
4080 " queuecommand %lu, reset %lu, biosparam %lu, interrupt %lu\n",
4081 s->queuecommand, s->reset, s->biosparam,
4082 s->interrupt);
4083 ASC_PRT_NEXT();
4084
4085 len = asc_prt_line(cp, leftlen,
4086 " callback %lu, done %lu, build_error %lu, build_noreq %lu, build_nosg %lu\n",
4087 s->callback, s->done, s->build_error,
4088 s->adv_build_noreq, s->adv_build_nosg);
4089 ASC_PRT_NEXT();
4090
4091 len = asc_prt_line(cp, leftlen,
4092 " exe_noerror %lu, exe_busy %lu, exe_error %lu, exe_unknown %lu\n",
4093 s->exe_noerror, s->exe_busy, s->exe_error,
4094 s->exe_unknown);
4095 ASC_PRT_NEXT();
4096
4097
4098
4099
4100 if (s->xfer_cnt > 0) {
4101 len = asc_prt_line(cp, leftlen, " xfer_cnt %lu, xfer_elem %lu, ",
4102 s->xfer_cnt, s->xfer_elem);
4103 ASC_PRT_NEXT();
4104
4105 len = asc_prt_line(cp, leftlen, "xfer_bytes %lu.%01lu kb\n",
4106 s->xfer_sect / 2, ASC_TENTHS(s->xfer_sect, 2));
4107 ASC_PRT_NEXT();
4108
4109
4110 len = asc_prt_line(cp, leftlen, " avg_num_elem %lu.%01lu, ",
4111 s->xfer_elem / s->xfer_cnt,
4112 ASC_TENTHS(s->xfer_elem, s->xfer_cnt));
4113 ASC_PRT_NEXT();
4114
4115 len = asc_prt_line(cp, leftlen, "avg_elem_size %lu.%01lu kb, ",
4116 (s->xfer_sect / 2) / s->xfer_elem,
4117 ASC_TENTHS((s->xfer_sect / 2), s->xfer_elem));
4118 ASC_PRT_NEXT();
4119
4120 len = asc_prt_line(cp, leftlen, "avg_xfer_size %lu.%01lu kb\n",
4121 (s->xfer_sect / 2) / s->xfer_cnt,
4122 ASC_TENTHS((s->xfer_sect / 2), s->xfer_cnt));
4123 ASC_PRT_NEXT();
4124 }
4125
4126 return totlen;
4127}
4128#endif
4129
4130
4131
4132
4133
4134
4135
4136
4137
4138
4139
4140
4141
4142
4143
4144
4145
4146
4147
4148
4149
4150static int
4151advansys_proc_info(struct Scsi_Host *shost, char *buffer, char **start,
4152 off_t offset, int length, int inout)
4153{
4154 struct asc_board *boardp = shost_priv(shost);
4155 char *cp;
4156 int cplen;
4157 int cnt;
4158 int totcnt;
4159 int leftlen;
4160 char *curbuf;
4161 off_t advoffset;
4162
4163 ASC_DBG(1, "begin\n");
4164
4165
4166
4167
4168 if (inout == TRUE)
4169 return -ENOSYS;
4170
4171
4172
4173
4174
4175
4176 *start = buffer;
4177 curbuf = buffer;
4178 advoffset = 0;
4179 totcnt = 0;
4180 leftlen = length;
4181
4182
4183
4184
4185
4186
4187 cp = (char *)advansys_info(shost);
4188 strcat(cp, "\n");
4189 cplen = strlen(cp);
4190
4191 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4192 totcnt += cnt;
4193 leftlen -= cnt;
4194 if (leftlen == 0) {
4195 ASC_DBG(1, "totcnt %d\n", totcnt);
4196 return totcnt;
4197 }
4198 advoffset += cplen;
4199 curbuf += cnt;
4200
4201
4202
4203
4204 if (!ASC_NARROW_BOARD(boardp)) {
4205 cp = boardp->prtbuf;
4206 cplen = asc_prt_adv_bios(shost, cp, ASC_PRTBUF_SIZE);
4207 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4208 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp,
4209 cplen);
4210 totcnt += cnt;
4211 leftlen -= cnt;
4212 if (leftlen == 0) {
4213 ASC_DBG(1, "totcnt %d\n", totcnt);
4214 return totcnt;
4215 }
4216 advoffset += cplen;
4217 curbuf += cnt;
4218 }
4219
4220
4221
4222
4223 cp = boardp->prtbuf;
4224 cplen = asc_prt_board_devices(shost, cp, ASC_PRTBUF_SIZE);
4225 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4226 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4227 totcnt += cnt;
4228 leftlen -= cnt;
4229 if (leftlen == 0) {
4230 ASC_DBG(1, "totcnt %d\n", totcnt);
4231 return totcnt;
4232 }
4233 advoffset += cplen;
4234 curbuf += cnt;
4235
4236
4237
4238
4239 cp = boardp->prtbuf;
4240 if (ASC_NARROW_BOARD(boardp)) {
4241 cplen = asc_prt_asc_board_eeprom(shost, cp, ASC_PRTBUF_SIZE);
4242 } else {
4243 cplen = asc_prt_adv_board_eeprom(shost, cp, ASC_PRTBUF_SIZE);
4244 }
4245 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4246 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4247 totcnt += cnt;
4248 leftlen -= cnt;
4249 if (leftlen == 0) {
4250 ASC_DBG(1, "totcnt %d\n", totcnt);
4251 return totcnt;
4252 }
4253 advoffset += cplen;
4254 curbuf += cnt;
4255
4256
4257
4258
4259 cp = boardp->prtbuf;
4260 cplen = asc_prt_driver_conf(shost, cp, ASC_PRTBUF_SIZE);
4261 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4262 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4263 totcnt += cnt;
4264 leftlen -= cnt;
4265 if (leftlen == 0) {
4266 ASC_DBG(1, "totcnt %d\n", totcnt);
4267 return totcnt;
4268 }
4269 advoffset += cplen;
4270 curbuf += cnt;
4271
4272#ifdef ADVANSYS_STATS
4273
4274
4275
4276 cp = boardp->prtbuf;
4277 cplen = asc_prt_board_stats(shost, cp, ASC_PRTBUF_SIZE);
4278 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4279 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4280 totcnt += cnt;
4281 leftlen -= cnt;
4282 if (leftlen == 0) {
4283 ASC_DBG(1, "totcnt %d\n", totcnt);
4284 return totcnt;
4285 }
4286 advoffset += cplen;
4287 curbuf += cnt;
4288#endif
4289
4290
4291
4292
4293
4294 cp = boardp->prtbuf;
4295 if (ASC_NARROW_BOARD(boardp)) {
4296 cplen = asc_prt_asc_board_info(shost, cp, ASC_PRTBUF_SIZE);
4297 } else {
4298 cplen = asc_prt_adv_board_info(shost, cp, ASC_PRTBUF_SIZE);
4299 }
4300 BUG_ON(cplen >= ASC_PRTBUF_SIZE);
4301 cnt = asc_proc_copy(advoffset, offset, curbuf, leftlen, cp, cplen);
4302 totcnt += cnt;
4303 leftlen -= cnt;
4304 if (leftlen == 0) {
4305 ASC_DBG(1, "totcnt %d\n", totcnt);
4306 return totcnt;
4307 }
4308 advoffset += cplen;
4309 curbuf += cnt;
4310
4311 ASC_DBG(1, "totcnt %d\n", totcnt);
4312
4313 return totcnt;
4314}
4315#endif
4316
4317static void asc_scsi_done(struct scsi_cmnd *scp)
4318{
4319 scsi_dma_unmap(scp);
4320 ASC_STATS(scp->device->host, done);
4321 scp->scsi_done(scp);
4322}
4323
4324static void AscSetBank(PortAddr iop_base, uchar bank)
4325{
4326 uchar val;
4327
4328 val = AscGetChipControl(iop_base) &
4329 (~
4330 (CC_SINGLE_STEP | CC_TEST | CC_DIAG | CC_SCSI_RESET |
4331 CC_CHIP_RESET));
4332 if (bank == 1) {
4333 val |= CC_BANK_ONE;
4334 } else if (bank == 2) {
4335 val |= CC_DIAG | CC_BANK_ONE;
4336 } else {
4337 val &= ~CC_BANK_ONE;
4338 }
4339 AscSetChipControl(iop_base, val);
4340}
4341
4342static void AscSetChipIH(PortAddr iop_base, ushort ins_code)
4343{
4344 AscSetBank(iop_base, 1);
4345 AscWriteChipIH(iop_base, ins_code);
4346 AscSetBank(iop_base, 0);
4347}
4348
4349static int AscStartChip(PortAddr iop_base)
4350{
4351 AscSetChipControl(iop_base, 0);
4352 if ((AscGetChipStatus(iop_base) & CSW_HALTED) != 0) {
4353 return (0);
4354 }
4355 return (1);
4356}
4357
4358static int AscStopChip(PortAddr iop_base)
4359{
4360 uchar cc_val;
4361
4362 cc_val =
4363 AscGetChipControl(iop_base) &
4364 (~(CC_SINGLE_STEP | CC_TEST | CC_DIAG));
4365 AscSetChipControl(iop_base, (uchar)(cc_val | CC_HALT));
4366 AscSetChipIH(iop_base, INS_HALT);
4367 AscSetChipIH(iop_base, INS_RFLAG_WTM);
4368 if ((AscGetChipStatus(iop_base) & CSW_HALTED) == 0) {
4369 return (0);
4370 }
4371 return (1);
4372}
4373
4374static int AscIsChipHalted(PortAddr iop_base)
4375{
4376 if ((AscGetChipStatus(iop_base) & CSW_HALTED) != 0) {
4377 if ((AscGetChipControl(iop_base) & CC_HALT) != 0) {
4378 return (1);
4379 }
4380 }
4381 return (0);
4382}
4383
4384static int AscResetChipAndScsiBus(ASC_DVC_VAR *asc_dvc)
4385{
4386 PortAddr iop_base;
4387 int i = 10;
4388
4389 iop_base = asc_dvc->iop_base;
4390 while ((AscGetChipStatus(iop_base) & CSW_SCSI_RESET_ACTIVE)
4391 && (i-- > 0)) {
4392 mdelay(100);
4393 }
4394 AscStopChip(iop_base);
4395 AscSetChipControl(iop_base, CC_CHIP_RESET | CC_SCSI_RESET | CC_HALT);
4396 udelay(60);
4397 AscSetChipIH(iop_base, INS_RFLAG_WTM);
4398 AscSetChipIH(iop_base, INS_HALT);
4399 AscSetChipControl(iop_base, CC_CHIP_RESET | CC_HALT);
4400 AscSetChipControl(iop_base, CC_HALT);
4401 mdelay(200);
4402 AscSetChipStatus(iop_base, CIW_CLR_SCSI_RESET_INT);
4403 AscSetChipStatus(iop_base, 0);
4404 return (AscIsChipHalted(iop_base));
4405}
4406
4407static int AscFindSignature(PortAddr iop_base)
4408{
4409 ushort sig_word;
4410
4411 ASC_DBG(1, "AscGetChipSignatureByte(0x%x) 0x%x\n",
4412 iop_base, AscGetChipSignatureByte(iop_base));
4413 if (AscGetChipSignatureByte(iop_base) == (uchar)ASC_1000_ID1B) {
4414 ASC_DBG(1, "AscGetChipSignatureWord(0x%x) 0x%x\n",
4415 iop_base, AscGetChipSignatureWord(iop_base));
4416 sig_word = AscGetChipSignatureWord(iop_base);
4417 if ((sig_word == (ushort)ASC_1000_ID0W) ||
4418 (sig_word == (ushort)ASC_1000_ID0W_FIX)) {
4419 return (1);
4420 }
4421 }
4422 return (0);
4423}
4424
4425static void AscEnableInterrupt(PortAddr iop_base)
4426{
4427 ushort cfg;
4428
4429 cfg = AscGetChipCfgLsw(iop_base);
4430 AscSetChipCfgLsw(iop_base, cfg | ASC_CFG0_HOST_INT_ON);
4431}
4432
4433static void AscDisableInterrupt(PortAddr iop_base)
4434{
4435 ushort cfg;
4436
4437 cfg = AscGetChipCfgLsw(iop_base);
4438 AscSetChipCfgLsw(iop_base, cfg & (~ASC_CFG0_HOST_INT_ON));
4439}
4440
4441static uchar AscReadLramByte(PortAddr iop_base, ushort addr)
4442{
4443 unsigned char byte_data;
4444 unsigned short word_data;
4445
4446 if (isodd_word(addr)) {
4447 AscSetChipLramAddr(iop_base, addr - 1);
4448 word_data = AscGetChipLramData(iop_base);
4449 byte_data = (word_data >> 8) & 0xFF;
4450 } else {
4451 AscSetChipLramAddr(iop_base, addr);
4452 word_data = AscGetChipLramData(iop_base);
4453 byte_data = word_data & 0xFF;
4454 }
4455 return byte_data;
4456}
4457
4458static ushort AscReadLramWord(PortAddr iop_base, ushort addr)
4459{
4460 ushort word_data;
4461
4462 AscSetChipLramAddr(iop_base, addr);
4463 word_data = AscGetChipLramData(iop_base);
4464 return (word_data);
4465}
4466
4467#if CC_VERY_LONG_SG_LIST
4468static ASC_DCNT AscReadLramDWord(PortAddr iop_base, ushort addr)
4469{
4470 ushort val_low, val_high;
4471 ASC_DCNT dword_data;
4472
4473 AscSetChipLramAddr(iop_base, addr);
4474 val_low = AscGetChipLramData(iop_base);
4475 val_high = AscGetChipLramData(iop_base);
4476 dword_data = ((ASC_DCNT) val_high << 16) | (ASC_DCNT) val_low;
4477 return (dword_data);
4478}
4479#endif
4480
4481static void
4482AscMemWordSetLram(PortAddr iop_base, ushort s_addr, ushort set_wval, int words)
4483{
4484 int i;
4485
4486 AscSetChipLramAddr(iop_base, s_addr);
4487 for (i = 0; i < words; i++) {
4488 AscSetChipLramData(iop_base, set_wval);
4489 }
4490}
4491
4492static void AscWriteLramWord(PortAddr iop_base, ushort addr, ushort word_val)
4493{
4494 AscSetChipLramAddr(iop_base, addr);
4495 AscSetChipLramData(iop_base, word_val);
4496}
4497
4498static void AscWriteLramByte(PortAddr iop_base, ushort addr, uchar byte_val)
4499{
4500 ushort word_data;
4501
4502 if (isodd_word(addr)) {
4503 addr--;
4504 word_data = AscReadLramWord(iop_base, addr);
4505 word_data &= 0x00FF;
4506 word_data |= (((ushort)byte_val << 8) & 0xFF00);
4507 } else {
4508 word_data = AscReadLramWord(iop_base, addr);
4509 word_data &= 0xFF00;
4510 word_data |= ((ushort)byte_val & 0x00FF);
4511 }
4512 AscWriteLramWord(iop_base, addr, word_data);
4513}
4514
4515
4516
4517
4518
4519
4520
4521static void
4522AscMemWordCopyPtrToLram(PortAddr iop_base, ushort s_addr,
4523 const uchar *s_buffer, int words)
4524{
4525 int i;
4526
4527 AscSetChipLramAddr(iop_base, s_addr);
4528 for (i = 0; i < 2 * words; i += 2) {
4529
4530
4531
4532
4533
4534
4535
4536
4537 outpw(iop_base + IOP_RAM_DATA,
4538 ((ushort)s_buffer[i + 1] << 8) | s_buffer[i]);
4539 }
4540}
4541
4542
4543
4544
4545
4546
4547
4548static void
4549AscMemDWordCopyPtrToLram(PortAddr iop_base,
4550 ushort s_addr, uchar *s_buffer, int dwords)
4551{
4552 int i;
4553
4554 AscSetChipLramAddr(iop_base, s_addr);
4555 for (i = 0; i < 4 * dwords; i += 4) {
4556 outpw(iop_base + IOP_RAM_DATA, ((ushort)s_buffer[i + 1] << 8) | s_buffer[i]);
4557 outpw(iop_base + IOP_RAM_DATA, ((ushort)s_buffer[i + 3] << 8) | s_buffer[i + 2]);
4558 }
4559}
4560
4561
4562
4563
4564
4565
4566
4567static void
4568AscMemWordCopyPtrFromLram(PortAddr iop_base,
4569 ushort s_addr, uchar *d_buffer, int words)
4570{
4571 int i;
4572 ushort word;
4573
4574 AscSetChipLramAddr(iop_base, s_addr);
4575 for (i = 0; i < 2 * words; i += 2) {
4576 word = inpw(iop_base + IOP_RAM_DATA);
4577 d_buffer[i] = word & 0xff;
4578 d_buffer[i + 1] = (word >> 8) & 0xff;
4579 }
4580}
4581
4582static ASC_DCNT AscMemSumLramWord(PortAddr iop_base, ushort s_addr, int words)
4583{
4584 ASC_DCNT sum;
4585 int i;
4586
4587 sum = 0L;
4588 for (i = 0; i < words; i++, s_addr += 2) {
4589 sum += AscReadLramWord(iop_base, s_addr);
4590 }
4591 return (sum);
4592}
4593
4594static ushort AscInitLram(ASC_DVC_VAR *asc_dvc)
4595{
4596 uchar i;
4597 ushort s_addr;
4598 PortAddr iop_base;
4599 ushort warn_code;
4600
4601 iop_base = asc_dvc->iop_base;
4602 warn_code = 0;
4603 AscMemWordSetLram(iop_base, ASC_QADR_BEG, 0,
4604 (ushort)(((int)(asc_dvc->max_total_qng + 2 + 1) *
4605 64) >> 1));
4606 i = ASC_MIN_ACTIVE_QNO;
4607 s_addr = ASC_QADR_BEG + ASC_QBLK_SIZE;
4608 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
4609 (uchar)(i + 1));
4610 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
4611 (uchar)(asc_dvc->max_total_qng));
4612 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
4613 (uchar)i);
4614 i++;
4615 s_addr += ASC_QBLK_SIZE;
4616 for (; i < asc_dvc->max_total_qng; i++, s_addr += ASC_QBLK_SIZE) {
4617 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
4618 (uchar)(i + 1));
4619 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
4620 (uchar)(i - 1));
4621 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
4622 (uchar)i);
4623 }
4624 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_FWD),
4625 (uchar)ASC_QLINK_END);
4626 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_BWD),
4627 (uchar)(asc_dvc->max_total_qng - 1));
4628 AscWriteLramByte(iop_base, (ushort)(s_addr + ASC_SCSIQ_B_QNO),
4629 (uchar)asc_dvc->max_total_qng);
4630 i++;
4631 s_addr += ASC_QBLK_SIZE;
4632 for (; i <= (uchar)(asc_dvc->max_total_qng + 3);
4633 i++, s_addr += ASC_QBLK_SIZE) {
4634 AscWriteLramByte(iop_base,
4635 (ushort)(s_addr + (ushort)ASC_SCSIQ_B_FWD), i);
4636 AscWriteLramByte(iop_base,
4637 (ushort)(s_addr + (ushort)ASC_SCSIQ_B_BWD), i);
4638 AscWriteLramByte(iop_base,
4639 (ushort)(s_addr + (ushort)ASC_SCSIQ_B_QNO), i);
4640 }
4641 return warn_code;
4642}
4643
4644static ASC_DCNT
4645AscLoadMicroCode(PortAddr iop_base, ushort s_addr,
4646 const uchar *mcode_buf, ushort mcode_size)
4647{
4648 ASC_DCNT chksum;
4649 ushort mcode_word_size;
4650 ushort mcode_chksum;
4651
4652
4653 mcode_word_size = (ushort)(mcode_size >> 1);
4654 AscMemWordSetLram(iop_base, s_addr, 0, mcode_word_size);
4655 AscMemWordCopyPtrToLram(iop_base, s_addr, mcode_buf, mcode_word_size);
4656
4657 chksum = AscMemSumLramWord(iop_base, s_addr, mcode_word_size);
4658 ASC_DBG(1, "chksum 0x%lx\n", (ulong)chksum);
4659 mcode_chksum = (ushort)AscMemSumLramWord(iop_base,
4660 (ushort)ASC_CODE_SEC_BEG,
4661 (ushort)((mcode_size -
4662 s_addr - (ushort)
4663 ASC_CODE_SEC_BEG) /
4664 2));
4665 ASC_DBG(1, "mcode_chksum 0x%lx\n", (ulong)mcode_chksum);
4666 AscWriteLramWord(iop_base, ASCV_MCODE_CHKSUM_W, mcode_chksum);
4667 AscWriteLramWord(iop_base, ASCV_MCODE_SIZE_W, mcode_size);
4668 return chksum;
4669}
4670
4671static void AscInitQLinkVar(ASC_DVC_VAR *asc_dvc)
4672{
4673 PortAddr iop_base;
4674 int i;
4675 ushort lram_addr;
4676
4677 iop_base = asc_dvc->iop_base;
4678 AscPutRiscVarFreeQHead(iop_base, 1);
4679 AscPutRiscVarDoneQTail(iop_base, asc_dvc->max_total_qng);
4680 AscPutVarFreeQHead(iop_base, 1);
4681 AscPutVarDoneQTail(iop_base, asc_dvc->max_total_qng);
4682 AscWriteLramByte(iop_base, ASCV_BUSY_QHEAD_B,
4683 (uchar)((int)asc_dvc->max_total_qng + 1));
4684 AscWriteLramByte(iop_base, ASCV_DISC1_QHEAD_B,
4685 (uchar)((int)asc_dvc->max_total_qng + 2));
4686 AscWriteLramByte(iop_base, (ushort)ASCV_TOTAL_READY_Q_B,
4687 asc_dvc->max_total_qng);
4688 AscWriteLramWord(iop_base, ASCV_ASCDVC_ERR_CODE_W, 0);
4689 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
4690 AscWriteLramByte(iop_base, ASCV_STOP_CODE_B, 0);
4691 AscWriteLramByte(iop_base, ASCV_SCSIBUSY_B, 0);
4692 AscWriteLramByte(iop_base, ASCV_WTM_FLAG_B, 0);
4693 AscPutQDoneInProgress(iop_base, 0);
4694 lram_addr = ASC_QADR_BEG;
4695 for (i = 0; i < 32; i++, lram_addr += 2) {
4696 AscWriteLramWord(iop_base, lram_addr, 0);
4697 }
4698}
4699
4700static ushort AscInitMicroCodeVar(ASC_DVC_VAR *asc_dvc)
4701{
4702 int i;
4703 ushort warn_code;
4704 PortAddr iop_base;
4705 ASC_PADDR phy_addr;
4706 ASC_DCNT phy_size;
4707 struct asc_board *board = asc_dvc_to_board(asc_dvc);
4708
4709 iop_base = asc_dvc->iop_base;
4710 warn_code = 0;
4711 for (i = 0; i <= ASC_MAX_TID; i++) {
4712 AscPutMCodeInitSDTRAtID(iop_base, i,
4713 asc_dvc->cfg->sdtr_period_offset[i]);
4714 }
4715
4716 AscInitQLinkVar(asc_dvc);
4717 AscWriteLramByte(iop_base, ASCV_DISC_ENABLE_B,
4718 asc_dvc->cfg->disc_enable);
4719 AscWriteLramByte(iop_base, ASCV_HOSTSCSI_ID_B,
4720 ASC_TID_TO_TARGET_ID(asc_dvc->cfg->chip_scsi_id));
4721
4722
4723 BUG_ON((unsigned long)asc_dvc->overrun_buf & 7);
4724 asc_dvc->overrun_dma = dma_map_single(board->dev, asc_dvc->overrun_buf,
4725 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
4726 if (dma_mapping_error(board->dev, asc_dvc->overrun_dma)) {
4727 warn_code = -ENOMEM;
4728 goto err_dma_map;
4729 }
4730 phy_addr = cpu_to_le32(asc_dvc->overrun_dma);
4731 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_PADDR_D,
4732 (uchar *)&phy_addr, 1);
4733 phy_size = cpu_to_le32(ASC_OVERRUN_BSIZE);
4734 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_BSIZE_D,
4735 (uchar *)&phy_size, 1);
4736
4737 asc_dvc->cfg->mcode_date =
4738 AscReadLramWord(iop_base, (ushort)ASCV_MC_DATE_W);
4739 asc_dvc->cfg->mcode_version =
4740 AscReadLramWord(iop_base, (ushort)ASCV_MC_VER_W);
4741
4742 AscSetPCAddr(iop_base, ASC_MCODE_START_ADDR);
4743 if (AscGetPCAddr(iop_base) != ASC_MCODE_START_ADDR) {
4744 asc_dvc->err_code |= ASC_IERR_SET_PC_ADDR;
4745 warn_code = UW_ERR;
4746 goto err_mcode_start;
4747 }
4748 if (AscStartChip(iop_base) != 1) {
4749 asc_dvc->err_code |= ASC_IERR_START_STOP_CHIP;
4750 warn_code = UW_ERR;
4751 goto err_mcode_start;
4752 }
4753
4754 return warn_code;
4755
4756err_mcode_start:
4757 dma_unmap_single(board->dev, asc_dvc->overrun_dma,
4758 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
4759err_dma_map:
4760 asc_dvc->overrun_dma = 0;
4761 return warn_code;
4762}
4763
4764static ushort AscInitAsc1000Driver(ASC_DVC_VAR *asc_dvc)
4765{
4766 const struct firmware *fw;
4767 const char fwname[] = "advansys/mcode.bin";
4768 int err;
4769 unsigned long chksum;
4770 ushort warn_code;
4771 PortAddr iop_base;
4772
4773 iop_base = asc_dvc->iop_base;
4774 warn_code = 0;
4775 if ((asc_dvc->dvc_cntl & ASC_CNTL_RESET_SCSI) &&
4776 !(asc_dvc->init_state & ASC_INIT_RESET_SCSI_DONE)) {
4777 AscResetChipAndScsiBus(asc_dvc);
4778 mdelay(asc_dvc->scsi_reset_wait * 1000);
4779 }
4780 asc_dvc->init_state |= ASC_INIT_STATE_BEG_LOAD_MC;
4781 if (asc_dvc->err_code != 0)
4782 return UW_ERR;
4783 if (!AscFindSignature(asc_dvc->iop_base)) {
4784 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
4785 return warn_code;
4786 }
4787 AscDisableInterrupt(iop_base);
4788 warn_code |= AscInitLram(asc_dvc);
4789 if (asc_dvc->err_code != 0)
4790 return UW_ERR;
4791
4792 err = request_firmware(&fw, fwname, asc_dvc->drv_ptr->dev);
4793 if (err) {
4794 printk(KERN_ERR "Failed to load image \"%s\" err %d\n",
4795 fwname, err);
4796 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
4797 return err;
4798 }
4799 if (fw->size < 4) {
4800 printk(KERN_ERR "Bogus length %zu in image \"%s\"\n",
4801 fw->size, fwname);
4802 release_firmware(fw);
4803 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
4804 return -EINVAL;
4805 }
4806 chksum = (fw->data[3] << 24) | (fw->data[2] << 16) |
4807 (fw->data[1] << 8) | fw->data[0];
4808 ASC_DBG(1, "_asc_mcode_chksum 0x%lx\n", (ulong)chksum);
4809 if (AscLoadMicroCode(iop_base, 0, &fw->data[4],
4810 fw->size - 4) != chksum) {
4811 asc_dvc->err_code |= ASC_IERR_MCODE_CHKSUM;
4812 release_firmware(fw);
4813 return warn_code;
4814 }
4815 release_firmware(fw);
4816 warn_code |= AscInitMicroCodeVar(asc_dvc);
4817 if (!asc_dvc->overrun_dma)
4818 return warn_code;
4819 asc_dvc->init_state |= ASC_INIT_STATE_END_LOAD_MC;
4820 AscEnableInterrupt(iop_base);
4821 return warn_code;
4822}
4823
4824
4825
4826
4827
4828
4829
4830
4831
4832
4833
4834
4835
4836
4837
4838
4839
4840
4841
4842
4843
4844
4845
4846static int AdvLoadMicrocode(AdvPortAddr iop_base, const unsigned char *buf,
4847 int size, int memsize, int chksum)
4848{
4849 int i, j, end, len = 0;
4850 ADV_DCNT sum;
4851
4852 AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
4853
4854 for (i = 253 * 2; i < size; i++) {
4855 if (buf[i] == 0xff) {
4856 unsigned short word = (buf[i + 3] << 8) | buf[i + 2];
4857 for (j = 0; j < buf[i + 1]; j++) {
4858 AdvWriteWordAutoIncLram(iop_base, word);
4859 len += 2;
4860 }
4861 i += 3;
4862 } else if (buf[i] == 0xfe) {
4863 unsigned short word = (buf[i + 2] << 8) | buf[i + 1];
4864 AdvWriteWordAutoIncLram(iop_base, word);
4865 i += 2;
4866 len += 2;
4867 } else {
4868 unsigned int off = buf[i] * 2;
4869 unsigned short word = (buf[off + 1] << 8) | buf[off];
4870 AdvWriteWordAutoIncLram(iop_base, word);
4871 len += 2;
4872 }
4873 }
4874
4875 end = len;
4876
4877 while (len < memsize) {
4878 AdvWriteWordAutoIncLram(iop_base, 0);
4879 len += 2;
4880 }
4881
4882
4883 sum = 0;
4884 AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, 0);
4885
4886 for (len = 0; len < end; len += 2) {
4887 sum += AdvReadWordAutoIncLram(iop_base);
4888 }
4889
4890 if (sum != chksum)
4891 return ASC_IERR_MCODE_CHKSUM;
4892
4893 return 0;
4894}
4895
4896static void AdvBuildCarrierFreelist(struct adv_dvc_var *asc_dvc)
4897{
4898 ADV_CARR_T *carrp;
4899 ADV_SDCNT buf_size;
4900 ADV_PADDR carr_paddr;
4901
4902 carrp = (ADV_CARR_T *) ADV_16BALIGN(asc_dvc->carrier_buf);
4903 asc_dvc->carr_freelist = NULL;
4904 if (carrp == asc_dvc->carrier_buf) {
4905 buf_size = ADV_CARRIER_BUFSIZE;
4906 } else {
4907 buf_size = ADV_CARRIER_BUFSIZE - sizeof(ADV_CARR_T);
4908 }
4909
4910 do {
4911
4912 carr_paddr = cpu_to_le32(virt_to_bus(carrp));
4913
4914 buf_size -= sizeof(ADV_CARR_T);
4915
4916 carrp->carr_pa = carr_paddr;
4917 carrp->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(carrp));
4918
4919
4920
4921
4922 carrp->next_vpa =
4923 cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
4924 asc_dvc->carr_freelist = carrp;
4925
4926 carrp++;
4927 } while (buf_size > 0);
4928}
4929
4930
4931
4932
4933
4934
4935
4936
4937
4938
4939
4940
4941
4942
4943
4944static int
4945AdvSendIdleCmd(ADV_DVC_VAR *asc_dvc,
4946 ushort idle_cmd, ADV_DCNT idle_cmd_parameter)
4947{
4948 int result;
4949 ADV_DCNT i, j;
4950 AdvPortAddr iop_base;
4951
4952 iop_base = asc_dvc->iop_base;
4953
4954
4955
4956
4957
4958
4959 AdvWriteWordLram(iop_base, ASC_MC_IDLE_CMD_STATUS, (ushort)0);
4960
4961
4962
4963
4964
4965
4966
4967 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IDLE_CMD_PARAMETER,
4968 cpu_to_le32(idle_cmd_parameter));
4969 AdvWriteWordLram(iop_base, ASC_MC_IDLE_CMD, idle_cmd);
4970
4971
4972
4973
4974 AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_B);
4975 if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
4976
4977
4978
4979
4980
4981 AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_NOP);
4982 }
4983
4984
4985 for (i = 0; i < SCSI_WAIT_100_MSEC; i++) {
4986
4987 for (j = 0; j < SCSI_US_PER_MSEC; j++) {
4988 AdvReadWordLram(iop_base, ASC_MC_IDLE_CMD_STATUS,
4989 result);
4990 if (result != 0)
4991 return result;
4992 udelay(1);
4993 }
4994 }
4995
4996 BUG();
4997 return ADV_ERROR;
4998}
4999
5000
5001
5002
5003
5004
5005
5006
5007
5008
5009static int AdvResetSB(ADV_DVC_VAR *asc_dvc)
5010{
5011 int status;
5012
5013
5014
5015
5016
5017 status = AdvSendIdleCmd(asc_dvc, (ushort)IDLE_CMD_SCSI_RESET_START, 0L);
5018 if (status != ADV_TRUE) {
5019 return status;
5020 }
5021
5022
5023
5024
5025
5026
5027
5028 udelay(ASC_SCSI_RESET_HOLD_TIME_US);
5029
5030
5031
5032
5033
5034 status = AdvSendIdleCmd(asc_dvc, (ushort)IDLE_CMD_SCSI_RESET_END, 0L);
5035 if (status != ADV_TRUE) {
5036 return status;
5037 }
5038
5039 mdelay(asc_dvc->scsi_reset_wait * 1000);
5040
5041 return status;
5042}
5043
5044
5045
5046
5047
5048
5049
5050
5051
5052
5053
5054static int AdvInitAsc3550Driver(ADV_DVC_VAR *asc_dvc)
5055{
5056 const struct firmware *fw;
5057 const char fwname[] = "advansys/3550.bin";
5058 AdvPortAddr iop_base;
5059 ushort warn_code;
5060 int begin_addr;
5061 int end_addr;
5062 ushort code_sum;
5063 int word;
5064 int i;
5065 int err;
5066 unsigned long chksum;
5067 ushort scsi_cfg1;
5068 uchar tid;
5069 ushort bios_mem[ASC_MC_BIOSLEN / 2];
5070 ushort wdtr_able = 0, sdtr_able, tagqng_able;
5071 uchar max_cmd[ADV_MAX_TID + 1];
5072
5073
5074 if (asc_dvc->err_code != 0)
5075 return ADV_ERROR;
5076
5077
5078
5079
5080 if (asc_dvc->chip_type != ADV_CHIP_ASC3550) {
5081 asc_dvc->err_code = ASC_IERR_BAD_CHIPTYPE;
5082 return ADV_ERROR;
5083 }
5084
5085 warn_code = 0;
5086 iop_base = asc_dvc->iop_base;
5087
5088
5089
5090
5091
5092
5093
5094
5095
5096 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
5097 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
5098 bios_mem[i]);
5099 }
5100
5101
5102
5103
5104 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] == 0x55AA) {
5105 ushort bios_version, major, minor;
5106
5107 bios_version =
5108 bios_mem[(ASC_MC_BIOS_VERSION - ASC_MC_BIOSMEM) / 2];
5109 major = (bios_version >> 12) & 0xF;
5110 minor = (bios_version >> 8) & 0xF;
5111 if (major < 3 || (major == 3 && minor == 1)) {
5112
5113 AdvReadWordLram(iop_base, 0x120, wdtr_able);
5114 } else {
5115 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
5116 }
5117 }
5118 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
5119 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
5120 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
5121 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
5122 max_cmd[tid]);
5123 }
5124
5125 err = request_firmware(&fw, fwname, asc_dvc->drv_ptr->dev);
5126 if (err) {
5127 printk(KERN_ERR "Failed to load image \"%s\" err %d\n",
5128 fwname, err);
5129 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
5130 return err;
5131 }
5132 if (fw->size < 4) {
5133 printk(KERN_ERR "Bogus length %zu in image \"%s\"\n",
5134 fw->size, fwname);
5135 release_firmware(fw);
5136 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
5137 return -EINVAL;
5138 }
5139 chksum = (fw->data[3] << 24) | (fw->data[2] << 16) |
5140 (fw->data[1] << 8) | fw->data[0];
5141 asc_dvc->err_code = AdvLoadMicrocode(iop_base, &fw->data[4],
5142 fw->size - 4, ADV_3550_MEMSIZE,
5143 chksum);
5144 release_firmware(fw);
5145 if (asc_dvc->err_code)
5146 return ADV_ERROR;
5147
5148
5149
5150
5151 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
5152 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
5153 bios_mem[i]);
5154 }
5155
5156
5157
5158
5159
5160 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
5161 AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
5162 code_sum = 0;
5163 AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
5164 for (word = begin_addr; word < end_addr; word += 2) {
5165 code_sum += AdvReadWordAutoIncLram(iop_base);
5166 }
5167 AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
5168
5169
5170
5171
5172 AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
5173 asc_dvc->cfg->mcode_date);
5174 AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
5175 asc_dvc->cfg->mcode_version);
5176
5177
5178
5179
5180 AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC3550);
5181
5182
5183
5184
5185
5186
5187
5188 if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
5189 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
5190 word |= CONTROL_FLAG_IGNORE_PERR;
5191 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
5192 }
5193
5194
5195
5196
5197
5198 AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
5199 START_CTL_EMFU | READ_CMD_MRM);
5200
5201
5202
5203
5204
5205
5206
5207
5208
5209
5210
5211
5212
5213 if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
5214 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
5215 asc_dvc->wdtr_able);
5216 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
5217 asc_dvc->sdtr_able);
5218 }
5219
5220
5221
5222
5223
5224
5225
5226
5227
5228
5229
5230
5231
5232
5233
5234
5235
5236
5237
5238
5239
5240
5241
5242 word = 0;
5243 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
5244 if (ADV_TID_TO_TIDMASK(tid) & asc_dvc->ultra_able) {
5245
5246 word |= (0x3 << (4 * (tid % 4)));
5247 } else {
5248
5249 word |= (0x2 << (4 * (tid % 4)));
5250 }
5251 if (tid == 3) {
5252 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, word);
5253 word = 0;
5254 } else if (tid == 7) {
5255 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, word);
5256 word = 0;
5257 } else if (tid == 11) {
5258 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, word);
5259 word = 0;
5260 } else if (tid == 15) {
5261 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, word);
5262
5263 }
5264 }
5265
5266
5267
5268
5269 AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
5270 asc_dvc->cfg->disc_enable);
5271
5272
5273
5274
5275
5276
5277
5278 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
5279 PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
5280 asc_dvc->chip_scsi_id);
5281
5282
5283
5284
5285
5286
5287
5288
5289
5290 scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
5291
5292
5293
5294
5295 if ((scsi_cfg1 & CABLE_ILLEGAL_A) == 0 ||
5296 (scsi_cfg1 & CABLE_ILLEGAL_B) == 0) {
5297 asc_dvc->err_code |= ASC_IERR_ILLEGAL_CONNECTION;
5298 return ADV_ERROR;
5299 }
5300
5301
5302
5303
5304
5305
5306 if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
5307 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
5308 return ADV_ERROR;
5309 }
5310
5311
5312
5313
5314
5315 if ((scsi_cfg1 & DIFF_MODE) && (scsi_cfg1 & DIFF_SENSE) == 0) {
5316 asc_dvc->err_code |= ASC_IERR_SINGLE_END_DEVICE;
5317 return ADV_ERROR;
5318 }
5319
5320
5321
5322
5323
5324
5325
5326
5327
5328 if (asc_dvc->cfg->termination == 0) {
5329
5330
5331
5332
5333 asc_dvc->cfg->termination |= TERM_CTL_SEL;
5334
5335 switch (scsi_cfg1 & CABLE_DETECT) {
5336
5337 case 0x3:
5338 case 0x7:
5339 case 0xB:
5340 case 0xD:
5341 case 0xE:
5342 case 0xF:
5343 asc_dvc->cfg->termination |= (TERM_CTL_H | TERM_CTL_L);
5344 break;
5345
5346
5347 case 0x1:
5348 case 0x5:
5349 case 0x9:
5350 case 0xA:
5351 case 0xC:
5352 asc_dvc->cfg->termination |= TERM_CTL_H;
5353 break;
5354
5355
5356 case 0x2:
5357 case 0x6:
5358 break;
5359 }
5360 }
5361
5362
5363
5364
5365 scsi_cfg1 &= ~TERM_CTL;
5366
5367
5368
5369
5370
5371
5372
5373 scsi_cfg1 |= (TERM_CTL_SEL | (~asc_dvc->cfg->termination & TERM_CTL));
5374
5375
5376
5377
5378
5379
5380
5381
5382
5383
5384 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1,
5385 FLTR_DISABLE | scsi_cfg1);
5386
5387
5388
5389
5390
5391
5392
5393
5394
5395
5396
5397
5398 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
5399 BIOS_EN | RAM_SZ_8KB);
5400
5401
5402
5403
5404
5405
5406
5407 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
5408 ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
5409
5410 AdvBuildCarrierFreelist(asc_dvc);
5411
5412
5413
5414
5415
5416 if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
5417 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
5418 return ADV_ERROR;
5419 }
5420 asc_dvc->carr_freelist = (ADV_CARR_T *)
5421 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
5422
5423
5424
5425
5426 asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
5427
5428
5429
5430
5431 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
5432
5433
5434
5435
5436 if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
5437 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
5438 return ADV_ERROR;
5439 }
5440 asc_dvc->carr_freelist = (ADV_CARR_T *)
5441 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
5442
5443
5444
5445
5446
5447
5448
5449
5450 asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
5451
5452
5453
5454
5455 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
5456 asc_dvc->carr_pending_cnt = 0;
5457
5458 AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
5459 (ADV_INTR_ENABLE_HOST_INTR |
5460 ADV_INTR_ENABLE_GLOBAL_INTR));
5461
5462 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
5463 AdvWriteWordRegister(iop_base, IOPW_PC, word);
5464
5465
5466 AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
5467
5468
5469
5470
5471
5472
5473 if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
5474
5475
5476
5477
5478
5479 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
5480 0x55AA) {
5481
5482
5483
5484 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
5485 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
5486 AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
5487 tagqng_able);
5488 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
5489 AdvWriteByteLram(iop_base,
5490 ASC_MC_NUMBER_OF_MAX_CMD + tid,
5491 max_cmd[tid]);
5492 }
5493 } else {
5494 if (AdvResetSB(asc_dvc) != ADV_TRUE) {
5495 warn_code = ASC_WARN_BUSRESET_ERROR;
5496 }
5497 }
5498 }
5499
5500 return warn_code;
5501}
5502
5503
5504
5505
5506
5507
5508
5509
5510
5511
5512
5513static int AdvInitAsc38C0800Driver(ADV_DVC_VAR *asc_dvc)
5514{
5515 const struct firmware *fw;
5516 const char fwname[] = "advansys/38C0800.bin";
5517 AdvPortAddr iop_base;
5518 ushort warn_code;
5519 int begin_addr;
5520 int end_addr;
5521 ushort code_sum;
5522 int word;
5523 int i;
5524 int err;
5525 unsigned long chksum;
5526 ushort scsi_cfg1;
5527 uchar byte;
5528 uchar tid;
5529 ushort bios_mem[ASC_MC_BIOSLEN / 2];
5530 ushort wdtr_able, sdtr_able, tagqng_able;
5531 uchar max_cmd[ADV_MAX_TID + 1];
5532
5533
5534 if (asc_dvc->err_code != 0)
5535 return ADV_ERROR;
5536
5537
5538
5539
5540 if (asc_dvc->chip_type != ADV_CHIP_ASC38C0800) {
5541 asc_dvc->err_code = ASC_IERR_BAD_CHIPTYPE;
5542 return ADV_ERROR;
5543 }
5544
5545 warn_code = 0;
5546 iop_base = asc_dvc->iop_base;
5547
5548
5549
5550
5551
5552
5553
5554
5555
5556 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
5557 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
5558 bios_mem[i]);
5559 }
5560
5561
5562
5563
5564 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
5565 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
5566 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
5567 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
5568 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
5569 max_cmd[tid]);
5570 }
5571
5572
5573
5574
5575
5576
5577
5578
5579
5580
5581
5582
5583
5584
5585
5586
5587
5588
5589
5590
5591
5592
5593
5594
5595
5596
5597
5598
5599
5600
5601 for (i = 0; i < 2; i++) {
5602 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, PRE_TEST_MODE);
5603 mdelay(10);
5604 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
5605 if ((byte & RAM_TEST_DONE) == 0
5606 || (byte & 0x0F) != PRE_TEST_VALUE) {
5607 asc_dvc->err_code = ASC_IERR_BIST_PRE_TEST;
5608 return ADV_ERROR;
5609 }
5610
5611 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
5612 mdelay(10);
5613 if (AdvReadByteRegister(iop_base, IOPB_RAM_BIST)
5614 != NORMAL_VALUE) {
5615 asc_dvc->err_code = ASC_IERR_BIST_PRE_TEST;
5616 return ADV_ERROR;
5617 }
5618 }
5619
5620
5621
5622
5623
5624
5625
5626
5627 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, RAM_TEST_MODE);
5628 mdelay(10);
5629
5630 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
5631 if ((byte & RAM_TEST_DONE) == 0 || (byte & RAM_TEST_STATUS) != 0) {
5632
5633 asc_dvc->bist_err_code = byte;
5634 asc_dvc->err_code = ASC_IERR_BIST_RAM_TEST;
5635 return ADV_ERROR;
5636 }
5637
5638
5639 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
5640
5641 err = request_firmware(&fw, fwname, asc_dvc->drv_ptr->dev);
5642 if (err) {
5643 printk(KERN_ERR "Failed to load image \"%s\" err %d\n",
5644 fwname, err);
5645 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
5646 return err;
5647 }
5648 if (fw->size < 4) {
5649 printk(KERN_ERR "Bogus length %zu in image \"%s\"\n",
5650 fw->size, fwname);
5651 release_firmware(fw);
5652 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
5653 return -EINVAL;
5654 }
5655 chksum = (fw->data[3] << 24) | (fw->data[2] << 16) |
5656 (fw->data[1] << 8) | fw->data[0];
5657 asc_dvc->err_code = AdvLoadMicrocode(iop_base, &fw->data[4],
5658 fw->size - 4, ADV_38C0800_MEMSIZE,
5659 chksum);
5660 release_firmware(fw);
5661 if (asc_dvc->err_code)
5662 return ADV_ERROR;
5663
5664
5665
5666
5667 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
5668 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
5669 bios_mem[i]);
5670 }
5671
5672
5673
5674
5675
5676 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
5677 AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
5678 code_sum = 0;
5679 AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
5680 for (word = begin_addr; word < end_addr; word += 2) {
5681 code_sum += AdvReadWordAutoIncLram(iop_base);
5682 }
5683 AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
5684
5685
5686
5687
5688 AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
5689 asc_dvc->cfg->mcode_date);
5690 AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
5691 asc_dvc->cfg->mcode_version);
5692
5693
5694
5695
5696 AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC38C0800);
5697
5698
5699
5700
5701
5702
5703
5704
5705
5706 scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
5707 AdvWriteWordRegister(iop_base, IOPW_SCSI_CFG1,
5708 scsi_cfg1 | DIS_TERM_DRV);
5709
5710
5711
5712
5713
5714
5715
5716 if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
5717 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
5718 word |= CONTROL_FLAG_IGNORE_PERR;
5719 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
5720 }
5721
5722
5723
5724
5725
5726
5727
5728
5729
5730 AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
5731 BC_THRESH_ENB | FIFO_THRESH_80B | START_CTL_TH |
5732 READ_CMD_MRM);
5733
5734
5735
5736
5737
5738
5739
5740
5741
5742
5743
5744
5745
5746 if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
5747 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
5748 asc_dvc->wdtr_able);
5749 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
5750 asc_dvc->sdtr_able);
5751 }
5752
5753
5754
5755
5756
5757
5758
5759
5760
5761
5762 AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
5763 asc_dvc->cfg->disc_enable);
5764 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, asc_dvc->sdtr_speed1);
5765 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, asc_dvc->sdtr_speed2);
5766 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, asc_dvc->sdtr_speed3);
5767 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, asc_dvc->sdtr_speed4);
5768
5769
5770
5771
5772
5773
5774
5775 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
5776 PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
5777 asc_dvc->chip_scsi_id);
5778
5779
5780
5781
5782
5783
5784
5785
5786
5787 scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
5788
5789
5790
5791
5792
5793
5794 if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
5795 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
5796 return ADV_ERROR;
5797 }
5798
5799
5800
5801
5802
5803
5804
5805
5806
5807
5808
5809
5810 if (scsi_cfg1 & HVD) {
5811 asc_dvc->err_code = ASC_IERR_HVD_DEVICE;
5812 return ADV_ERROR;
5813 }
5814
5815
5816
5817
5818
5819
5820
5821
5822
5823 if ((asc_dvc->cfg->termination & TERM_SE) == 0) {
5824
5825 switch (scsi_cfg1 & C_DET_SE) {
5826
5827 case 0x1:
5828 case 0x2:
5829 case 0x3:
5830 asc_dvc->cfg->termination |= TERM_SE;
5831 break;
5832
5833
5834 case 0x0:
5835 asc_dvc->cfg->termination |= TERM_SE_HI;
5836 break;
5837 }
5838 }
5839
5840 if ((asc_dvc->cfg->termination & TERM_LVD) == 0) {
5841
5842 switch (scsi_cfg1 & C_DET_LVD) {
5843
5844 case 0x4:
5845 case 0x8:
5846 case 0xC:
5847 asc_dvc->cfg->termination |= TERM_LVD;
5848 break;
5849
5850
5851 case 0x0:
5852 break;
5853 }
5854 }
5855
5856
5857
5858
5859 scsi_cfg1 &= (~TERM_SE & ~TERM_LVD);
5860
5861
5862
5863
5864 scsi_cfg1 |= (~asc_dvc->cfg->termination & 0xF0);
5865
5866
5867
5868
5869
5870
5871 scsi_cfg1 &= (~BIG_ENDIAN & ~DIS_TERM_DRV & ~TERM_POL & ~HVD_LVD_SE);
5872
5873
5874
5875
5876
5877
5878
5879
5880
5881
5882 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1, scsi_cfg1);
5883
5884
5885
5886
5887
5888
5889
5890
5891
5892
5893
5894
5895 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
5896 BIOS_EN | RAM_SZ_16KB);
5897
5898
5899
5900
5901
5902
5903
5904 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
5905 ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
5906
5907 AdvBuildCarrierFreelist(asc_dvc);
5908
5909
5910
5911
5912
5913 if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
5914 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
5915 return ADV_ERROR;
5916 }
5917 asc_dvc->carr_freelist = (ADV_CARR_T *)
5918 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
5919
5920
5921
5922
5923 asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
5924
5925
5926
5927
5928
5929 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
5930
5931
5932
5933
5934 if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
5935 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
5936 return ADV_ERROR;
5937 }
5938 asc_dvc->carr_freelist = (ADV_CARR_T *)
5939 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
5940
5941
5942
5943
5944
5945
5946
5947
5948 asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
5949
5950
5951
5952
5953
5954
5955 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
5956 asc_dvc->carr_pending_cnt = 0;
5957
5958 AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
5959 (ADV_INTR_ENABLE_HOST_INTR |
5960 ADV_INTR_ENABLE_GLOBAL_INTR));
5961
5962 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
5963 AdvWriteWordRegister(iop_base, IOPW_PC, word);
5964
5965
5966 AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
5967
5968
5969
5970
5971
5972
5973 if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
5974
5975
5976
5977
5978
5979 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
5980 0x55AA) {
5981
5982
5983
5984 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
5985 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
5986 AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
5987 tagqng_able);
5988 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
5989 AdvWriteByteLram(iop_base,
5990 ASC_MC_NUMBER_OF_MAX_CMD + tid,
5991 max_cmd[tid]);
5992 }
5993 } else {
5994 if (AdvResetSB(asc_dvc) != ADV_TRUE) {
5995 warn_code = ASC_WARN_BUSRESET_ERROR;
5996 }
5997 }
5998 }
5999
6000 return warn_code;
6001}
6002
6003
6004
6005
6006
6007
6008
6009
6010
6011
6012
6013static int AdvInitAsc38C1600Driver(ADV_DVC_VAR *asc_dvc)
6014{
6015 const struct firmware *fw;
6016 const char fwname[] = "advansys/38C1600.bin";
6017 AdvPortAddr iop_base;
6018 ushort warn_code;
6019 int begin_addr;
6020 int end_addr;
6021 ushort code_sum;
6022 long word;
6023 int i;
6024 int err;
6025 unsigned long chksum;
6026 ushort scsi_cfg1;
6027 uchar byte;
6028 uchar tid;
6029 ushort bios_mem[ASC_MC_BIOSLEN / 2];
6030 ushort wdtr_able, sdtr_able, ppr_able, tagqng_able;
6031 uchar max_cmd[ASC_MAX_TID + 1];
6032
6033
6034 if (asc_dvc->err_code != 0) {
6035 return ADV_ERROR;
6036 }
6037
6038
6039
6040
6041 if (asc_dvc->chip_type != ADV_CHIP_ASC38C1600) {
6042 asc_dvc->err_code = ASC_IERR_BAD_CHIPTYPE;
6043 return ADV_ERROR;
6044 }
6045
6046 warn_code = 0;
6047 iop_base = asc_dvc->iop_base;
6048
6049
6050
6051
6052
6053
6054
6055
6056
6057 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
6058 AdvReadWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
6059 bios_mem[i]);
6060 }
6061
6062
6063
6064
6065 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
6066 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
6067 AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
6068 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
6069 for (tid = 0; tid <= ASC_MAX_TID; tid++) {
6070 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
6071 max_cmd[tid]);
6072 }
6073
6074
6075
6076
6077
6078
6079
6080
6081
6082
6083
6084
6085
6086
6087
6088
6089
6090
6091
6092
6093
6094
6095
6096
6097
6098
6099
6100
6101
6102
6103 for (i = 0; i < 2; i++) {
6104 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, PRE_TEST_MODE);
6105 mdelay(10);
6106 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
6107 if ((byte & RAM_TEST_DONE) == 0
6108 || (byte & 0x0F) != PRE_TEST_VALUE) {
6109 asc_dvc->err_code = ASC_IERR_BIST_PRE_TEST;
6110 return ADV_ERROR;
6111 }
6112
6113 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
6114 mdelay(10);
6115 if (AdvReadByteRegister(iop_base, IOPB_RAM_BIST)
6116 != NORMAL_VALUE) {
6117 asc_dvc->err_code = ASC_IERR_BIST_PRE_TEST;
6118 return ADV_ERROR;
6119 }
6120 }
6121
6122
6123
6124
6125
6126
6127
6128
6129 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, RAM_TEST_MODE);
6130 mdelay(10);
6131
6132 byte = AdvReadByteRegister(iop_base, IOPB_RAM_BIST);
6133 if ((byte & RAM_TEST_DONE) == 0 || (byte & RAM_TEST_STATUS) != 0) {
6134
6135 asc_dvc->bist_err_code = byte;
6136 asc_dvc->err_code = ASC_IERR_BIST_RAM_TEST;
6137 return ADV_ERROR;
6138 }
6139
6140
6141 AdvWriteByteRegister(iop_base, IOPB_RAM_BIST, NORMAL_MODE);
6142
6143 err = request_firmware(&fw, fwname, asc_dvc->drv_ptr->dev);
6144 if (err) {
6145 printk(KERN_ERR "Failed to load image \"%s\" err %d\n",
6146 fwname, err);
6147 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
6148 return err;
6149 }
6150 if (fw->size < 4) {
6151 printk(KERN_ERR "Bogus length %zu in image \"%s\"\n",
6152 fw->size, fwname);
6153 release_firmware(fw);
6154 asc_dvc->err_code = ASC_IERR_MCODE_CHKSUM;
6155 return -EINVAL;
6156 }
6157 chksum = (fw->data[3] << 24) | (fw->data[2] << 16) |
6158 (fw->data[1] << 8) | fw->data[0];
6159 asc_dvc->err_code = AdvLoadMicrocode(iop_base, &fw->data[4],
6160 fw->size - 4, ADV_38C1600_MEMSIZE,
6161 chksum);
6162 release_firmware(fw);
6163 if (asc_dvc->err_code)
6164 return ADV_ERROR;
6165
6166
6167
6168
6169 for (i = 0; i < ASC_MC_BIOSLEN / 2; i++) {
6170 AdvWriteWordLram(iop_base, ASC_MC_BIOSMEM + (2 * i),
6171 bios_mem[i]);
6172 }
6173
6174
6175
6176
6177
6178 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, begin_addr);
6179 AdvReadWordLram(iop_base, ASC_MC_CODE_END_ADDR, end_addr);
6180 code_sum = 0;
6181 AdvWriteWordRegister(iop_base, IOPW_RAM_ADDR, begin_addr);
6182 for (word = begin_addr; word < end_addr; word += 2) {
6183 code_sum += AdvReadWordAutoIncLram(iop_base);
6184 }
6185 AdvWriteWordLram(iop_base, ASC_MC_CODE_CHK_SUM, code_sum);
6186
6187
6188
6189
6190 AdvReadWordLram(iop_base, ASC_MC_VERSION_DATE,
6191 asc_dvc->cfg->mcode_date);
6192 AdvReadWordLram(iop_base, ASC_MC_VERSION_NUM,
6193 asc_dvc->cfg->mcode_version);
6194
6195
6196
6197
6198 AdvWriteWordLram(iop_base, ASC_MC_CHIP_TYPE, ADV_CHIP_ASC38C1600);
6199
6200
6201
6202
6203
6204
6205
6206
6207
6208 scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
6209 AdvWriteWordRegister(iop_base, IOPW_SCSI_CFG1,
6210 scsi_cfg1 | DIS_TERM_DRV);
6211
6212
6213
6214
6215
6216
6217
6218 if (asc_dvc->cfg->control_flag & CONTROL_FLAG_IGNORE_PERR) {
6219 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
6220 word |= CONTROL_FLAG_IGNORE_PERR;
6221 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
6222 }
6223
6224
6225
6226
6227
6228
6229
6230 if ((asc_dvc->bios_ctrl & BIOS_CTRL_AIPP_DIS) == 0) {
6231 AdvReadWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
6232 word |= CONTROL_FLAG_ENABLE_AIPP;
6233 AdvWriteWordLram(iop_base, ASC_MC_CONTROL_FLAG, word);
6234 }
6235
6236
6237
6238
6239
6240 AdvWriteByteRegister(iop_base, IOPB_DMA_CFG0,
6241 FIFO_THRESH_80B | START_CTL_TH | READ_CMD_MRM);
6242
6243
6244
6245
6246
6247
6248
6249
6250
6251
6252
6253
6254
6255 if ((asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) == 0) {
6256 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE,
6257 asc_dvc->wdtr_able);
6258 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE,
6259 asc_dvc->sdtr_able);
6260 }
6261
6262
6263
6264
6265
6266
6267
6268
6269
6270
6271 AdvWriteWordLram(iop_base, ASC_MC_DISC_ENABLE,
6272 asc_dvc->cfg->disc_enable);
6273 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED1, asc_dvc->sdtr_speed1);
6274 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED2, asc_dvc->sdtr_speed2);
6275 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED3, asc_dvc->sdtr_speed3);
6276 AdvWriteWordLram(iop_base, ASC_MC_SDTR_SPEED4, asc_dvc->sdtr_speed4);
6277
6278
6279
6280
6281
6282
6283
6284 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG0,
6285 PARITY_EN | QUEUE_128 | SEL_TMO_LONG | OUR_ID_EN |
6286 asc_dvc->chip_scsi_id);
6287
6288
6289
6290
6291
6292
6293
6294
6295
6296
6297 scsi_cfg1 = AdvReadWordRegister(iop_base, IOPW_SCSI_CFG1);
6298
6299
6300
6301
6302
6303
6304 if ((AdvReadWordRegister(iop_base, IOPW_SCSI_CTRL) & 0x3F07) == 0x3F07) {
6305 asc_dvc->err_code |= ASC_IERR_REVERSED_CABLE;
6306 return ADV_ERROR;
6307 }
6308
6309
6310
6311
6312
6313
6314
6315
6316
6317 if (scsi_cfg1 & HVD) {
6318 asc_dvc->err_code |= ASC_IERR_HVD_DEVICE;
6319 return ADV_ERROR;
6320 }
6321
6322
6323
6324
6325
6326
6327
6328
6329
6330
6331
6332
6333
6334
6335 if ((asc_dvc->cfg->termination & TERM_SE) == 0) {
6336 struct pci_dev *pdev = adv_dvc_to_pdev(asc_dvc);
6337
6338 switch (scsi_cfg1 & C_DET_SE) {
6339
6340 case 0x1:
6341 case 0x2:
6342 case 0x3:
6343 asc_dvc->cfg->termination |= TERM_SE;
6344 break;
6345
6346 case 0x0:
6347 if (PCI_FUNC(pdev->devfn) == 0) {
6348
6349 } else {
6350
6351 asc_dvc->cfg->termination |= TERM_SE_HI;
6352 }
6353 break;
6354 }
6355 }
6356
6357
6358
6359
6360 scsi_cfg1 &= ~TERM_SE;
6361
6362
6363
6364
6365 scsi_cfg1 |= (~asc_dvc->cfg->termination & TERM_SE);
6366
6367
6368
6369
6370
6371
6372
6373
6374 scsi_cfg1 &= (~BIG_ENDIAN & ~DIS_TERM_DRV & ~TERM_POL);
6375
6376
6377
6378
6379
6380
6381
6382
6383
6384
6385 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SCSI_CFG1, scsi_cfg1);
6386
6387
6388
6389
6390
6391
6392
6393
6394
6395
6396
6397
6398
6399
6400
6401
6402
6403
6404
6405
6406 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_MEM_CFG,
6407 BIOS_EN | RAM_SZ_16KB);
6408
6409
6410
6411
6412
6413
6414
6415 AdvWriteWordLram(iop_base, ASC_MC_DEFAULT_SEL_MASK,
6416 ADV_TID_TO_TIDMASK(asc_dvc->chip_scsi_id));
6417
6418 AdvBuildCarrierFreelist(asc_dvc);
6419
6420
6421
6422
6423 if ((asc_dvc->icq_sp = asc_dvc->carr_freelist) == NULL) {
6424 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
6425 return ADV_ERROR;
6426 }
6427 asc_dvc->carr_freelist = (ADV_CARR_T *)
6428 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->icq_sp->next_vpa));
6429
6430
6431
6432
6433 asc_dvc->icq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
6434
6435
6436
6437
6438
6439
6440 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_ICQ, asc_dvc->icq_sp->carr_pa);
6441 AdvWriteDWordRegister(iop_base, IOPDW_COMMA,
6442 le32_to_cpu(asc_dvc->icq_sp->carr_pa));
6443
6444
6445
6446
6447 if ((asc_dvc->irq_sp = asc_dvc->carr_freelist) == NULL) {
6448 asc_dvc->err_code |= ASC_IERR_NO_CARRIER;
6449 return ADV_ERROR;
6450 }
6451 asc_dvc->carr_freelist = (ADV_CARR_T *)
6452 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->next_vpa));
6453
6454
6455
6456
6457
6458
6459
6460
6461 asc_dvc->irq_sp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
6462
6463
6464
6465
6466 AdvWriteDWordLramNoSwap(iop_base, ASC_MC_IRQ, asc_dvc->irq_sp->carr_pa);
6467 asc_dvc->carr_pending_cnt = 0;
6468
6469 AdvWriteByteRegister(iop_base, IOPB_INTR_ENABLES,
6470 (ADV_INTR_ENABLE_HOST_INTR |
6471 ADV_INTR_ENABLE_GLOBAL_INTR));
6472 AdvReadWordLram(iop_base, ASC_MC_CODE_BEGIN_ADDR, word);
6473 AdvWriteWordRegister(iop_base, IOPW_PC, word);
6474
6475
6476 AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_RUN);
6477
6478
6479
6480
6481
6482
6483 if (asc_dvc->bios_ctrl & BIOS_CTRL_RESET_SCSI_BUS) {
6484
6485
6486
6487
6488 if (bios_mem[(ASC_MC_BIOS_SIGNATURE - ASC_MC_BIOSMEM) / 2] ==
6489 0x55AA) {
6490
6491
6492
6493 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
6494 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
6495 AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
6496 AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
6497 tagqng_able);
6498 for (tid = 0; tid <= ASC_MAX_TID; tid++) {
6499 AdvWriteByteLram(iop_base,
6500 ASC_MC_NUMBER_OF_MAX_CMD + tid,
6501 max_cmd[tid]);
6502 }
6503 } else {
6504 if (AdvResetSB(asc_dvc) != ADV_TRUE) {
6505 warn_code = ASC_WARN_BUSRESET_ERROR;
6506 }
6507 }
6508 }
6509
6510 return warn_code;
6511}
6512
6513
6514
6515
6516
6517
6518
6519
6520static int AdvResetChipAndSB(ADV_DVC_VAR *asc_dvc)
6521{
6522 int status;
6523 ushort wdtr_able, sdtr_able, tagqng_able;
6524 ushort ppr_able = 0;
6525 uchar tid, max_cmd[ADV_MAX_TID + 1];
6526 AdvPortAddr iop_base;
6527 ushort bios_sig;
6528
6529 iop_base = asc_dvc->iop_base;
6530
6531
6532
6533
6534 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
6535 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
6536 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
6537 AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
6538 }
6539 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
6540 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
6541 AdvReadByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
6542 max_cmd[tid]);
6543 }
6544
6545
6546
6547
6548
6549
6550
6551 AdvReadWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, bios_sig);
6552 AdvWriteWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, 0);
6553
6554
6555
6556
6557 AdvWriteWordRegister(iop_base, IOPW_RISC_CSR, ADV_RISC_CSR_STOP);
6558 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG, ADV_CTRL_REG_CMD_RESET);
6559 mdelay(100);
6560 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
6561 ADV_CTRL_REG_CMD_WR_IO_REG);
6562
6563
6564
6565
6566
6567 asc_dvc->err_code = 0;
6568 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
6569 status = AdvInitAsc38C1600Driver(asc_dvc);
6570 } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
6571 status = AdvInitAsc38C0800Driver(asc_dvc);
6572 } else {
6573 status = AdvInitAsc3550Driver(asc_dvc);
6574 }
6575
6576
6577 if (status == 0) {
6578 status = ADV_TRUE;
6579 } else {
6580 status = ADV_FALSE;
6581 }
6582
6583
6584
6585
6586 AdvWriteWordLram(iop_base, ASC_MC_BIOS_SIGNATURE, bios_sig);
6587
6588
6589
6590
6591 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, wdtr_able);
6592 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, sdtr_able);
6593 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
6594 AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE, ppr_able);
6595 }
6596 AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE, tagqng_able);
6597 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
6598 AdvWriteByteLram(iop_base, ASC_MC_NUMBER_OF_MAX_CMD + tid,
6599 max_cmd[tid]);
6600 }
6601
6602 return status;
6603}
6604
6605
6606
6607
6608static void adv_async_callback(ADV_DVC_VAR *adv_dvc_varp, uchar code)
6609{
6610 switch (code) {
6611 case ADV_ASYNC_SCSI_BUS_RESET_DET:
6612
6613
6614
6615 ASC_DBG(0, "ADV_ASYNC_SCSI_BUS_RESET_DET\n");
6616 break;
6617
6618 case ADV_ASYNC_RDMA_FAILURE:
6619
6620
6621
6622
6623
6624 ASC_DBG(0, "ADV_ASYNC_RDMA_FAILURE\n");
6625 AdvResetChipAndSB(adv_dvc_varp);
6626 break;
6627
6628 case ADV_HOST_SCSI_BUS_RESET:
6629
6630
6631
6632 ASC_DBG(0, "ADV_HOST_SCSI_BUS_RESET\n");
6633 break;
6634
6635 default:
6636 ASC_DBG(0, "unknown code 0x%x\n", code);
6637 break;
6638 }
6639}
6640
6641
6642
6643
6644
6645
6646static void adv_isr_callback(ADV_DVC_VAR *adv_dvc_varp, ADV_SCSI_REQ_Q *scsiqp)
6647{
6648 struct asc_board *boardp;
6649 adv_req_t *reqp;
6650 adv_sgblk_t *sgblkp;
6651 struct scsi_cmnd *scp;
6652 struct Scsi_Host *shost;
6653 ADV_DCNT resid_cnt;
6654
6655 ASC_DBG(1, "adv_dvc_varp 0x%lx, scsiqp 0x%lx\n",
6656 (ulong)adv_dvc_varp, (ulong)scsiqp);
6657 ASC_DBG_PRT_ADV_SCSI_REQ_Q(2, scsiqp);
6658
6659
6660
6661
6662
6663
6664 reqp = (adv_req_t *)ADV_U32_TO_VADDR(scsiqp->srb_ptr);
6665 ASC_DBG(1, "reqp 0x%lx\n", (ulong)reqp);
6666 if (reqp == NULL) {
6667 ASC_PRINT("adv_isr_callback: reqp is NULL\n");
6668 return;
6669 }
6670
6671
6672
6673
6674
6675
6676
6677
6678
6679 scp = reqp->cmndp;
6680 ASC_DBG(1, "scp 0x%p\n", scp);
6681 if (scp == NULL) {
6682 ASC_PRINT
6683 ("adv_isr_callback: scp is NULL; adv_req_t dropped.\n");
6684 return;
6685 }
6686 ASC_DBG_PRT_CDB(2, scp->cmnd, scp->cmd_len);
6687
6688 shost = scp->device->host;
6689 ASC_STATS(shost, callback);
6690 ASC_DBG(1, "shost 0x%p\n", shost);
6691
6692 boardp = shost_priv(shost);
6693 BUG_ON(adv_dvc_varp != &boardp->dvc_var.adv_dvc_var);
6694
6695
6696
6697
6698 switch (scsiqp->done_status) {
6699 case QD_NO_ERROR:
6700 ASC_DBG(2, "QD_NO_ERROR\n");
6701 scp->result = 0;
6702
6703
6704
6705
6706
6707
6708
6709 resid_cnt = le32_to_cpu(scsiqp->data_cnt);
6710 if (scsi_bufflen(scp) != 0 && resid_cnt != 0 &&
6711 resid_cnt <= scsi_bufflen(scp)) {
6712 ASC_DBG(1, "underrun condition %lu bytes\n",
6713 (ulong)resid_cnt);
6714 scsi_set_resid(scp, resid_cnt);
6715 }
6716 break;
6717
6718 case QD_WITH_ERROR:
6719 ASC_DBG(2, "QD_WITH_ERROR\n");
6720 switch (scsiqp->host_status) {
6721 case QHSTA_NO_ERROR:
6722 if (scsiqp->scsi_status == SAM_STAT_CHECK_CONDITION) {
6723 ASC_DBG(2, "SAM_STAT_CHECK_CONDITION\n");
6724 ASC_DBG_PRT_SENSE(2, scp->sense_buffer,
6725 SCSI_SENSE_BUFFERSIZE);
6726
6727
6728
6729
6730
6731
6732
6733
6734
6735
6736
6737
6738 scp->result = DRIVER_BYTE(DRIVER_SENSE) |
6739 STATUS_BYTE(scsiqp->scsi_status);
6740 } else {
6741 scp->result = STATUS_BYTE(scsiqp->scsi_status);
6742 }
6743 break;
6744
6745 default:
6746
6747 ASC_DBG(1, "host_status 0x%x\n", scsiqp->host_status);
6748 scp->result = HOST_BYTE(DID_BAD_TARGET);
6749 break;
6750 }
6751 break;
6752
6753 case QD_ABORTED_BY_HOST:
6754 ASC_DBG(1, "QD_ABORTED_BY_HOST\n");
6755 scp->result =
6756 HOST_BYTE(DID_ABORT) | STATUS_BYTE(scsiqp->scsi_status);
6757 break;
6758
6759 default:
6760 ASC_DBG(1, "done_status 0x%x\n", scsiqp->done_status);
6761 scp->result =
6762 HOST_BYTE(DID_ERROR) | STATUS_BYTE(scsiqp->scsi_status);
6763 break;
6764 }
6765
6766
6767
6768
6769
6770
6771 if ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(scp->device->id)) == 0 &&
6772 scsiqp->done_status == QD_NO_ERROR &&
6773 scsiqp->host_status == QHSTA_NO_ERROR) {
6774 boardp->init_tidmask |= ADV_TID_TO_TIDMASK(scp->device->id);
6775 }
6776
6777 asc_scsi_done(scp);
6778
6779
6780
6781
6782 while ((sgblkp = reqp->sgblkp) != NULL) {
6783
6784 reqp->sgblkp = sgblkp->next_sgblkp;
6785
6786
6787 sgblkp->next_sgblkp = boardp->adv_sgblkp;
6788 boardp->adv_sgblkp = sgblkp;
6789 }
6790
6791
6792
6793
6794
6795 reqp->next_reqp = boardp->adv_reqp;
6796 boardp->adv_reqp = reqp;
6797
6798 ASC_DBG(1, "done\n");
6799}
6800
6801
6802
6803
6804
6805
6806
6807
6808
6809
6810
6811
6812
6813
6814
6815
6816
6817
6818
6819
6820static int AdvISR(ADV_DVC_VAR *asc_dvc)
6821{
6822 AdvPortAddr iop_base;
6823 uchar int_stat;
6824 ushort target_bit;
6825 ADV_CARR_T *free_carrp;
6826 ADV_VADDR irq_next_vpa;
6827 ADV_SCSI_REQ_Q *scsiq;
6828
6829 iop_base = asc_dvc->iop_base;
6830
6831
6832 int_stat = AdvReadByteRegister(iop_base, IOPB_INTR_STATUS_REG);
6833
6834 if ((int_stat & (ADV_INTR_STATUS_INTRA | ADV_INTR_STATUS_INTRB |
6835 ADV_INTR_STATUS_INTRC)) == 0) {
6836 return ADV_FALSE;
6837 }
6838
6839
6840
6841
6842
6843
6844 if (int_stat & ADV_INTR_STATUS_INTRB) {
6845 uchar intrb_code;
6846
6847 AdvReadByteLram(iop_base, ASC_MC_INTRB_CODE, intrb_code);
6848
6849 if (asc_dvc->chip_type == ADV_CHIP_ASC3550 ||
6850 asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
6851 if (intrb_code == ADV_ASYNC_CARRIER_READY_FAILURE &&
6852 asc_dvc->carr_pending_cnt != 0) {
6853 AdvWriteByteRegister(iop_base, IOPB_TICKLE,
6854 ADV_TICKLE_A);
6855 if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
6856 AdvWriteByteRegister(iop_base,
6857 IOPB_TICKLE,
6858 ADV_TICKLE_NOP);
6859 }
6860 }
6861 }
6862
6863 adv_async_callback(asc_dvc, intrb_code);
6864 }
6865
6866
6867
6868
6869 while (((irq_next_vpa =
6870 le32_to_cpu(asc_dvc->irq_sp->next_vpa)) & ASC_RQ_DONE) != 0) {
6871
6872
6873
6874
6875
6876
6877
6878
6879
6880 scsiq = (ADV_SCSI_REQ_Q *)
6881 ADV_U32_TO_VADDR(le32_to_cpu(asc_dvc->irq_sp->areq_vpa));
6882
6883
6884
6885
6886
6887
6888 if ((irq_next_vpa & ASC_RQ_GOOD) != 0) {
6889 scsiq->done_status = QD_NO_ERROR;
6890 scsiq->host_status = scsiq->scsi_status = 0;
6891 scsiq->data_cnt = 0L;
6892 }
6893
6894
6895
6896
6897
6898
6899 free_carrp = asc_dvc->irq_sp;
6900 asc_dvc->irq_sp = (ADV_CARR_T *)
6901 ADV_U32_TO_VADDR(ASC_GET_CARRP(irq_next_vpa));
6902
6903 free_carrp->next_vpa =
6904 cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->carr_freelist));
6905 asc_dvc->carr_freelist = free_carrp;
6906 asc_dvc->carr_pending_cnt--;
6907
6908 target_bit = ADV_TID_TO_TIDMASK(scsiq->target_id);
6909
6910
6911
6912
6913 scsiq->cntl = 0;
6914
6915
6916
6917
6918
6919 scsiq->a_flag |= ADV_SCSIQ_DONE;
6920 adv_isr_callback(asc_dvc, scsiq);
6921
6922
6923
6924
6925
6926
6927
6928 }
6929 return ADV_TRUE;
6930}
6931
6932static int AscSetLibErrorCode(ASC_DVC_VAR *asc_dvc, ushort err_code)
6933{
6934 if (asc_dvc->err_code == 0) {
6935 asc_dvc->err_code = err_code;
6936 AscWriteLramWord(asc_dvc->iop_base, ASCV_ASCDVC_ERR_CODE_W,
6937 err_code);
6938 }
6939 return err_code;
6940}
6941
6942static void AscAckInterrupt(PortAddr iop_base)
6943{
6944 uchar host_flag;
6945 uchar risc_flag;
6946 ushort loop;
6947
6948 loop = 0;
6949 do {
6950 risc_flag = AscReadLramByte(iop_base, ASCV_RISC_FLAG_B);
6951 if (loop++ > 0x7FFF) {
6952 break;
6953 }
6954 } while ((risc_flag & ASC_RISC_FLAG_GEN_INT) != 0);
6955 host_flag =
6956 AscReadLramByte(iop_base,
6957 ASCV_HOST_FLAG_B) & (~ASC_HOST_FLAG_ACK_INT);
6958 AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B,
6959 (uchar)(host_flag | ASC_HOST_FLAG_ACK_INT));
6960 AscSetChipStatus(iop_base, CIW_INT_ACK);
6961 loop = 0;
6962 while (AscGetChipStatus(iop_base) & CSW_INT_PENDING) {
6963 AscSetChipStatus(iop_base, CIW_INT_ACK);
6964 if (loop++ > 3) {
6965 break;
6966 }
6967 }
6968 AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B, host_flag);
6969}
6970
6971static uchar AscGetSynPeriodIndex(ASC_DVC_VAR *asc_dvc, uchar syn_time)
6972{
6973 const uchar *period_table;
6974 int max_index;
6975 int min_index;
6976 int i;
6977
6978 period_table = asc_dvc->sdtr_period_tbl;
6979 max_index = (int)asc_dvc->max_sdtr_index;
6980 min_index = (int)asc_dvc->min_sdtr_index;
6981 if ((syn_time <= period_table[max_index])) {
6982 for (i = min_index; i < (max_index - 1); i++) {
6983 if (syn_time <= period_table[i]) {
6984 return (uchar)i;
6985 }
6986 }
6987 return (uchar)max_index;
6988 } else {
6989 return (uchar)(max_index + 1);
6990 }
6991}
6992
6993static uchar
6994AscMsgOutSDTR(ASC_DVC_VAR *asc_dvc, uchar sdtr_period, uchar sdtr_offset)
6995{
6996 EXT_MSG sdtr_buf;
6997 uchar sdtr_period_index;
6998 PortAddr iop_base;
6999
7000 iop_base = asc_dvc->iop_base;
7001 sdtr_buf.msg_type = EXTENDED_MESSAGE;
7002 sdtr_buf.msg_len = MS_SDTR_LEN;
7003 sdtr_buf.msg_req = EXTENDED_SDTR;
7004 sdtr_buf.xfer_period = sdtr_period;
7005 sdtr_offset &= ASC_SYN_MAX_OFFSET;
7006 sdtr_buf.req_ack_offset = sdtr_offset;
7007 sdtr_period_index = AscGetSynPeriodIndex(asc_dvc, sdtr_period);
7008 if (sdtr_period_index <= asc_dvc->max_sdtr_index) {
7009 AscMemWordCopyPtrToLram(iop_base, ASCV_MSGOUT_BEG,
7010 (uchar *)&sdtr_buf,
7011 sizeof(EXT_MSG) >> 1);
7012 return ((sdtr_period_index << 4) | sdtr_offset);
7013 } else {
7014 sdtr_buf.req_ack_offset = 0;
7015 AscMemWordCopyPtrToLram(iop_base, ASCV_MSGOUT_BEG,
7016 (uchar *)&sdtr_buf,
7017 sizeof(EXT_MSG) >> 1);
7018 return 0;
7019 }
7020}
7021
7022static uchar
7023AscCalSDTRData(ASC_DVC_VAR *asc_dvc, uchar sdtr_period, uchar syn_offset)
7024{
7025 uchar byte;
7026 uchar sdtr_period_ix;
7027
7028 sdtr_period_ix = AscGetSynPeriodIndex(asc_dvc, sdtr_period);
7029 if (sdtr_period_ix > asc_dvc->max_sdtr_index)
7030 return 0xFF;
7031 byte = (sdtr_period_ix << 4) | (syn_offset & ASC_SYN_MAX_OFFSET);
7032 return byte;
7033}
7034
7035static int AscSetChipSynRegAtID(PortAddr iop_base, uchar id, uchar sdtr_data)
7036{
7037 ASC_SCSI_BIT_ID_TYPE org_id;
7038 int i;
7039 int sta = TRUE;
7040
7041 AscSetBank(iop_base, 1);
7042 org_id = AscReadChipDvcID(iop_base);
7043 for (i = 0; i <= ASC_MAX_TID; i++) {
7044 if (org_id == (0x01 << i))
7045 break;
7046 }
7047 org_id = (ASC_SCSI_BIT_ID_TYPE) i;
7048 AscWriteChipDvcID(iop_base, id);
7049 if (AscReadChipDvcID(iop_base) == (0x01 << id)) {
7050 AscSetBank(iop_base, 0);
7051 AscSetChipSyn(iop_base, sdtr_data);
7052 if (AscGetChipSyn(iop_base) != sdtr_data) {
7053 sta = FALSE;
7054 }
7055 } else {
7056 sta = FALSE;
7057 }
7058 AscSetBank(iop_base, 1);
7059 AscWriteChipDvcID(iop_base, org_id);
7060 AscSetBank(iop_base, 0);
7061 return (sta);
7062}
7063
7064static void AscSetChipSDTR(PortAddr iop_base, uchar sdtr_data, uchar tid_no)
7065{
7066 AscSetChipSynRegAtID(iop_base, tid_no, sdtr_data);
7067 AscPutMCodeSDTRDoneAtID(iop_base, tid_no, sdtr_data);
7068}
7069
7070static int AscIsrChipHalted(ASC_DVC_VAR *asc_dvc)
7071{
7072 EXT_MSG ext_msg;
7073 EXT_MSG out_msg;
7074 ushort halt_q_addr;
7075 int sdtr_accept;
7076 ushort int_halt_code;
7077 ASC_SCSI_BIT_ID_TYPE scsi_busy;
7078 ASC_SCSI_BIT_ID_TYPE target_id;
7079 PortAddr iop_base;
7080 uchar tag_code;
7081 uchar q_status;
7082 uchar halt_qp;
7083 uchar sdtr_data;
7084 uchar target_ix;
7085 uchar q_cntl, tid_no;
7086 uchar cur_dvc_qng;
7087 uchar asyn_sdtr;
7088 uchar scsi_status;
7089 struct asc_board *boardp;
7090
7091 BUG_ON(!asc_dvc->drv_ptr);
7092 boardp = asc_dvc->drv_ptr;
7093
7094 iop_base = asc_dvc->iop_base;
7095 int_halt_code = AscReadLramWord(iop_base, ASCV_HALTCODE_W);
7096
7097 halt_qp = AscReadLramByte(iop_base, ASCV_CURCDB_B);
7098 halt_q_addr = ASC_QNO_TO_QADDR(halt_qp);
7099 target_ix = AscReadLramByte(iop_base,
7100 (ushort)(halt_q_addr +
7101 (ushort)ASC_SCSIQ_B_TARGET_IX));
7102 q_cntl = AscReadLramByte(iop_base,
7103 (ushort)(halt_q_addr + (ushort)ASC_SCSIQ_B_CNTL));
7104 tid_no = ASC_TIX_TO_TID(target_ix);
7105 target_id = (uchar)ASC_TID_TO_TARGET_ID(tid_no);
7106 if (asc_dvc->pci_fix_asyn_xfer & target_id) {
7107 asyn_sdtr = ASYN_SDTR_DATA_FIX_PCI_REV_AB;
7108 } else {
7109 asyn_sdtr = 0;
7110 }
7111 if (int_halt_code == ASC_HALT_DISABLE_ASYN_USE_SYN_FIX) {
7112 if (asc_dvc->pci_fix_asyn_xfer & target_id) {
7113 AscSetChipSDTR(iop_base, 0, tid_no);
7114 boardp->sdtr_data[tid_no] = 0;
7115 }
7116 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7117 return (0);
7118 } else if (int_halt_code == ASC_HALT_ENABLE_ASYN_USE_SYN_FIX) {
7119 if (asc_dvc->pci_fix_asyn_xfer & target_id) {
7120 AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
7121 boardp->sdtr_data[tid_no] = asyn_sdtr;
7122 }
7123 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7124 return (0);
7125 } else if (int_halt_code == ASC_HALT_EXTMSG_IN) {
7126 AscMemWordCopyPtrFromLram(iop_base,
7127 ASCV_MSGIN_BEG,
7128 (uchar *)&ext_msg,
7129 sizeof(EXT_MSG) >> 1);
7130
7131 if (ext_msg.msg_type == EXTENDED_MESSAGE &&
7132 ext_msg.msg_req == EXTENDED_SDTR &&
7133 ext_msg.msg_len == MS_SDTR_LEN) {
7134 sdtr_accept = TRUE;
7135 if ((ext_msg.req_ack_offset > ASC_SYN_MAX_OFFSET)) {
7136
7137 sdtr_accept = FALSE;
7138 ext_msg.req_ack_offset = ASC_SYN_MAX_OFFSET;
7139 }
7140 if ((ext_msg.xfer_period <
7141 asc_dvc->sdtr_period_tbl[asc_dvc->min_sdtr_index])
7142 || (ext_msg.xfer_period >
7143 asc_dvc->sdtr_period_tbl[asc_dvc->
7144 max_sdtr_index])) {
7145 sdtr_accept = FALSE;
7146 ext_msg.xfer_period =
7147 asc_dvc->sdtr_period_tbl[asc_dvc->
7148 min_sdtr_index];
7149 }
7150 if (sdtr_accept) {
7151 sdtr_data =
7152 AscCalSDTRData(asc_dvc, ext_msg.xfer_period,
7153 ext_msg.req_ack_offset);
7154 if ((sdtr_data == 0xFF)) {
7155
7156 q_cntl |= QC_MSG_OUT;
7157 asc_dvc->init_sdtr &= ~target_id;
7158 asc_dvc->sdtr_done &= ~target_id;
7159 AscSetChipSDTR(iop_base, asyn_sdtr,
7160 tid_no);
7161 boardp->sdtr_data[tid_no] = asyn_sdtr;
7162 }
7163 }
7164 if (ext_msg.req_ack_offset == 0) {
7165
7166 q_cntl &= ~QC_MSG_OUT;
7167 asc_dvc->init_sdtr &= ~target_id;
7168 asc_dvc->sdtr_done &= ~target_id;
7169 AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
7170 } else {
7171 if (sdtr_accept && (q_cntl & QC_MSG_OUT)) {
7172 q_cntl &= ~QC_MSG_OUT;
7173 asc_dvc->sdtr_done |= target_id;
7174 asc_dvc->init_sdtr |= target_id;
7175 asc_dvc->pci_fix_asyn_xfer &=
7176 ~target_id;
7177 sdtr_data =
7178 AscCalSDTRData(asc_dvc,
7179 ext_msg.xfer_period,
7180 ext_msg.
7181 req_ack_offset);
7182 AscSetChipSDTR(iop_base, sdtr_data,
7183 tid_no);
7184 boardp->sdtr_data[tid_no] = sdtr_data;
7185 } else {
7186 q_cntl |= QC_MSG_OUT;
7187 AscMsgOutSDTR(asc_dvc,
7188 ext_msg.xfer_period,
7189 ext_msg.req_ack_offset);
7190 asc_dvc->pci_fix_asyn_xfer &=
7191 ~target_id;
7192 sdtr_data =
7193 AscCalSDTRData(asc_dvc,
7194 ext_msg.xfer_period,
7195 ext_msg.
7196 req_ack_offset);
7197 AscSetChipSDTR(iop_base, sdtr_data,
7198 tid_no);
7199 boardp->sdtr_data[tid_no] = sdtr_data;
7200 asc_dvc->sdtr_done |= target_id;
7201 asc_dvc->init_sdtr |= target_id;
7202 }
7203 }
7204
7205 AscWriteLramByte(iop_base,
7206 (ushort)(halt_q_addr +
7207 (ushort)ASC_SCSIQ_B_CNTL),
7208 q_cntl);
7209 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7210 return (0);
7211 } else if (ext_msg.msg_type == EXTENDED_MESSAGE &&
7212 ext_msg.msg_req == EXTENDED_WDTR &&
7213 ext_msg.msg_len == MS_WDTR_LEN) {
7214
7215 ext_msg.wdtr_width = 0;
7216 AscMemWordCopyPtrToLram(iop_base,
7217 ASCV_MSGOUT_BEG,
7218 (uchar *)&ext_msg,
7219 sizeof(EXT_MSG) >> 1);
7220 q_cntl |= QC_MSG_OUT;
7221 AscWriteLramByte(iop_base,
7222 (ushort)(halt_q_addr +
7223 (ushort)ASC_SCSIQ_B_CNTL),
7224 q_cntl);
7225 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7226 return (0);
7227 } else {
7228
7229 ext_msg.msg_type = MESSAGE_REJECT;
7230 AscMemWordCopyPtrToLram(iop_base,
7231 ASCV_MSGOUT_BEG,
7232 (uchar *)&ext_msg,
7233 sizeof(EXT_MSG) >> 1);
7234 q_cntl |= QC_MSG_OUT;
7235 AscWriteLramByte(iop_base,
7236 (ushort)(halt_q_addr +
7237 (ushort)ASC_SCSIQ_B_CNTL),
7238 q_cntl);
7239 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7240 return (0);
7241 }
7242 } else if (int_halt_code == ASC_HALT_CHK_CONDITION) {
7243
7244 q_cntl |= QC_REQ_SENSE;
7245
7246 if ((asc_dvc->init_sdtr & target_id) != 0) {
7247
7248 asc_dvc->sdtr_done &= ~target_id;
7249
7250 sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
7251 q_cntl |= QC_MSG_OUT;
7252 AscMsgOutSDTR(asc_dvc,
7253 asc_dvc->
7254 sdtr_period_tbl[(sdtr_data >> 4) &
7255 (uchar)(asc_dvc->
7256 max_sdtr_index -
7257 1)],
7258 (uchar)(sdtr_data & (uchar)
7259 ASC_SYN_MAX_OFFSET));
7260 }
7261
7262 AscWriteLramByte(iop_base,
7263 (ushort)(halt_q_addr +
7264 (ushort)ASC_SCSIQ_B_CNTL), q_cntl);
7265
7266 tag_code = AscReadLramByte(iop_base,
7267 (ushort)(halt_q_addr + (ushort)
7268 ASC_SCSIQ_B_TAG_CODE));
7269 tag_code &= 0xDC;
7270 if ((asc_dvc->pci_fix_asyn_xfer & target_id)
7271 && !(asc_dvc->pci_fix_asyn_xfer_always & target_id)
7272 ) {
7273
7274 tag_code |= (ASC_TAG_FLAG_DISABLE_DISCONNECT
7275 | ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX);
7276
7277 }
7278 AscWriteLramByte(iop_base,
7279 (ushort)(halt_q_addr +
7280 (ushort)ASC_SCSIQ_B_TAG_CODE),
7281 tag_code);
7282
7283 q_status = AscReadLramByte(iop_base,
7284 (ushort)(halt_q_addr + (ushort)
7285 ASC_SCSIQ_B_STATUS));
7286 q_status |= (QS_READY | QS_BUSY);
7287 AscWriteLramByte(iop_base,
7288 (ushort)(halt_q_addr +
7289 (ushort)ASC_SCSIQ_B_STATUS),
7290 q_status);
7291
7292 scsi_busy = AscReadLramByte(iop_base, (ushort)ASCV_SCSIBUSY_B);
7293 scsi_busy &= ~target_id;
7294 AscWriteLramByte(iop_base, (ushort)ASCV_SCSIBUSY_B, scsi_busy);
7295
7296 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7297 return (0);
7298 } else if (int_halt_code == ASC_HALT_SDTR_REJECTED) {
7299
7300 AscMemWordCopyPtrFromLram(iop_base,
7301 ASCV_MSGOUT_BEG,
7302 (uchar *)&out_msg,
7303 sizeof(EXT_MSG) >> 1);
7304
7305 if ((out_msg.msg_type == EXTENDED_MESSAGE) &&
7306 (out_msg.msg_len == MS_SDTR_LEN) &&
7307 (out_msg.msg_req == EXTENDED_SDTR)) {
7308
7309 asc_dvc->init_sdtr &= ~target_id;
7310 asc_dvc->sdtr_done &= ~target_id;
7311 AscSetChipSDTR(iop_base, asyn_sdtr, tid_no);
7312 boardp->sdtr_data[tid_no] = asyn_sdtr;
7313 }
7314 q_cntl &= ~QC_MSG_OUT;
7315 AscWriteLramByte(iop_base,
7316 (ushort)(halt_q_addr +
7317 (ushort)ASC_SCSIQ_B_CNTL), q_cntl);
7318 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7319 return (0);
7320 } else if (int_halt_code == ASC_HALT_SS_QUEUE_FULL) {
7321
7322 scsi_status = AscReadLramByte(iop_base,
7323 (ushort)((ushort)halt_q_addr +
7324 (ushort)
7325 ASC_SCSIQ_SCSI_STATUS));
7326 cur_dvc_qng =
7327 AscReadLramByte(iop_base,
7328 (ushort)((ushort)ASC_QADR_BEG +
7329 (ushort)target_ix));
7330 if ((cur_dvc_qng > 0) && (asc_dvc->cur_dvc_qng[tid_no] > 0)) {
7331
7332 scsi_busy = AscReadLramByte(iop_base,
7333 (ushort)ASCV_SCSIBUSY_B);
7334 scsi_busy |= target_id;
7335 AscWriteLramByte(iop_base,
7336 (ushort)ASCV_SCSIBUSY_B, scsi_busy);
7337 asc_dvc->queue_full_or_busy |= target_id;
7338
7339 if (scsi_status == SAM_STAT_TASK_SET_FULL) {
7340 if (cur_dvc_qng > ASC_MIN_TAGGED_CMD) {
7341 cur_dvc_qng -= 1;
7342 asc_dvc->max_dvc_qng[tid_no] =
7343 cur_dvc_qng;
7344
7345 AscWriteLramByte(iop_base,
7346 (ushort)((ushort)
7347 ASCV_MAX_DVC_QNG_BEG
7348 + (ushort)
7349 tid_no),
7350 cur_dvc_qng);
7351
7352
7353
7354
7355
7356
7357 boardp->queue_full |= target_id;
7358 boardp->queue_full_cnt[tid_no] =
7359 cur_dvc_qng;
7360 }
7361 }
7362 }
7363 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7364 return (0);
7365 }
7366#if CC_VERY_LONG_SG_LIST
7367 else if (int_halt_code == ASC_HALT_HOST_COPY_SG_LIST_TO_RISC) {
7368 uchar q_no;
7369 ushort q_addr;
7370 uchar sg_wk_q_no;
7371 uchar first_sg_wk_q_no;
7372 ASC_SCSI_Q *scsiq;
7373 ASC_SG_HEAD *sg_head;
7374 ASC_SG_LIST_Q scsi_sg_q;
7375 ushort sg_list_dwords;
7376 ushort sg_entry_cnt;
7377 uchar next_qp;
7378 int i;
7379
7380 q_no = AscReadLramByte(iop_base, (ushort)ASCV_REQ_SG_LIST_QP);
7381 if (q_no == ASC_QLINK_END)
7382 return 0;
7383
7384 q_addr = ASC_QNO_TO_QADDR(q_no);
7385
7386
7387
7388
7389
7390
7391
7392
7393 scsiq = (ASC_SCSI_Q *)
7394 ASC_SRB2SCSIQ(ASC_U32_TO_VADDR(AscReadLramDWord(iop_base,
7395 (ushort)
7396 (q_addr +
7397 ASC_SCSIQ_D_SRBPTR))));
7398
7399
7400
7401
7402 sg_wk_q_no = AscReadLramByte(iop_base,
7403 (ushort)(q_addr +
7404 ASC_SCSIQ_B_SG_WK_QP));
7405
7406 first_sg_wk_q_no = AscReadLramByte(iop_base,
7407 (ushort)(q_addr +
7408 ASC_SCSIQ_B_FIRST_SG_WK_QP));
7409
7410
7411
7412
7413
7414 AscWriteLramByte(iop_base,
7415 (ushort)(q_addr +
7416 (ushort)ASC_SCSIQ_B_SG_WK_QP),
7417 first_sg_wk_q_no);
7418
7419 sg_head = scsiq->sg_head;
7420
7421
7422
7423
7424
7425
7426
7427
7428
7429
7430 if (scsiq->remain_sg_entry_cnt > (ASC_MAX_SG_LIST - 1)) {
7431 sg_entry_cnt = ASC_MAX_SG_LIST - 1;
7432
7433
7434
7435
7436
7437 scsiq->remain_sg_entry_cnt -= (ASC_MAX_SG_LIST - 1);
7438 } else {
7439 sg_entry_cnt = scsiq->remain_sg_entry_cnt;
7440 scsiq->remain_sg_entry_cnt = 0;
7441 }
7442
7443
7444
7445
7446
7447
7448 next_qp = first_sg_wk_q_no;
7449 q_addr = ASC_QNO_TO_QADDR(next_qp);
7450 scsi_sg_q.sg_head_qp = q_no;
7451 scsi_sg_q.cntl = QCSG_SG_XFER_LIST;
7452 for (i = 0; i < sg_head->queue_cnt; i++) {
7453 scsi_sg_q.seq_no = i + 1;
7454 if (sg_entry_cnt > ASC_SG_LIST_PER_Q) {
7455 sg_list_dwords = (uchar)(ASC_SG_LIST_PER_Q * 2);
7456 sg_entry_cnt -= ASC_SG_LIST_PER_Q;
7457
7458
7459
7460
7461
7462
7463
7464 scsi_sg_q.sg_list_cnt = ASC_SG_LIST_PER_Q - 1;
7465 scsi_sg_q.sg_cur_list_cnt =
7466 ASC_SG_LIST_PER_Q - 1;
7467 } else {
7468
7469
7470
7471
7472
7473
7474 if (scsiq->remain_sg_entry_cnt != 0) {
7475 scsi_sg_q.cntl |= QCSG_SG_XFER_MORE;
7476 } else {
7477 scsi_sg_q.cntl |= QCSG_SG_XFER_END;
7478 }
7479
7480 sg_list_dwords = sg_entry_cnt << 1;
7481 scsi_sg_q.sg_list_cnt = sg_entry_cnt - 1;
7482 scsi_sg_q.sg_cur_list_cnt = sg_entry_cnt - 1;
7483 sg_entry_cnt = 0;
7484 }
7485
7486 scsi_sg_q.q_no = next_qp;
7487 AscMemWordCopyPtrToLram(iop_base,
7488 q_addr + ASC_SCSIQ_SGHD_CPY_BEG,
7489 (uchar *)&scsi_sg_q,
7490 sizeof(ASC_SG_LIST_Q) >> 1);
7491
7492 AscMemDWordCopyPtrToLram(iop_base,
7493 q_addr + ASC_SGQ_LIST_BEG,
7494 (uchar *)&sg_head->
7495 sg_list[scsiq->next_sg_index],
7496 sg_list_dwords);
7497
7498 scsiq->next_sg_index += ASC_SG_LIST_PER_Q;
7499
7500
7501
7502
7503
7504
7505 if (scsi_sg_q.cntl & QCSG_SG_XFER_END) {
7506 break;
7507 }
7508
7509 next_qp = AscReadLramByte(iop_base,
7510 (ushort)(q_addr +
7511 ASC_SCSIQ_B_FWD));
7512 q_addr = ASC_QNO_TO_QADDR(next_qp);
7513 }
7514
7515
7516
7517
7518
7519 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0);
7520 return (0);
7521 }
7522#endif
7523 return (0);
7524}
7525
7526
7527
7528
7529
7530
7531
7532
7533
7534
7535
7536static void
7537DvcGetQinfo(PortAddr iop_base, ushort s_addr, uchar *inbuf, int words)
7538{
7539 int i;
7540 ushort word;
7541
7542 AscSetChipLramAddr(iop_base, s_addr);
7543 for (i = 0; i < 2 * words; i += 2) {
7544 if (i == 10) {
7545 continue;
7546 }
7547 word = inpw(iop_base + IOP_RAM_DATA);
7548 inbuf[i] = word & 0xff;
7549 inbuf[i + 1] = (word >> 8) & 0xff;
7550 }
7551 ASC_DBG_PRT_HEX(2, "DvcGetQinfo", inbuf, 2 * words);
7552}
7553
7554static uchar
7555_AscCopyLramScsiDoneQ(PortAddr iop_base,
7556 ushort q_addr,
7557 ASC_QDONE_INFO *scsiq, ASC_DCNT max_dma_count)
7558{
7559 ushort _val;
7560 uchar sg_queue_cnt;
7561
7562 DvcGetQinfo(iop_base,
7563 q_addr + ASC_SCSIQ_DONE_INFO_BEG,
7564 (uchar *)scsiq,
7565 (sizeof(ASC_SCSIQ_2) + sizeof(ASC_SCSIQ_3)) / 2);
7566
7567 _val = AscReadLramWord(iop_base,
7568 (ushort)(q_addr + (ushort)ASC_SCSIQ_B_STATUS));
7569 scsiq->q_status = (uchar)_val;
7570 scsiq->q_no = (uchar)(_val >> 8);
7571 _val = AscReadLramWord(iop_base,
7572 (ushort)(q_addr + (ushort)ASC_SCSIQ_B_CNTL));
7573 scsiq->cntl = (uchar)_val;
7574 sg_queue_cnt = (uchar)(_val >> 8);
7575 _val = AscReadLramWord(iop_base,
7576 (ushort)(q_addr +
7577 (ushort)ASC_SCSIQ_B_SENSE_LEN));
7578 scsiq->sense_len = (uchar)_val;
7579 scsiq->extra_bytes = (uchar)(_val >> 8);
7580
7581
7582
7583
7584 scsiq->remain_bytes = (((ADV_DCNT)AscReadLramWord(iop_base,
7585 (ushort)(q_addr +
7586 (ushort)
7587 ASC_SCSIQ_W_ALT_DC1)))
7588 << 16);
7589
7590
7591
7592 scsiq->remain_bytes += AscReadLramWord(iop_base,
7593 (ushort)(q_addr + (ushort)
7594 ASC_SCSIQ_DW_REMAIN_XFER_CNT));
7595
7596 scsiq->remain_bytes &= max_dma_count;
7597 return sg_queue_cnt;
7598}
7599
7600
7601
7602
7603
7604
7605static void asc_isr_callback(ASC_DVC_VAR *asc_dvc_varp, ASC_QDONE_INFO *qdonep)
7606{
7607 struct asc_board *boardp;
7608 struct scsi_cmnd *scp;
7609 struct Scsi_Host *shost;
7610
7611 ASC_DBG(1, "asc_dvc_varp 0x%p, qdonep 0x%p\n", asc_dvc_varp, qdonep);
7612 ASC_DBG_PRT_ASC_QDONE_INFO(2, qdonep);
7613
7614 scp = advansys_srb_to_ptr(asc_dvc_varp, qdonep->d2.srb_ptr);
7615 if (!scp)
7616 return;
7617
7618 ASC_DBG_PRT_CDB(2, scp->cmnd, scp->cmd_len);
7619
7620 shost = scp->device->host;
7621 ASC_STATS(shost, callback);
7622 ASC_DBG(1, "shost 0x%p\n", shost);
7623
7624 boardp = shost_priv(shost);
7625 BUG_ON(asc_dvc_varp != &boardp->dvc_var.asc_dvc_var);
7626
7627 dma_unmap_single(boardp->dev, scp->SCp.dma_handle,
7628 SCSI_SENSE_BUFFERSIZE, DMA_FROM_DEVICE);
7629
7630
7631
7632 switch (qdonep->d3.done_stat) {
7633 case QD_NO_ERROR:
7634 ASC_DBG(2, "QD_NO_ERROR\n");
7635 scp->result = 0;
7636
7637
7638
7639
7640
7641
7642
7643 if (scsi_bufflen(scp) != 0 && qdonep->remain_bytes != 0 &&
7644 qdonep->remain_bytes <= scsi_bufflen(scp)) {
7645 ASC_DBG(1, "underrun condition %u bytes\n",
7646 (unsigned)qdonep->remain_bytes);
7647 scsi_set_resid(scp, qdonep->remain_bytes);
7648 }
7649 break;
7650
7651 case QD_WITH_ERROR:
7652 ASC_DBG(2, "QD_WITH_ERROR\n");
7653 switch (qdonep->d3.host_stat) {
7654 case QHSTA_NO_ERROR:
7655 if (qdonep->d3.scsi_stat == SAM_STAT_CHECK_CONDITION) {
7656 ASC_DBG(2, "SAM_STAT_CHECK_CONDITION\n");
7657 ASC_DBG_PRT_SENSE(2, scp->sense_buffer,
7658 SCSI_SENSE_BUFFERSIZE);
7659
7660
7661
7662
7663
7664
7665
7666
7667
7668
7669
7670
7671 scp->result = DRIVER_BYTE(DRIVER_SENSE) |
7672 STATUS_BYTE(qdonep->d3.scsi_stat);
7673 } else {
7674 scp->result = STATUS_BYTE(qdonep->d3.scsi_stat);
7675 }
7676 break;
7677
7678 default:
7679
7680 ASC_DBG(1, "host_stat 0x%x\n", qdonep->d3.host_stat);
7681 scp->result = HOST_BYTE(DID_BAD_TARGET);
7682 break;
7683 }
7684 break;
7685
7686 case QD_ABORTED_BY_HOST:
7687 ASC_DBG(1, "QD_ABORTED_BY_HOST\n");
7688 scp->result =
7689 HOST_BYTE(DID_ABORT) | MSG_BYTE(qdonep->d3.
7690 scsi_msg) |
7691 STATUS_BYTE(qdonep->d3.scsi_stat);
7692 break;
7693
7694 default:
7695 ASC_DBG(1, "done_stat 0x%x\n", qdonep->d3.done_stat);
7696 scp->result =
7697 HOST_BYTE(DID_ERROR) | MSG_BYTE(qdonep->d3.
7698 scsi_msg) |
7699 STATUS_BYTE(qdonep->d3.scsi_stat);
7700 break;
7701 }
7702
7703
7704
7705
7706
7707
7708 if ((boardp->init_tidmask & ADV_TID_TO_TIDMASK(scp->device->id)) == 0 &&
7709 qdonep->d3.done_stat == QD_NO_ERROR &&
7710 qdonep->d3.host_stat == QHSTA_NO_ERROR) {
7711 boardp->init_tidmask |= ADV_TID_TO_TIDMASK(scp->device->id);
7712 }
7713
7714 asc_scsi_done(scp);
7715}
7716
7717static int AscIsrQDone(ASC_DVC_VAR *asc_dvc)
7718{
7719 uchar next_qp;
7720 uchar n_q_used;
7721 uchar sg_list_qp;
7722 uchar sg_queue_cnt;
7723 uchar q_cnt;
7724 uchar done_q_tail;
7725 uchar tid_no;
7726 ASC_SCSI_BIT_ID_TYPE scsi_busy;
7727 ASC_SCSI_BIT_ID_TYPE target_id;
7728 PortAddr iop_base;
7729 ushort q_addr;
7730 ushort sg_q_addr;
7731 uchar cur_target_qng;
7732 ASC_QDONE_INFO scsiq_buf;
7733 ASC_QDONE_INFO *scsiq;
7734 int false_overrun;
7735
7736 iop_base = asc_dvc->iop_base;
7737 n_q_used = 1;
7738 scsiq = (ASC_QDONE_INFO *)&scsiq_buf;
7739 done_q_tail = (uchar)AscGetVarDoneQTail(iop_base);
7740 q_addr = ASC_QNO_TO_QADDR(done_q_tail);
7741 next_qp = AscReadLramByte(iop_base,
7742 (ushort)(q_addr + (ushort)ASC_SCSIQ_B_FWD));
7743 if (next_qp != ASC_QLINK_END) {
7744 AscPutVarDoneQTail(iop_base, next_qp);
7745 q_addr = ASC_QNO_TO_QADDR(next_qp);
7746 sg_queue_cnt = _AscCopyLramScsiDoneQ(iop_base, q_addr, scsiq,
7747 asc_dvc->max_dma_count);
7748 AscWriteLramByte(iop_base,
7749 (ushort)(q_addr +
7750 (ushort)ASC_SCSIQ_B_STATUS),
7751 (uchar)(scsiq->
7752 q_status & (uchar)~(QS_READY |
7753 QS_ABORTED)));
7754 tid_no = ASC_TIX_TO_TID(scsiq->d2.target_ix);
7755 target_id = ASC_TIX_TO_TARGET_ID(scsiq->d2.target_ix);
7756 if ((scsiq->cntl & QC_SG_HEAD) != 0) {
7757 sg_q_addr = q_addr;
7758 sg_list_qp = next_qp;
7759 for (q_cnt = 0; q_cnt < sg_queue_cnt; q_cnt++) {
7760 sg_list_qp = AscReadLramByte(iop_base,
7761 (ushort)(sg_q_addr
7762 + (ushort)
7763 ASC_SCSIQ_B_FWD));
7764 sg_q_addr = ASC_QNO_TO_QADDR(sg_list_qp);
7765 if (sg_list_qp == ASC_QLINK_END) {
7766 AscSetLibErrorCode(asc_dvc,
7767 ASCQ_ERR_SG_Q_LINKS);
7768 scsiq->d3.done_stat = QD_WITH_ERROR;
7769 scsiq->d3.host_stat =
7770 QHSTA_D_QDONE_SG_LIST_CORRUPTED;
7771 goto FATAL_ERR_QDONE;
7772 }
7773 AscWriteLramByte(iop_base,
7774 (ushort)(sg_q_addr + (ushort)
7775 ASC_SCSIQ_B_STATUS),
7776 QS_FREE);
7777 }
7778 n_q_used = sg_queue_cnt + 1;
7779 AscPutVarDoneQTail(iop_base, sg_list_qp);
7780 }
7781 if (asc_dvc->queue_full_or_busy & target_id) {
7782 cur_target_qng = AscReadLramByte(iop_base,
7783 (ushort)((ushort)
7784 ASC_QADR_BEG
7785 + (ushort)
7786 scsiq->d2.
7787 target_ix));
7788 if (cur_target_qng < asc_dvc->max_dvc_qng[tid_no]) {
7789 scsi_busy = AscReadLramByte(iop_base, (ushort)
7790 ASCV_SCSIBUSY_B);
7791 scsi_busy &= ~target_id;
7792 AscWriteLramByte(iop_base,
7793 (ushort)ASCV_SCSIBUSY_B,
7794 scsi_busy);
7795 asc_dvc->queue_full_or_busy &= ~target_id;
7796 }
7797 }
7798 if (asc_dvc->cur_total_qng >= n_q_used) {
7799 asc_dvc->cur_total_qng -= n_q_used;
7800 if (asc_dvc->cur_dvc_qng[tid_no] != 0) {
7801 asc_dvc->cur_dvc_qng[tid_no]--;
7802 }
7803 } else {
7804 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_CUR_QNG);
7805 scsiq->d3.done_stat = QD_WITH_ERROR;
7806 goto FATAL_ERR_QDONE;
7807 }
7808 if ((scsiq->d2.srb_ptr == 0UL) ||
7809 ((scsiq->q_status & QS_ABORTED) != 0)) {
7810 return (0x11);
7811 } else if (scsiq->q_status == QS_DONE) {
7812 false_overrun = FALSE;
7813 if (scsiq->extra_bytes != 0) {
7814 scsiq->remain_bytes +=
7815 (ADV_DCNT)scsiq->extra_bytes;
7816 }
7817 if (scsiq->d3.done_stat == QD_WITH_ERROR) {
7818 if (scsiq->d3.host_stat ==
7819 QHSTA_M_DATA_OVER_RUN) {
7820 if ((scsiq->
7821 cntl & (QC_DATA_IN | QC_DATA_OUT))
7822 == 0) {
7823 scsiq->d3.done_stat =
7824 QD_NO_ERROR;
7825 scsiq->d3.host_stat =
7826 QHSTA_NO_ERROR;
7827 } else if (false_overrun) {
7828 scsiq->d3.done_stat =
7829 QD_NO_ERROR;
7830 scsiq->d3.host_stat =
7831 QHSTA_NO_ERROR;
7832 }
7833 } else if (scsiq->d3.host_stat ==
7834 QHSTA_M_HUNG_REQ_SCSI_BUS_RESET) {
7835 AscStopChip(iop_base);
7836 AscSetChipControl(iop_base,
7837 (uchar)(CC_SCSI_RESET
7838 | CC_HALT));
7839 udelay(60);
7840 AscSetChipControl(iop_base, CC_HALT);
7841 AscSetChipStatus(iop_base,
7842 CIW_CLR_SCSI_RESET_INT);
7843 AscSetChipStatus(iop_base, 0);
7844 AscSetChipControl(iop_base, 0);
7845 }
7846 }
7847 if ((scsiq->cntl & QC_NO_CALLBACK) == 0) {
7848 asc_isr_callback(asc_dvc, scsiq);
7849 } else {
7850 if ((AscReadLramByte(iop_base,
7851 (ushort)(q_addr + (ushort)
7852 ASC_SCSIQ_CDB_BEG))
7853 == START_STOP)) {
7854 asc_dvc->unit_not_ready &= ~target_id;
7855 if (scsiq->d3.done_stat != QD_NO_ERROR) {
7856 asc_dvc->start_motor &=
7857 ~target_id;
7858 }
7859 }
7860 }
7861 return (1);
7862 } else {
7863 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_Q_STATUS);
7864 FATAL_ERR_QDONE:
7865 if ((scsiq->cntl & QC_NO_CALLBACK) == 0) {
7866 asc_isr_callback(asc_dvc, scsiq);
7867 }
7868 return (0x80);
7869 }
7870 }
7871 return (0);
7872}
7873
7874static int AscISR(ASC_DVC_VAR *asc_dvc)
7875{
7876 ASC_CS_TYPE chipstat;
7877 PortAddr iop_base;
7878 ushort saved_ram_addr;
7879 uchar ctrl_reg;
7880 uchar saved_ctrl_reg;
7881 int int_pending;
7882 int status;
7883 uchar host_flag;
7884
7885 iop_base = asc_dvc->iop_base;
7886 int_pending = FALSE;
7887
7888 if (AscIsIntPending(iop_base) == 0)
7889 return int_pending;
7890
7891 if ((asc_dvc->init_state & ASC_INIT_STATE_END_LOAD_MC) == 0) {
7892 return ERR;
7893 }
7894 if (asc_dvc->in_critical_cnt != 0) {
7895 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_ISR_ON_CRITICAL);
7896 return ERR;
7897 }
7898 if (asc_dvc->is_in_int) {
7899 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_ISR_RE_ENTRY);
7900 return ERR;
7901 }
7902 asc_dvc->is_in_int = TRUE;
7903 ctrl_reg = AscGetChipControl(iop_base);
7904 saved_ctrl_reg = ctrl_reg & (~(CC_SCSI_RESET | CC_CHIP_RESET |
7905 CC_SINGLE_STEP | CC_DIAG | CC_TEST));
7906 chipstat = AscGetChipStatus(iop_base);
7907 if (chipstat & CSW_SCSI_RESET_LATCH) {
7908 if (!(asc_dvc->bus_type & (ASC_IS_VL | ASC_IS_EISA))) {
7909 int i = 10;
7910 int_pending = TRUE;
7911 asc_dvc->sdtr_done = 0;
7912 saved_ctrl_reg &= (uchar)(~CC_HALT);
7913 while ((AscGetChipStatus(iop_base) &
7914 CSW_SCSI_RESET_ACTIVE) && (i-- > 0)) {
7915 mdelay(100);
7916 }
7917 AscSetChipControl(iop_base, (CC_CHIP_RESET | CC_HALT));
7918 AscSetChipControl(iop_base, CC_HALT);
7919 AscSetChipStatus(iop_base, CIW_CLR_SCSI_RESET_INT);
7920 AscSetChipStatus(iop_base, 0);
7921 chipstat = AscGetChipStatus(iop_base);
7922 }
7923 }
7924 saved_ram_addr = AscGetChipLramAddr(iop_base);
7925 host_flag = AscReadLramByte(iop_base,
7926 ASCV_HOST_FLAG_B) &
7927 (uchar)(~ASC_HOST_FLAG_IN_ISR);
7928 AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B,
7929 (uchar)(host_flag | (uchar)ASC_HOST_FLAG_IN_ISR));
7930 if ((chipstat & CSW_INT_PENDING) || (int_pending)) {
7931 AscAckInterrupt(iop_base);
7932 int_pending = TRUE;
7933 if ((chipstat & CSW_HALTED) && (ctrl_reg & CC_SINGLE_STEP)) {
7934 if (AscIsrChipHalted(asc_dvc) == ERR) {
7935 goto ISR_REPORT_QDONE_FATAL_ERROR;
7936 } else {
7937 saved_ctrl_reg &= (uchar)(~CC_HALT);
7938 }
7939 } else {
7940 ISR_REPORT_QDONE_FATAL_ERROR:
7941 if ((asc_dvc->dvc_cntl & ASC_CNTL_INT_MULTI_Q) != 0) {
7942 while (((status =
7943 AscIsrQDone(asc_dvc)) & 0x01) != 0) {
7944 }
7945 } else {
7946 do {
7947 if ((status =
7948 AscIsrQDone(asc_dvc)) == 1) {
7949 break;
7950 }
7951 } while (status == 0x11);
7952 }
7953 if ((status & 0x80) != 0)
7954 int_pending = ERR;
7955 }
7956 }
7957 AscWriteLramByte(iop_base, ASCV_HOST_FLAG_B, host_flag);
7958 AscSetChipLramAddr(iop_base, saved_ram_addr);
7959 AscSetChipControl(iop_base, saved_ctrl_reg);
7960 asc_dvc->is_in_int = FALSE;
7961 return int_pending;
7962}
7963
7964
7965
7966
7967
7968
7969
7970
7971
7972
7973static int advansys_reset(struct scsi_cmnd *scp)
7974{
7975 struct Scsi_Host *shost = scp->device->host;
7976 struct asc_board *boardp = shost_priv(shost);
7977 unsigned long flags;
7978 int status;
7979 int ret = SUCCESS;
7980
7981 ASC_DBG(1, "0x%p\n", scp);
7982
7983 ASC_STATS(shost, reset);
7984
7985 scmd_printk(KERN_INFO, scp, "SCSI bus reset started...\n");
7986
7987 if (ASC_NARROW_BOARD(boardp)) {
7988 ASC_DVC_VAR *asc_dvc = &boardp->dvc_var.asc_dvc_var;
7989
7990
7991 ASC_DBG(1, "before AscInitAsc1000Driver()\n");
7992 status = AscInitAsc1000Driver(asc_dvc);
7993
7994
7995 if (asc_dvc->err_code || !asc_dvc->overrun_dma) {
7996 scmd_printk(KERN_INFO, scp, "SCSI bus reset error: "
7997 "0x%x, status: 0x%x\n", asc_dvc->err_code,
7998 status);
7999 ret = FAILED;
8000 } else if (status) {
8001 scmd_printk(KERN_INFO, scp, "SCSI bus reset warning: "
8002 "0x%x\n", status);
8003 } else {
8004 scmd_printk(KERN_INFO, scp, "SCSI bus reset "
8005 "successful\n");
8006 }
8007
8008 ASC_DBG(1, "after AscInitAsc1000Driver()\n");
8009 spin_lock_irqsave(shost->host_lock, flags);
8010 } else {
8011
8012
8013
8014
8015 ADV_DVC_VAR *adv_dvc = &boardp->dvc_var.adv_dvc_var;
8016
8017
8018
8019
8020 ASC_DBG(1, "before AdvResetChipAndSB()\n");
8021 switch (AdvResetChipAndSB(adv_dvc)) {
8022 case ASC_TRUE:
8023 scmd_printk(KERN_INFO, scp, "SCSI bus reset "
8024 "successful\n");
8025 break;
8026 case ASC_FALSE:
8027 default:
8028 scmd_printk(KERN_INFO, scp, "SCSI bus reset error\n");
8029 ret = FAILED;
8030 break;
8031 }
8032 spin_lock_irqsave(shost->host_lock, flags);
8033 AdvISR(adv_dvc);
8034 }
8035
8036
8037 boardp->last_reset = jiffies;
8038 spin_unlock_irqrestore(shost->host_lock, flags);
8039
8040 ASC_DBG(1, "ret %d\n", ret);
8041
8042 return ret;
8043}
8044
8045
8046
8047
8048
8049
8050
8051
8052
8053
8054
8055
8056static int
8057advansys_biosparam(struct scsi_device *sdev, struct block_device *bdev,
8058 sector_t capacity, int ip[])
8059{
8060 struct asc_board *boardp = shost_priv(sdev->host);
8061
8062 ASC_DBG(1, "begin\n");
8063 ASC_STATS(sdev->host, biosparam);
8064 if (ASC_NARROW_BOARD(boardp)) {
8065 if ((boardp->dvc_var.asc_dvc_var.dvc_cntl &
8066 ASC_CNTL_BIOS_GT_1GB) && capacity > 0x200000) {
8067 ip[0] = 255;
8068 ip[1] = 63;
8069 } else {
8070 ip[0] = 64;
8071 ip[1] = 32;
8072 }
8073 } else {
8074 if ((boardp->dvc_var.adv_dvc_var.bios_ctrl &
8075 BIOS_CTRL_EXTENDED_XLAT) && capacity > 0x200000) {
8076 ip[0] = 255;
8077 ip[1] = 63;
8078 } else {
8079 ip[0] = 64;
8080 ip[1] = 32;
8081 }
8082 }
8083 ip[2] = (unsigned long)capacity / (ip[0] * ip[1]);
8084 ASC_DBG(1, "end\n");
8085 return 0;
8086}
8087
8088
8089
8090
8091
8092
8093static irqreturn_t advansys_interrupt(int irq, void *dev_id)
8094{
8095 struct Scsi_Host *shost = dev_id;
8096 struct asc_board *boardp = shost_priv(shost);
8097 irqreturn_t result = IRQ_NONE;
8098
8099 ASC_DBG(2, "boardp 0x%p\n", boardp);
8100 spin_lock(shost->host_lock);
8101 if (ASC_NARROW_BOARD(boardp)) {
8102 if (AscIsIntPending(shost->io_port)) {
8103 result = IRQ_HANDLED;
8104 ASC_STATS(shost, interrupt);
8105 ASC_DBG(1, "before AscISR()\n");
8106 AscISR(&boardp->dvc_var.asc_dvc_var);
8107 }
8108 } else {
8109 ASC_DBG(1, "before AdvISR()\n");
8110 if (AdvISR(&boardp->dvc_var.adv_dvc_var)) {
8111 result = IRQ_HANDLED;
8112 ASC_STATS(shost, interrupt);
8113 }
8114 }
8115 spin_unlock(shost->host_lock);
8116
8117 ASC_DBG(1, "end\n");
8118 return result;
8119}
8120
8121static int AscHostReqRiscHalt(PortAddr iop_base)
8122{
8123 int count = 0;
8124 int sta = 0;
8125 uchar saved_stop_code;
8126
8127 if (AscIsChipHalted(iop_base))
8128 return (1);
8129 saved_stop_code = AscReadLramByte(iop_base, ASCV_STOP_CODE_B);
8130 AscWriteLramByte(iop_base, ASCV_STOP_CODE_B,
8131 ASC_STOP_HOST_REQ_RISC_HALT | ASC_STOP_REQ_RISC_STOP);
8132 do {
8133 if (AscIsChipHalted(iop_base)) {
8134 sta = 1;
8135 break;
8136 }
8137 mdelay(100);
8138 } while (count++ < 20);
8139 AscWriteLramByte(iop_base, ASCV_STOP_CODE_B, saved_stop_code);
8140 return (sta);
8141}
8142
8143static int
8144AscSetRunChipSynRegAtID(PortAddr iop_base, uchar tid_no, uchar sdtr_data)
8145{
8146 int sta = FALSE;
8147
8148 if (AscHostReqRiscHalt(iop_base)) {
8149 sta = AscSetChipSynRegAtID(iop_base, tid_no, sdtr_data);
8150 AscStartChip(iop_base);
8151 }
8152 return sta;
8153}
8154
8155static void AscAsyncFix(ASC_DVC_VAR *asc_dvc, struct scsi_device *sdev)
8156{
8157 char type = sdev->type;
8158 ASC_SCSI_BIT_ID_TYPE tid_bits = 1 << sdev->id;
8159
8160 if (!(asc_dvc->bug_fix_cntl & ASC_BUG_FIX_ASYN_USE_SYN))
8161 return;
8162 if (asc_dvc->init_sdtr & tid_bits)
8163 return;
8164
8165 if ((type == TYPE_ROM) && (strncmp(sdev->vendor, "HP ", 3) == 0))
8166 asc_dvc->pci_fix_asyn_xfer_always |= tid_bits;
8167
8168 asc_dvc->pci_fix_asyn_xfer |= tid_bits;
8169 if ((type == TYPE_PROCESSOR) || (type == TYPE_SCANNER) ||
8170 (type == TYPE_ROM) || (type == TYPE_TAPE))
8171 asc_dvc->pci_fix_asyn_xfer &= ~tid_bits;
8172
8173 if (asc_dvc->pci_fix_asyn_xfer & tid_bits)
8174 AscSetRunChipSynRegAtID(asc_dvc->iop_base, sdev->id,
8175 ASYN_SDTR_DATA_FIX_PCI_REV_AB);
8176}
8177
8178static void
8179advansys_narrow_slave_configure(struct scsi_device *sdev, ASC_DVC_VAR *asc_dvc)
8180{
8181 ASC_SCSI_BIT_ID_TYPE tid_bit = 1 << sdev->id;
8182 ASC_SCSI_BIT_ID_TYPE orig_use_tagged_qng = asc_dvc->use_tagged_qng;
8183
8184 if (sdev->lun == 0) {
8185 ASC_SCSI_BIT_ID_TYPE orig_init_sdtr = asc_dvc->init_sdtr;
8186 if ((asc_dvc->cfg->sdtr_enable & tid_bit) && sdev->sdtr) {
8187 asc_dvc->init_sdtr |= tid_bit;
8188 } else {
8189 asc_dvc->init_sdtr &= ~tid_bit;
8190 }
8191
8192 if (orig_init_sdtr != asc_dvc->init_sdtr)
8193 AscAsyncFix(asc_dvc, sdev);
8194 }
8195
8196 if (sdev->tagged_supported) {
8197 if (asc_dvc->cfg->cmd_qng_enabled & tid_bit) {
8198 if (sdev->lun == 0) {
8199 asc_dvc->cfg->can_tagged_qng |= tid_bit;
8200 asc_dvc->use_tagged_qng |= tid_bit;
8201 }
8202 scsi_adjust_queue_depth(sdev, MSG_ORDERED_TAG,
8203 asc_dvc->max_dvc_qng[sdev->id]);
8204 }
8205 } else {
8206 if (sdev->lun == 0) {
8207 asc_dvc->cfg->can_tagged_qng &= ~tid_bit;
8208 asc_dvc->use_tagged_qng &= ~tid_bit;
8209 }
8210 scsi_adjust_queue_depth(sdev, 0, sdev->host->cmd_per_lun);
8211 }
8212
8213 if ((sdev->lun == 0) &&
8214 (orig_use_tagged_qng != asc_dvc->use_tagged_qng)) {
8215 AscWriteLramByte(asc_dvc->iop_base, ASCV_DISC_ENABLE_B,
8216 asc_dvc->cfg->disc_enable);
8217 AscWriteLramByte(asc_dvc->iop_base, ASCV_USE_TAGGED_QNG_B,
8218 asc_dvc->use_tagged_qng);
8219 AscWriteLramByte(asc_dvc->iop_base, ASCV_CAN_TAGGED_QNG_B,
8220 asc_dvc->cfg->can_tagged_qng);
8221
8222 asc_dvc->max_dvc_qng[sdev->id] =
8223 asc_dvc->cfg->max_tag_qng[sdev->id];
8224 AscWriteLramByte(asc_dvc->iop_base,
8225 (ushort)(ASCV_MAX_DVC_QNG_BEG + sdev->id),
8226 asc_dvc->max_dvc_qng[sdev->id]);
8227 }
8228}
8229
8230
8231
8232
8233
8234
8235
8236
8237static void
8238advansys_wide_enable_wdtr(AdvPortAddr iop_base, unsigned short tidmask)
8239{
8240 unsigned short cfg_word;
8241 AdvReadWordLram(iop_base, ASC_MC_WDTR_ABLE, cfg_word);
8242 if ((cfg_word & tidmask) != 0)
8243 return;
8244
8245 cfg_word |= tidmask;
8246 AdvWriteWordLram(iop_base, ASC_MC_WDTR_ABLE, cfg_word);
8247
8248
8249
8250
8251
8252
8253
8254 AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE, cfg_word);
8255 cfg_word &= ~tidmask;
8256 AdvWriteWordLram(iop_base, ASC_MC_SDTR_DONE, cfg_word);
8257 AdvReadWordLram(iop_base, ASC_MC_WDTR_DONE, cfg_word);
8258 cfg_word &= ~tidmask;
8259 AdvWriteWordLram(iop_base, ASC_MC_WDTR_DONE, cfg_word);
8260}
8261
8262
8263
8264
8265
8266
8267
8268
8269static void
8270advansys_wide_enable_sdtr(AdvPortAddr iop_base, unsigned short tidmask)
8271{
8272 unsigned short cfg_word;
8273 AdvReadWordLram(iop_base, ASC_MC_SDTR_ABLE, cfg_word);
8274 if ((cfg_word & tidmask) != 0)
8275 return;
8276
8277 cfg_word |= tidmask;
8278 AdvWriteWordLram(iop_base, ASC_MC_SDTR_ABLE, cfg_word);
8279
8280
8281
8282
8283
8284 AdvReadWordLram(iop_base, ASC_MC_SDTR_DONE, cfg_word);
8285 cfg_word &= ~tidmask;
8286 AdvWriteWordLram(iop_base, ASC_MC_SDTR_DONE, cfg_word);
8287}
8288
8289
8290
8291
8292
8293
8294
8295
8296
8297static void advansys_wide_enable_ppr(ADV_DVC_VAR *adv_dvc,
8298 AdvPortAddr iop_base, unsigned short tidmask)
8299{
8300 AdvReadWordLram(iop_base, ASC_MC_PPR_ABLE, adv_dvc->ppr_able);
8301 adv_dvc->ppr_able |= tidmask;
8302 AdvWriteWordLram(iop_base, ASC_MC_PPR_ABLE, adv_dvc->ppr_able);
8303}
8304
8305static void
8306advansys_wide_slave_configure(struct scsi_device *sdev, ADV_DVC_VAR *adv_dvc)
8307{
8308 AdvPortAddr iop_base = adv_dvc->iop_base;
8309 unsigned short tidmask = 1 << sdev->id;
8310
8311 if (sdev->lun == 0) {
8312
8313
8314
8315
8316
8317
8318 if ((adv_dvc->wdtr_able & tidmask) && sdev->wdtr)
8319 advansys_wide_enable_wdtr(iop_base, tidmask);
8320 if ((adv_dvc->sdtr_able & tidmask) && sdev->sdtr)
8321 advansys_wide_enable_sdtr(iop_base, tidmask);
8322 if (adv_dvc->chip_type == ADV_CHIP_ASC38C1600 && sdev->ppr)
8323 advansys_wide_enable_ppr(adv_dvc, iop_base, tidmask);
8324
8325
8326
8327
8328
8329
8330
8331 if ((adv_dvc->tagqng_able & tidmask) &&
8332 sdev->tagged_supported) {
8333 unsigned short cfg_word;
8334 AdvReadWordLram(iop_base, ASC_MC_TAGQNG_ABLE, cfg_word);
8335 cfg_word |= tidmask;
8336 AdvWriteWordLram(iop_base, ASC_MC_TAGQNG_ABLE,
8337 cfg_word);
8338 AdvWriteByteLram(iop_base,
8339 ASC_MC_NUMBER_OF_MAX_CMD + sdev->id,
8340 adv_dvc->max_dvc_qng);
8341 }
8342 }
8343
8344 if ((adv_dvc->tagqng_able & tidmask) && sdev->tagged_supported) {
8345 scsi_adjust_queue_depth(sdev, MSG_ORDERED_TAG,
8346 adv_dvc->max_dvc_qng);
8347 } else {
8348 scsi_adjust_queue_depth(sdev, 0, sdev->host->cmd_per_lun);
8349 }
8350}
8351
8352
8353
8354
8355
8356static int advansys_slave_configure(struct scsi_device *sdev)
8357{
8358 struct asc_board *boardp = shost_priv(sdev->host);
8359
8360 if (ASC_NARROW_BOARD(boardp))
8361 advansys_narrow_slave_configure(sdev,
8362 &boardp->dvc_var.asc_dvc_var);
8363 else
8364 advansys_wide_slave_configure(sdev,
8365 &boardp->dvc_var.adv_dvc_var);
8366
8367 return 0;
8368}
8369
8370static __le32 advansys_get_sense_buffer_dma(struct scsi_cmnd *scp)
8371{
8372 struct asc_board *board = shost_priv(scp->device->host);
8373 scp->SCp.dma_handle = dma_map_single(board->dev, scp->sense_buffer,
8374 SCSI_SENSE_BUFFERSIZE, DMA_FROM_DEVICE);
8375 dma_cache_sync(board->dev, scp->sense_buffer,
8376 SCSI_SENSE_BUFFERSIZE, DMA_FROM_DEVICE);
8377 return cpu_to_le32(scp->SCp.dma_handle);
8378}
8379
8380static int asc_build_req(struct asc_board *boardp, struct scsi_cmnd *scp,
8381 struct asc_scsi_q *asc_scsi_q)
8382{
8383 struct asc_dvc_var *asc_dvc = &boardp->dvc_var.asc_dvc_var;
8384 int use_sg;
8385
8386 memset(asc_scsi_q, 0, sizeof(*asc_scsi_q));
8387
8388
8389
8390
8391 asc_scsi_q->q2.srb_ptr = advansys_ptr_to_srb(asc_dvc, scp);
8392 if (asc_scsi_q->q2.srb_ptr == BAD_SRB) {
8393 scp->result = HOST_BYTE(DID_SOFT_ERROR);
8394 return ASC_ERROR;
8395 }
8396
8397
8398
8399
8400 asc_scsi_q->cdbptr = &scp->cmnd[0];
8401 asc_scsi_q->q2.cdb_len = scp->cmd_len;
8402 asc_scsi_q->q1.target_id = ASC_TID_TO_TARGET_ID(scp->device->id);
8403 asc_scsi_q->q1.target_lun = scp->device->lun;
8404 asc_scsi_q->q2.target_ix =
8405 ASC_TIDLUN_TO_IX(scp->device->id, scp->device->lun);
8406 asc_scsi_q->q1.sense_addr = advansys_get_sense_buffer_dma(scp);
8407 asc_scsi_q->q1.sense_len = SCSI_SENSE_BUFFERSIZE;
8408
8409
8410
8411
8412
8413
8414
8415
8416
8417
8418
8419
8420 if ((asc_dvc->cur_dvc_qng[scp->device->id] > 0) &&
8421 (boardp->reqcnt[scp->device->id] % 255) == 0) {
8422 asc_scsi_q->q2.tag_code = MSG_ORDERED_TAG;
8423 } else {
8424 asc_scsi_q->q2.tag_code = MSG_SIMPLE_TAG;
8425 }
8426
8427
8428 use_sg = scsi_dma_map(scp);
8429 if (use_sg != 0) {
8430 int sgcnt;
8431 struct scatterlist *slp;
8432 struct asc_sg_head *asc_sg_head;
8433
8434 if (use_sg > scp->device->host->sg_tablesize) {
8435 scmd_printk(KERN_ERR, scp, "use_sg %d > "
8436 "sg_tablesize %d\n", use_sg,
8437 scp->device->host->sg_tablesize);
8438 scsi_dma_unmap(scp);
8439 scp->result = HOST_BYTE(DID_ERROR);
8440 return ASC_ERROR;
8441 }
8442
8443 asc_sg_head = kzalloc(sizeof(asc_scsi_q->sg_head) +
8444 use_sg * sizeof(struct asc_sg_list), GFP_ATOMIC);
8445 if (!asc_sg_head) {
8446 scsi_dma_unmap(scp);
8447 scp->result = HOST_BYTE(DID_SOFT_ERROR);
8448 return ASC_ERROR;
8449 }
8450
8451 asc_scsi_q->q1.cntl |= QC_SG_HEAD;
8452 asc_scsi_q->sg_head = asc_sg_head;
8453 asc_scsi_q->q1.data_cnt = 0;
8454 asc_scsi_q->q1.data_addr = 0;
8455
8456 asc_sg_head->entry_cnt = asc_scsi_q->q1.sg_queue_cnt = use_sg;
8457 ASC_STATS_ADD(scp->device->host, xfer_elem,
8458 asc_sg_head->entry_cnt);
8459
8460
8461
8462
8463 scsi_for_each_sg(scp, slp, use_sg, sgcnt) {
8464 asc_sg_head->sg_list[sgcnt].addr =
8465 cpu_to_le32(sg_dma_address(slp));
8466 asc_sg_head->sg_list[sgcnt].bytes =
8467 cpu_to_le32(sg_dma_len(slp));
8468 ASC_STATS_ADD(scp->device->host, xfer_sect,
8469 DIV_ROUND_UP(sg_dma_len(slp), 512));
8470 }
8471 }
8472
8473 ASC_STATS(scp->device->host, xfer_cnt);
8474
8475 ASC_DBG_PRT_ASC_SCSI_Q(2, asc_scsi_q);
8476 ASC_DBG_PRT_CDB(1, scp->cmnd, scp->cmd_len);
8477
8478 return ASC_NOERROR;
8479}
8480
8481
8482
8483
8484
8485
8486
8487
8488
8489
8490
8491
8492
8493static int
8494adv_get_sglist(struct asc_board *boardp, adv_req_t *reqp, struct scsi_cmnd *scp,
8495 int use_sg)
8496{
8497 adv_sgblk_t *sgblkp;
8498 ADV_SCSI_REQ_Q *scsiqp;
8499 struct scatterlist *slp;
8500 int sg_elem_cnt;
8501 ADV_SG_BLOCK *sg_block, *prev_sg_block;
8502 ADV_PADDR sg_block_paddr;
8503 int i;
8504
8505 scsiqp = (ADV_SCSI_REQ_Q *)ADV_32BALIGN(&reqp->scsi_req_q);
8506 slp = scsi_sglist(scp);
8507 sg_elem_cnt = use_sg;
8508 prev_sg_block = NULL;
8509 reqp->sgblkp = NULL;
8510
8511 for (;;) {
8512
8513
8514
8515
8516
8517 if ((sgblkp = boardp->adv_sgblkp) == NULL) {
8518 ASC_DBG(1, "no free adv_sgblk_t\n");
8519 ASC_STATS(scp->device->host, adv_build_nosg);
8520
8521
8522
8523
8524
8525 while ((sgblkp = reqp->sgblkp) != NULL) {
8526
8527 reqp->sgblkp = sgblkp->next_sgblkp;
8528
8529
8530 sgblkp->next_sgblkp = boardp->adv_sgblkp;
8531 boardp->adv_sgblkp = sgblkp;
8532 }
8533 return ASC_BUSY;
8534 }
8535
8536
8537 boardp->adv_sgblkp = sgblkp->next_sgblkp;
8538 sgblkp->next_sgblkp = NULL;
8539
8540
8541
8542
8543
8544 sg_block = (ADV_SG_BLOCK *)ADV_8BALIGN(&sgblkp->sg_block);
8545 sg_block_paddr = virt_to_bus(sg_block);
8546
8547
8548
8549
8550
8551 if (reqp->sgblkp == NULL) {
8552
8553 reqp->sgblkp = sgblkp;
8554
8555
8556
8557
8558
8559 scsiqp->sg_list_ptr = sg_block;
8560 scsiqp->sg_real_addr = cpu_to_le32(sg_block_paddr);
8561 } else {
8562
8563 sgblkp->next_sgblkp = reqp->sgblkp;
8564 reqp->sgblkp = sgblkp;
8565
8566
8567
8568
8569
8570 prev_sg_block->sg_ptr = cpu_to_le32(sg_block_paddr);
8571 }
8572
8573 for (i = 0; i < NO_OF_SG_PER_BLOCK; i++) {
8574 sg_block->sg_list[i].sg_addr =
8575 cpu_to_le32(sg_dma_address(slp));
8576 sg_block->sg_list[i].sg_count =
8577 cpu_to_le32(sg_dma_len(slp));
8578 ASC_STATS_ADD(scp->device->host, xfer_sect,
8579 DIV_ROUND_UP(sg_dma_len(slp), 512));
8580
8581 if (--sg_elem_cnt == 0) {
8582 sg_block->sg_cnt = i + 1;
8583 sg_block->sg_ptr = 0L;
8584 return ADV_SUCCESS;
8585 }
8586 slp++;
8587 }
8588 sg_block->sg_cnt = NO_OF_SG_PER_BLOCK;
8589 prev_sg_block = sg_block;
8590 }
8591}
8592
8593
8594
8595
8596
8597
8598
8599
8600
8601
8602
8603static int
8604adv_build_req(struct asc_board *boardp, struct scsi_cmnd *scp,
8605 ADV_SCSI_REQ_Q **adv_scsiqpp)
8606{
8607 adv_req_t *reqp;
8608 ADV_SCSI_REQ_Q *scsiqp;
8609 int i;
8610 int ret;
8611 int use_sg;
8612
8613
8614
8615
8616
8617 if (boardp->adv_reqp == NULL) {
8618 ASC_DBG(1, "no free adv_req_t\n");
8619 ASC_STATS(scp->device->host, adv_build_noreq);
8620 return ASC_BUSY;
8621 } else {
8622 reqp = boardp->adv_reqp;
8623 boardp->adv_reqp = reqp->next_reqp;
8624 reqp->next_reqp = NULL;
8625 }
8626
8627
8628
8629
8630 scsiqp = (ADV_SCSI_REQ_Q *)ADV_32BALIGN(&reqp->scsi_req_q);
8631
8632
8633
8634
8635 scsiqp->cntl = scsiqp->scsi_cntl = scsiqp->done_status = 0;
8636
8637
8638
8639
8640 scsiqp->srb_ptr = ADV_VADDR_TO_U32(reqp);
8641
8642
8643
8644
8645 reqp->cmndp = scp;
8646
8647
8648
8649
8650
8651
8652 scsiqp->cdb_len = scp->cmd_len;
8653
8654 for (i = 0; i < scp->cmd_len && i < 12; i++) {
8655 scsiqp->cdb[i] = scp->cmnd[i];
8656 }
8657
8658 for (; i < scp->cmd_len; i++) {
8659 scsiqp->cdb16[i - 12] = scp->cmnd[i];
8660 }
8661
8662 scsiqp->target_id = scp->device->id;
8663 scsiqp->target_lun = scp->device->lun;
8664
8665 scsiqp->sense_addr = cpu_to_le32(virt_to_bus(&scp->sense_buffer[0]));
8666 scsiqp->sense_len = SCSI_SENSE_BUFFERSIZE;
8667
8668
8669
8670 use_sg = scsi_dma_map(scp);
8671 if (use_sg == 0) {
8672
8673 reqp->sgblkp = NULL;
8674 scsiqp->data_cnt = 0;
8675 scsiqp->vdata_addr = NULL;
8676
8677 scsiqp->data_addr = 0;
8678 scsiqp->sg_list_ptr = NULL;
8679 scsiqp->sg_real_addr = 0;
8680 } else {
8681 if (use_sg > ADV_MAX_SG_LIST) {
8682 scmd_printk(KERN_ERR, scp, "use_sg %d > "
8683 "ADV_MAX_SG_LIST %d\n", use_sg,
8684 scp->device->host->sg_tablesize);
8685 scsi_dma_unmap(scp);
8686 scp->result = HOST_BYTE(DID_ERROR);
8687
8688
8689
8690
8691
8692 reqp->next_reqp = boardp->adv_reqp;
8693 boardp->adv_reqp = reqp;
8694
8695 return ASC_ERROR;
8696 }
8697
8698 scsiqp->data_cnt = cpu_to_le32(scsi_bufflen(scp));
8699
8700 ret = adv_get_sglist(boardp, reqp, scp, use_sg);
8701 if (ret != ADV_SUCCESS) {
8702
8703
8704
8705
8706 reqp->next_reqp = boardp->adv_reqp;
8707 boardp->adv_reqp = reqp;
8708
8709 return ret;
8710 }
8711
8712 ASC_STATS_ADD(scp->device->host, xfer_elem, use_sg);
8713 }
8714
8715 ASC_STATS(scp->device->host, xfer_cnt);
8716
8717 ASC_DBG_PRT_ADV_SCSI_REQ_Q(2, scsiqp);
8718 ASC_DBG_PRT_CDB(1, scp->cmnd, scp->cmd_len);
8719
8720 *adv_scsiqpp = scsiqp;
8721
8722 return ASC_NOERROR;
8723}
8724
8725static int AscSgListToQueue(int sg_list)
8726{
8727 int n_sg_list_qs;
8728
8729 n_sg_list_qs = ((sg_list - 1) / ASC_SG_LIST_PER_Q);
8730 if (((sg_list - 1) % ASC_SG_LIST_PER_Q) != 0)
8731 n_sg_list_qs++;
8732 return n_sg_list_qs + 1;
8733}
8734
8735static uint
8736AscGetNumOfFreeQueue(ASC_DVC_VAR *asc_dvc, uchar target_ix, uchar n_qs)
8737{
8738 uint cur_used_qs;
8739 uint cur_free_qs;
8740 ASC_SCSI_BIT_ID_TYPE target_id;
8741 uchar tid_no;
8742
8743 target_id = ASC_TIX_TO_TARGET_ID(target_ix);
8744 tid_no = ASC_TIX_TO_TID(target_ix);
8745 if ((asc_dvc->unit_not_ready & target_id) ||
8746 (asc_dvc->queue_full_or_busy & target_id)) {
8747 return 0;
8748 }
8749 if (n_qs == 1) {
8750 cur_used_qs = (uint) asc_dvc->cur_total_qng +
8751 (uint) asc_dvc->last_q_shortage + (uint) ASC_MIN_FREE_Q;
8752 } else {
8753 cur_used_qs = (uint) asc_dvc->cur_total_qng +
8754 (uint) ASC_MIN_FREE_Q;
8755 }
8756 if ((uint) (cur_used_qs + n_qs) <= (uint) asc_dvc->max_total_qng) {
8757 cur_free_qs = (uint) asc_dvc->max_total_qng - cur_used_qs;
8758 if (asc_dvc->cur_dvc_qng[tid_no] >=
8759 asc_dvc->max_dvc_qng[tid_no]) {
8760 return 0;
8761 }
8762 return cur_free_qs;
8763 }
8764 if (n_qs > 1) {
8765 if ((n_qs > asc_dvc->last_q_shortage)
8766 && (n_qs <= (asc_dvc->max_total_qng - ASC_MIN_FREE_Q))) {
8767 asc_dvc->last_q_shortage = n_qs;
8768 }
8769 }
8770 return 0;
8771}
8772
8773static uchar AscAllocFreeQueue(PortAddr iop_base, uchar free_q_head)
8774{
8775 ushort q_addr;
8776 uchar next_qp;
8777 uchar q_status;
8778
8779 q_addr = ASC_QNO_TO_QADDR(free_q_head);
8780 q_status = (uchar)AscReadLramByte(iop_base,
8781 (ushort)(q_addr +
8782 ASC_SCSIQ_B_STATUS));
8783 next_qp = AscReadLramByte(iop_base, (ushort)(q_addr + ASC_SCSIQ_B_FWD));
8784 if (((q_status & QS_READY) == 0) && (next_qp != ASC_QLINK_END))
8785 return next_qp;
8786 return ASC_QLINK_END;
8787}
8788
8789static uchar
8790AscAllocMultipleFreeQueue(PortAddr iop_base, uchar free_q_head, uchar n_free_q)
8791{
8792 uchar i;
8793
8794 for (i = 0; i < n_free_q; i++) {
8795 free_q_head = AscAllocFreeQueue(iop_base, free_q_head);
8796 if (free_q_head == ASC_QLINK_END)
8797 break;
8798 }
8799 return free_q_head;
8800}
8801
8802
8803
8804
8805
8806
8807
8808
8809
8810
8811
8812static void
8813DvcPutScsiQ(PortAddr iop_base, ushort s_addr, uchar *outbuf, int words)
8814{
8815 int i;
8816
8817 ASC_DBG_PRT_HEX(2, "DvcPutScsiQ", outbuf, 2 * words);
8818 AscSetChipLramAddr(iop_base, s_addr);
8819 for (i = 0; i < 2 * words; i += 2) {
8820 if (i == 4 || i == 20) {
8821 continue;
8822 }
8823 outpw(iop_base + IOP_RAM_DATA,
8824 ((ushort)outbuf[i + 1] << 8) | outbuf[i]);
8825 }
8826}
8827
8828static int AscPutReadyQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar q_no)
8829{
8830 ushort q_addr;
8831 uchar tid_no;
8832 uchar sdtr_data;
8833 uchar syn_period_ix;
8834 uchar syn_offset;
8835 PortAddr iop_base;
8836
8837 iop_base = asc_dvc->iop_base;
8838 if (((asc_dvc->init_sdtr & scsiq->q1.target_id) != 0) &&
8839 ((asc_dvc->sdtr_done & scsiq->q1.target_id) == 0)) {
8840 tid_no = ASC_TIX_TO_TID(scsiq->q2.target_ix);
8841 sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
8842 syn_period_ix =
8843 (sdtr_data >> 4) & (asc_dvc->max_sdtr_index - 1);
8844 syn_offset = sdtr_data & ASC_SYN_MAX_OFFSET;
8845 AscMsgOutSDTR(asc_dvc,
8846 asc_dvc->sdtr_period_tbl[syn_period_ix],
8847 syn_offset);
8848 scsiq->q1.cntl |= QC_MSG_OUT;
8849 }
8850 q_addr = ASC_QNO_TO_QADDR(q_no);
8851 if ((scsiq->q1.target_id & asc_dvc->use_tagged_qng) == 0) {
8852 scsiq->q2.tag_code &= ~MSG_SIMPLE_TAG;
8853 }
8854 scsiq->q1.status = QS_FREE;
8855 AscMemWordCopyPtrToLram(iop_base,
8856 q_addr + ASC_SCSIQ_CDB_BEG,
8857 (uchar *)scsiq->cdbptr, scsiq->q2.cdb_len >> 1);
8858
8859 DvcPutScsiQ(iop_base,
8860 q_addr + ASC_SCSIQ_CPY_BEG,
8861 (uchar *)&scsiq->q1.cntl,
8862 ((sizeof(ASC_SCSIQ_1) + sizeof(ASC_SCSIQ_2)) / 2) - 1);
8863 AscWriteLramWord(iop_base,
8864 (ushort)(q_addr + (ushort)ASC_SCSIQ_B_STATUS),
8865 (ushort)(((ushort)scsiq->q1.
8866 q_no << 8) | (ushort)QS_READY));
8867 return 1;
8868}
8869
8870static int
8871AscPutReadySgListQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar q_no)
8872{
8873 int sta;
8874 int i;
8875 ASC_SG_HEAD *sg_head;
8876 ASC_SG_LIST_Q scsi_sg_q;
8877 ASC_DCNT saved_data_addr;
8878 ASC_DCNT saved_data_cnt;
8879 PortAddr iop_base;
8880 ushort sg_list_dwords;
8881 ushort sg_index;
8882 ushort sg_entry_cnt;
8883 ushort q_addr;
8884 uchar next_qp;
8885
8886 iop_base = asc_dvc->iop_base;
8887 sg_head = scsiq->sg_head;
8888 saved_data_addr = scsiq->q1.data_addr;
8889 saved_data_cnt = scsiq->q1.data_cnt;
8890 scsiq->q1.data_addr = (ASC_PADDR) sg_head->sg_list[0].addr;
8891 scsiq->q1.data_cnt = (ASC_DCNT) sg_head->sg_list[0].bytes;
8892#if CC_VERY_LONG_SG_LIST
8893
8894
8895
8896
8897
8898
8899 if (sg_head->entry_cnt > ASC_MAX_SG_LIST) {
8900
8901
8902
8903
8904
8905
8906
8907 sg_entry_cnt = ASC_MAX_SG_LIST - 1;
8908
8909
8910
8911
8912
8913 scsiq->remain_sg_entry_cnt =
8914 sg_head->entry_cnt - ASC_MAX_SG_LIST;
8915 } else {
8916#endif
8917
8918
8919
8920
8921
8922 sg_entry_cnt = sg_head->entry_cnt - 1;
8923#if CC_VERY_LONG_SG_LIST
8924 }
8925#endif
8926 if (sg_entry_cnt != 0) {
8927 scsiq->q1.cntl |= QC_SG_HEAD;
8928 q_addr = ASC_QNO_TO_QADDR(q_no);
8929 sg_index = 1;
8930 scsiq->q1.sg_queue_cnt = sg_head->queue_cnt;
8931 scsi_sg_q.sg_head_qp = q_no;
8932 scsi_sg_q.cntl = QCSG_SG_XFER_LIST;
8933 for (i = 0; i < sg_head->queue_cnt; i++) {
8934 scsi_sg_q.seq_no = i + 1;
8935 if (sg_entry_cnt > ASC_SG_LIST_PER_Q) {
8936 sg_list_dwords = (uchar)(ASC_SG_LIST_PER_Q * 2);
8937 sg_entry_cnt -= ASC_SG_LIST_PER_Q;
8938 if (i == 0) {
8939 scsi_sg_q.sg_list_cnt =
8940 ASC_SG_LIST_PER_Q;
8941 scsi_sg_q.sg_cur_list_cnt =
8942 ASC_SG_LIST_PER_Q;
8943 } else {
8944 scsi_sg_q.sg_list_cnt =
8945 ASC_SG_LIST_PER_Q - 1;
8946 scsi_sg_q.sg_cur_list_cnt =
8947 ASC_SG_LIST_PER_Q - 1;
8948 }
8949 } else {
8950#if CC_VERY_LONG_SG_LIST
8951
8952
8953
8954
8955
8956
8957 if (sg_head->entry_cnt > ASC_MAX_SG_LIST) {
8958 scsi_sg_q.cntl |= QCSG_SG_XFER_MORE;
8959 } else {
8960#endif
8961 scsi_sg_q.cntl |= QCSG_SG_XFER_END;
8962#if CC_VERY_LONG_SG_LIST
8963 }
8964#endif
8965 sg_list_dwords = sg_entry_cnt << 1;
8966 if (i == 0) {
8967 scsi_sg_q.sg_list_cnt = sg_entry_cnt;
8968 scsi_sg_q.sg_cur_list_cnt =
8969 sg_entry_cnt;
8970 } else {
8971 scsi_sg_q.sg_list_cnt =
8972 sg_entry_cnt - 1;
8973 scsi_sg_q.sg_cur_list_cnt =
8974 sg_entry_cnt - 1;
8975 }
8976 sg_entry_cnt = 0;
8977 }
8978 next_qp = AscReadLramByte(iop_base,
8979 (ushort)(q_addr +
8980 ASC_SCSIQ_B_FWD));
8981 scsi_sg_q.q_no = next_qp;
8982 q_addr = ASC_QNO_TO_QADDR(next_qp);
8983 AscMemWordCopyPtrToLram(iop_base,
8984 q_addr + ASC_SCSIQ_SGHD_CPY_BEG,
8985 (uchar *)&scsi_sg_q,
8986 sizeof(ASC_SG_LIST_Q) >> 1);
8987 AscMemDWordCopyPtrToLram(iop_base,
8988 q_addr + ASC_SGQ_LIST_BEG,
8989 (uchar *)&sg_head->
8990 sg_list[sg_index],
8991 sg_list_dwords);
8992 sg_index += ASC_SG_LIST_PER_Q;
8993 scsiq->next_sg_index = sg_index;
8994 }
8995 } else {
8996 scsiq->q1.cntl &= ~QC_SG_HEAD;
8997 }
8998 sta = AscPutReadyQueue(asc_dvc, scsiq, q_no);
8999 scsiq->q1.data_addr = saved_data_addr;
9000 scsiq->q1.data_cnt = saved_data_cnt;
9001 return (sta);
9002}
9003
9004static int
9005AscSendScsiQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq, uchar n_q_required)
9006{
9007 PortAddr iop_base;
9008 uchar free_q_head;
9009 uchar next_qp;
9010 uchar tid_no;
9011 uchar target_ix;
9012 int sta;
9013
9014 iop_base = asc_dvc->iop_base;
9015 target_ix = scsiq->q2.target_ix;
9016 tid_no = ASC_TIX_TO_TID(target_ix);
9017 sta = 0;
9018 free_q_head = (uchar)AscGetVarFreeQHead(iop_base);
9019 if (n_q_required > 1) {
9020 next_qp = AscAllocMultipleFreeQueue(iop_base, free_q_head,
9021 (uchar)n_q_required);
9022 if (next_qp != ASC_QLINK_END) {
9023 asc_dvc->last_q_shortage = 0;
9024 scsiq->sg_head->queue_cnt = n_q_required - 1;
9025 scsiq->q1.q_no = free_q_head;
9026 sta = AscPutReadySgListQueue(asc_dvc, scsiq,
9027 free_q_head);
9028 }
9029 } else if (n_q_required == 1) {
9030 next_qp = AscAllocFreeQueue(iop_base, free_q_head);
9031 if (next_qp != ASC_QLINK_END) {
9032 scsiq->q1.q_no = free_q_head;
9033 sta = AscPutReadyQueue(asc_dvc, scsiq, free_q_head);
9034 }
9035 }
9036 if (sta == 1) {
9037 AscPutVarFreeQHead(iop_base, next_qp);
9038 asc_dvc->cur_total_qng += n_q_required;
9039 asc_dvc->cur_dvc_qng[tid_no]++;
9040 }
9041 return sta;
9042}
9043
9044#define ASC_SYN_OFFSET_ONE_DISABLE_LIST 16
9045static uchar _syn_offset_one_disable_cmd[ASC_SYN_OFFSET_ONE_DISABLE_LIST] = {
9046 INQUIRY,
9047 REQUEST_SENSE,
9048 READ_CAPACITY,
9049 READ_TOC,
9050 MODE_SELECT,
9051 MODE_SENSE,
9052 MODE_SELECT_10,
9053 MODE_SENSE_10,
9054 0xFF,
9055 0xFF,
9056 0xFF,
9057 0xFF,
9058 0xFF,
9059 0xFF,
9060 0xFF,
9061 0xFF
9062};
9063
9064static int AscExeScsiQueue(ASC_DVC_VAR *asc_dvc, ASC_SCSI_Q *scsiq)
9065{
9066 PortAddr iop_base;
9067 int sta;
9068 int n_q_required;
9069 int disable_syn_offset_one_fix;
9070 int i;
9071 ASC_PADDR addr;
9072 ushort sg_entry_cnt = 0;
9073 ushort sg_entry_cnt_minus_one = 0;
9074 uchar target_ix;
9075 uchar tid_no;
9076 uchar sdtr_data;
9077 uchar extra_bytes;
9078 uchar scsi_cmd;
9079 uchar disable_cmd;
9080 ASC_SG_HEAD *sg_head;
9081 ASC_DCNT data_cnt;
9082
9083 iop_base = asc_dvc->iop_base;
9084 sg_head = scsiq->sg_head;
9085 if (asc_dvc->err_code != 0)
9086 return (ERR);
9087 scsiq->q1.q_no = 0;
9088 if ((scsiq->q2.tag_code & ASC_TAG_FLAG_EXTRA_BYTES) == 0) {
9089 scsiq->q1.extra_bytes = 0;
9090 }
9091 sta = 0;
9092 target_ix = scsiq->q2.target_ix;
9093 tid_no = ASC_TIX_TO_TID(target_ix);
9094 n_q_required = 1;
9095 if (scsiq->cdbptr[0] == REQUEST_SENSE) {
9096 if ((asc_dvc->init_sdtr & scsiq->q1.target_id) != 0) {
9097 asc_dvc->sdtr_done &= ~scsiq->q1.target_id;
9098 sdtr_data = AscGetMCodeInitSDTRAtID(iop_base, tid_no);
9099 AscMsgOutSDTR(asc_dvc,
9100 asc_dvc->
9101 sdtr_period_tbl[(sdtr_data >> 4) &
9102 (uchar)(asc_dvc->
9103 max_sdtr_index -
9104 1)],
9105 (uchar)(sdtr_data & (uchar)
9106 ASC_SYN_MAX_OFFSET));
9107 scsiq->q1.cntl |= (QC_MSG_OUT | QC_URGENT);
9108 }
9109 }
9110 if (asc_dvc->in_critical_cnt != 0) {
9111 AscSetLibErrorCode(asc_dvc, ASCQ_ERR_CRITICAL_RE_ENTRY);
9112 return (ERR);
9113 }
9114 asc_dvc->in_critical_cnt++;
9115 if ((scsiq->q1.cntl & QC_SG_HEAD) != 0) {
9116 if ((sg_entry_cnt = sg_head->entry_cnt) == 0) {
9117 asc_dvc->in_critical_cnt--;
9118 return (ERR);
9119 }
9120#if !CC_VERY_LONG_SG_LIST
9121 if (sg_entry_cnt > ASC_MAX_SG_LIST) {
9122 asc_dvc->in_critical_cnt--;
9123 return (ERR);
9124 }
9125#endif
9126 if (sg_entry_cnt == 1) {
9127 scsiq->q1.data_addr =
9128 (ADV_PADDR)sg_head->sg_list[0].addr;
9129 scsiq->q1.data_cnt =
9130 (ADV_DCNT)sg_head->sg_list[0].bytes;
9131 scsiq->q1.cntl &= ~(QC_SG_HEAD | QC_SG_SWAP_QUEUE);
9132 }
9133 sg_entry_cnt_minus_one = sg_entry_cnt - 1;
9134 }
9135 scsi_cmd = scsiq->cdbptr[0];
9136 disable_syn_offset_one_fix = FALSE;
9137 if ((asc_dvc->pci_fix_asyn_xfer & scsiq->q1.target_id) &&
9138 !(asc_dvc->pci_fix_asyn_xfer_always & scsiq->q1.target_id)) {
9139 if (scsiq->q1.cntl & QC_SG_HEAD) {
9140 data_cnt = 0;
9141 for (i = 0; i < sg_entry_cnt; i++) {
9142 data_cnt +=
9143 (ADV_DCNT)le32_to_cpu(sg_head->sg_list[i].
9144 bytes);
9145 }
9146 } else {
9147 data_cnt = le32_to_cpu(scsiq->q1.data_cnt);
9148 }
9149 if (data_cnt != 0UL) {
9150 if (data_cnt < 512UL) {
9151 disable_syn_offset_one_fix = TRUE;
9152 } else {
9153 for (i = 0; i < ASC_SYN_OFFSET_ONE_DISABLE_LIST;
9154 i++) {
9155 disable_cmd =
9156 _syn_offset_one_disable_cmd[i];
9157 if (disable_cmd == 0xFF) {
9158 break;
9159 }
9160 if (scsi_cmd == disable_cmd) {
9161 disable_syn_offset_one_fix =
9162 TRUE;
9163 break;
9164 }
9165 }
9166 }
9167 }
9168 }
9169 if (disable_syn_offset_one_fix) {
9170 scsiq->q2.tag_code &= ~MSG_SIMPLE_TAG;
9171 scsiq->q2.tag_code |= (ASC_TAG_FLAG_DISABLE_ASYN_USE_SYN_FIX |
9172 ASC_TAG_FLAG_DISABLE_DISCONNECT);
9173 } else {
9174 scsiq->q2.tag_code &= 0x27;
9175 }
9176 if ((scsiq->q1.cntl & QC_SG_HEAD) != 0) {
9177 if (asc_dvc->bug_fix_cntl) {
9178 if (asc_dvc->bug_fix_cntl & ASC_BUG_FIX_IF_NOT_DWB) {
9179 if ((scsi_cmd == READ_6) ||
9180 (scsi_cmd == READ_10)) {
9181 addr =
9182 (ADV_PADDR)le32_to_cpu(sg_head->
9183 sg_list
9184 [sg_entry_cnt_minus_one].
9185 addr) +
9186 (ADV_DCNT)le32_to_cpu(sg_head->
9187 sg_list
9188 [sg_entry_cnt_minus_one].
9189 bytes);
9190 extra_bytes =
9191 (uchar)((ushort)addr & 0x0003);
9192 if ((extra_bytes != 0)
9193 &&
9194 ((scsiq->q2.
9195 tag_code &
9196 ASC_TAG_FLAG_EXTRA_BYTES)
9197 == 0)) {
9198 scsiq->q2.tag_code |=
9199 ASC_TAG_FLAG_EXTRA_BYTES;
9200 scsiq->q1.extra_bytes =
9201 extra_bytes;
9202 data_cnt =
9203 le32_to_cpu(sg_head->
9204 sg_list
9205 [sg_entry_cnt_minus_one].
9206 bytes);
9207 data_cnt -=
9208 (ASC_DCNT) extra_bytes;
9209 sg_head->
9210 sg_list
9211 [sg_entry_cnt_minus_one].
9212 bytes =
9213 cpu_to_le32(data_cnt);
9214 }
9215 }
9216 }
9217 }
9218 sg_head->entry_to_copy = sg_head->entry_cnt;
9219#if CC_VERY_LONG_SG_LIST
9220
9221
9222
9223
9224
9225 if (sg_entry_cnt > ASC_MAX_SG_LIST) {
9226 sg_entry_cnt = ASC_MAX_SG_LIST;
9227 }
9228#endif
9229 n_q_required = AscSgListToQueue(sg_entry_cnt);
9230 if ((AscGetNumOfFreeQueue(asc_dvc, target_ix, n_q_required) >=
9231 (uint) n_q_required)
9232 || ((scsiq->q1.cntl & QC_URGENT) != 0)) {
9233 if ((sta =
9234 AscSendScsiQueue(asc_dvc, scsiq,
9235 n_q_required)) == 1) {
9236 asc_dvc->in_critical_cnt--;
9237 return (sta);
9238 }
9239 }
9240 } else {
9241 if (asc_dvc->bug_fix_cntl) {
9242 if (asc_dvc->bug_fix_cntl & ASC_BUG_FIX_IF_NOT_DWB) {
9243 if ((scsi_cmd == READ_6) ||
9244 (scsi_cmd == READ_10)) {
9245 addr =
9246 le32_to_cpu(scsiq->q1.data_addr) +
9247 le32_to_cpu(scsiq->q1.data_cnt);
9248 extra_bytes =
9249 (uchar)((ushort)addr & 0x0003);
9250 if ((extra_bytes != 0)
9251 &&
9252 ((scsiq->q2.
9253 tag_code &
9254 ASC_TAG_FLAG_EXTRA_BYTES)
9255 == 0)) {
9256 data_cnt =
9257 le32_to_cpu(scsiq->q1.
9258 data_cnt);
9259 if (((ushort)data_cnt & 0x01FF)
9260 == 0) {
9261 scsiq->q2.tag_code |=
9262 ASC_TAG_FLAG_EXTRA_BYTES;
9263 data_cnt -= (ASC_DCNT)
9264 extra_bytes;
9265 scsiq->q1.data_cnt =
9266 cpu_to_le32
9267 (data_cnt);
9268 scsiq->q1.extra_bytes =
9269 extra_bytes;
9270 }
9271 }
9272 }
9273 }
9274 }
9275 n_q_required = 1;
9276 if ((AscGetNumOfFreeQueue(asc_dvc, target_ix, 1) >= 1) ||
9277 ((scsiq->q1.cntl & QC_URGENT) != 0)) {
9278 if ((sta = AscSendScsiQueue(asc_dvc, scsiq,
9279 n_q_required)) == 1) {
9280 asc_dvc->in_critical_cnt--;
9281 return (sta);
9282 }
9283 }
9284 }
9285 asc_dvc->in_critical_cnt--;
9286 return (sta);
9287}
9288
9289
9290
9291
9292
9293
9294
9295
9296
9297
9298
9299
9300
9301
9302
9303
9304
9305
9306
9307
9308
9309
9310static int AdvExeScsiQueue(ADV_DVC_VAR *asc_dvc, ADV_SCSI_REQ_Q *scsiq)
9311{
9312 AdvPortAddr iop_base;
9313 ADV_PADDR req_paddr;
9314 ADV_CARR_T *new_carrp;
9315
9316
9317
9318
9319 if (scsiq->target_id > ADV_MAX_TID) {
9320 scsiq->host_status = QHSTA_M_INVALID_DEVICE;
9321 scsiq->done_status = QD_WITH_ERROR;
9322 return ADV_ERROR;
9323 }
9324
9325 iop_base = asc_dvc->iop_base;
9326
9327
9328
9329
9330
9331 if ((new_carrp = asc_dvc->carr_freelist) == NULL) {
9332 return ADV_BUSY;
9333 }
9334 asc_dvc->carr_freelist = (ADV_CARR_T *)
9335 ADV_U32_TO_VADDR(le32_to_cpu(new_carrp->next_vpa));
9336 asc_dvc->carr_pending_cnt++;
9337
9338
9339
9340
9341
9342
9343 new_carrp->next_vpa = cpu_to_le32(ASC_CQ_STOPPER);
9344
9345
9346
9347
9348 scsiq->a_flag &= ~ADV_SCSIQ_DONE;
9349
9350 req_paddr = virt_to_bus(scsiq);
9351 BUG_ON(req_paddr & 31);
9352
9353 req_paddr = cpu_to_le32(req_paddr);
9354
9355
9356 scsiq->scsiq_ptr = cpu_to_le32(ADV_VADDR_TO_U32(scsiq));
9357 scsiq->scsiq_rptr = req_paddr;
9358
9359 scsiq->carr_va = cpu_to_le32(ADV_VADDR_TO_U32(asc_dvc->icq_sp));
9360
9361
9362
9363
9364 scsiq->carr_pa = asc_dvc->icq_sp->carr_pa;
9365
9366
9367
9368
9369
9370
9371 asc_dvc->icq_sp->areq_vpa = req_paddr;
9372
9373
9374
9375
9376
9377
9378 asc_dvc->icq_sp->next_vpa = new_carrp->carr_pa;
9379
9380
9381
9382
9383 asc_dvc->icq_sp = new_carrp;
9384
9385 if (asc_dvc->chip_type == ADV_CHIP_ASC3550 ||
9386 asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
9387
9388
9389
9390 AdvWriteByteRegister(iop_base, IOPB_TICKLE, ADV_TICKLE_A);
9391 if (asc_dvc->chip_type == ADV_CHIP_ASC3550) {
9392
9393
9394
9395
9396
9397 AdvWriteByteRegister(iop_base, IOPB_TICKLE,
9398 ADV_TICKLE_NOP);
9399 }
9400 } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
9401
9402
9403
9404
9405 AdvWriteDWordRegister(iop_base, IOPDW_COMMA,
9406 le32_to_cpu(new_carrp->carr_pa));
9407 }
9408
9409 return ADV_SUCCESS;
9410}
9411
9412
9413
9414
9415static int asc_execute_scsi_cmnd(struct scsi_cmnd *scp)
9416{
9417 int ret, err_code;
9418 struct asc_board *boardp = shost_priv(scp->device->host);
9419
9420 ASC_DBG(1, "scp 0x%p\n", scp);
9421
9422 if (ASC_NARROW_BOARD(boardp)) {
9423 ASC_DVC_VAR *asc_dvc = &boardp->dvc_var.asc_dvc_var;
9424 struct asc_scsi_q asc_scsi_q;
9425
9426
9427 ret = asc_build_req(boardp, scp, &asc_scsi_q);
9428 if (ret == ASC_ERROR) {
9429 ASC_STATS(scp->device->host, build_error);
9430 return ASC_ERROR;
9431 }
9432
9433 ret = AscExeScsiQueue(asc_dvc, &asc_scsi_q);
9434 kfree(asc_scsi_q.sg_head);
9435 err_code = asc_dvc->err_code;
9436 } else {
9437 ADV_DVC_VAR *adv_dvc = &boardp->dvc_var.adv_dvc_var;
9438 ADV_SCSI_REQ_Q *adv_scsiqp;
9439
9440 switch (adv_build_req(boardp, scp, &adv_scsiqp)) {
9441 case ASC_NOERROR:
9442 ASC_DBG(3, "adv_build_req ASC_NOERROR\n");
9443 break;
9444 case ASC_BUSY:
9445 ASC_DBG(1, "adv_build_req ASC_BUSY\n");
9446
9447
9448
9449
9450
9451
9452 return ASC_BUSY;
9453 case ASC_ERROR:
9454 default:
9455 ASC_DBG(1, "adv_build_req ASC_ERROR\n");
9456 ASC_STATS(scp->device->host, build_error);
9457 return ASC_ERROR;
9458 }
9459
9460 ret = AdvExeScsiQueue(adv_dvc, adv_scsiqp);
9461 err_code = adv_dvc->err_code;
9462 }
9463
9464 switch (ret) {
9465 case ASC_NOERROR:
9466 ASC_STATS(scp->device->host, exe_noerror);
9467
9468
9469
9470
9471 boardp->reqcnt[scp->device->id]++;
9472 ASC_DBG(1, "ExeScsiQueue() ASC_NOERROR\n");
9473 break;
9474 case ASC_BUSY:
9475 ASC_STATS(scp->device->host, exe_busy);
9476 break;
9477 case ASC_ERROR:
9478 scmd_printk(KERN_ERR, scp, "ExeScsiQueue() ASC_ERROR, "
9479 "err_code 0x%x\n", err_code);
9480 ASC_STATS(scp->device->host, exe_error);
9481 scp->result = HOST_BYTE(DID_ERROR);
9482 break;
9483 default:
9484 scmd_printk(KERN_ERR, scp, "ExeScsiQueue() unknown, "
9485 "err_code 0x%x\n", err_code);
9486 ASC_STATS(scp->device->host, exe_unknown);
9487 scp->result = HOST_BYTE(DID_ERROR);
9488 break;
9489 }
9490
9491 ASC_DBG(1, "end\n");
9492 return ret;
9493}
9494
9495
9496
9497
9498
9499
9500
9501static int
9502advansys_queuecommand_lck(struct scsi_cmnd *scp, void (*done)(struct scsi_cmnd *))
9503{
9504 struct Scsi_Host *shost = scp->device->host;
9505 int asc_res, result = 0;
9506
9507 ASC_STATS(shost, queuecommand);
9508 scp->scsi_done = done;
9509
9510 asc_res = asc_execute_scsi_cmnd(scp);
9511
9512 switch (asc_res) {
9513 case ASC_NOERROR:
9514 break;
9515 case ASC_BUSY:
9516 result = SCSI_MLQUEUE_HOST_BUSY;
9517 break;
9518 case ASC_ERROR:
9519 default:
9520 asc_scsi_done(scp);
9521 break;
9522 }
9523
9524 return result;
9525}
9526
9527static DEF_SCSI_QCMD(advansys_queuecommand)
9528
9529static ushort __devinit AscGetEisaChipCfg(PortAddr iop_base)
9530{
9531 PortAddr eisa_cfg_iop = (PortAddr) ASC_GET_EISA_SLOT(iop_base) |
9532 (PortAddr) (ASC_EISA_CFG_IOP_MASK);
9533 return inpw(eisa_cfg_iop);
9534}
9535
9536
9537
9538
9539
9540static unsigned short __devinit
9541AscGetChipBiosAddress(PortAddr iop_base, unsigned short bus_type)
9542{
9543 unsigned short cfg_lsw;
9544 unsigned short bios_addr;
9545
9546
9547
9548
9549
9550
9551 if (bus_type & ASC_IS_PCI)
9552 return 0;
9553
9554 if ((bus_type & ASC_IS_EISA) != 0) {
9555 cfg_lsw = AscGetEisaChipCfg(iop_base);
9556 cfg_lsw &= 0x000F;
9557 bios_addr = ASC_BIOS_MIN_ADDR + cfg_lsw * ASC_BIOS_BANK_SIZE;
9558 return bios_addr;
9559 }
9560
9561 cfg_lsw = AscGetChipCfgLsw(iop_base);
9562
9563
9564
9565
9566 if (bus_type == ASC_IS_ISAPNP)
9567 cfg_lsw &= 0x7FFF;
9568 bios_addr = ASC_BIOS_MIN_ADDR + (cfg_lsw >> 12) * ASC_BIOS_BANK_SIZE;
9569 return bios_addr;
9570}
9571
9572static uchar __devinit AscSetChipScsiID(PortAddr iop_base, uchar new_host_id)
9573{
9574 ushort cfg_lsw;
9575
9576 if (AscGetChipScsiID(iop_base) == new_host_id) {
9577 return (new_host_id);
9578 }
9579 cfg_lsw = AscGetChipCfgLsw(iop_base);
9580 cfg_lsw &= 0xF8FF;
9581 cfg_lsw |= (ushort)((new_host_id & ASC_MAX_TID) << 8);
9582 AscSetChipCfgLsw(iop_base, cfg_lsw);
9583 return (AscGetChipScsiID(iop_base));
9584}
9585
9586static unsigned char __devinit AscGetChipScsiCtrl(PortAddr iop_base)
9587{
9588 unsigned char sc;
9589
9590 AscSetBank(iop_base, 1);
9591 sc = inp(iop_base + IOP_REG_SC);
9592 AscSetBank(iop_base, 0);
9593 return sc;
9594}
9595
9596static unsigned char __devinit
9597AscGetChipVersion(PortAddr iop_base, unsigned short bus_type)
9598{
9599 if (bus_type & ASC_IS_EISA) {
9600 PortAddr eisa_iop;
9601 unsigned char revision;
9602 eisa_iop = (PortAddr) ASC_GET_EISA_SLOT(iop_base) |
9603 (PortAddr) ASC_EISA_REV_IOP_MASK;
9604 revision = inp(eisa_iop);
9605 return ASC_CHIP_MIN_VER_EISA - 1 + revision;
9606 }
9607 return AscGetChipVerNo(iop_base);
9608}
9609
9610#ifdef CONFIG_ISA
9611static void __devinit AscEnableIsaDma(uchar dma_channel)
9612{
9613 if (dma_channel < 4) {
9614 outp(0x000B, (ushort)(0xC0 | dma_channel));
9615 outp(0x000A, dma_channel);
9616 } else if (dma_channel < 8) {
9617 outp(0x00D6, (ushort)(0xC0 | (dma_channel - 4)));
9618 outp(0x00D4, (ushort)(dma_channel - 4));
9619 }
9620}
9621#endif
9622
9623static int AscStopQueueExe(PortAddr iop_base)
9624{
9625 int count = 0;
9626
9627 if (AscReadLramByte(iop_base, ASCV_STOP_CODE_B) == 0) {
9628 AscWriteLramByte(iop_base, ASCV_STOP_CODE_B,
9629 ASC_STOP_REQ_RISC_STOP);
9630 do {
9631 if (AscReadLramByte(iop_base, ASCV_STOP_CODE_B) &
9632 ASC_STOP_ACK_RISC_STOP) {
9633 return (1);
9634 }
9635 mdelay(100);
9636 } while (count++ < 20);
9637 }
9638 return (0);
9639}
9640
9641static ASC_DCNT __devinit AscGetMaxDmaCount(ushort bus_type)
9642{
9643 if (bus_type & ASC_IS_ISA)
9644 return ASC_MAX_ISA_DMA_COUNT;
9645 else if (bus_type & (ASC_IS_EISA | ASC_IS_VL))
9646 return ASC_MAX_VL_DMA_COUNT;
9647 return ASC_MAX_PCI_DMA_COUNT;
9648}
9649
9650#ifdef CONFIG_ISA
9651static ushort __devinit AscGetIsaDmaChannel(PortAddr iop_base)
9652{
9653 ushort channel;
9654
9655 channel = AscGetChipCfgLsw(iop_base) & 0x0003;
9656 if (channel == 0x03)
9657 return (0);
9658 else if (channel == 0x00)
9659 return (7);
9660 return (channel + 4);
9661}
9662
9663static ushort __devinit AscSetIsaDmaChannel(PortAddr iop_base, ushort dma_channel)
9664{
9665 ushort cfg_lsw;
9666 uchar value;
9667
9668 if ((dma_channel >= 5) && (dma_channel <= 7)) {
9669 if (dma_channel == 7)
9670 value = 0x00;
9671 else
9672 value = dma_channel - 4;
9673 cfg_lsw = AscGetChipCfgLsw(iop_base) & 0xFFFC;
9674 cfg_lsw |= value;
9675 AscSetChipCfgLsw(iop_base, cfg_lsw);
9676 return (AscGetIsaDmaChannel(iop_base));
9677 }
9678 return 0;
9679}
9680
9681static uchar __devinit AscGetIsaDmaSpeed(PortAddr iop_base)
9682{
9683 uchar speed_value;
9684
9685 AscSetBank(iop_base, 1);
9686 speed_value = AscReadChipDmaSpeed(iop_base);
9687 speed_value &= 0x07;
9688 AscSetBank(iop_base, 0);
9689 return speed_value;
9690}
9691
9692static uchar __devinit AscSetIsaDmaSpeed(PortAddr iop_base, uchar speed_value)
9693{
9694 speed_value &= 0x07;
9695 AscSetBank(iop_base, 1);
9696 AscWriteChipDmaSpeed(iop_base, speed_value);
9697 AscSetBank(iop_base, 0);
9698 return AscGetIsaDmaSpeed(iop_base);
9699}
9700#endif
9701
9702static ushort __devinit AscInitAscDvcVar(ASC_DVC_VAR *asc_dvc)
9703{
9704 int i;
9705 PortAddr iop_base;
9706 ushort warn_code;
9707 uchar chip_version;
9708
9709 iop_base = asc_dvc->iop_base;
9710 warn_code = 0;
9711 asc_dvc->err_code = 0;
9712 if ((asc_dvc->bus_type &
9713 (ASC_IS_ISA | ASC_IS_PCI | ASC_IS_EISA | ASC_IS_VL)) == 0) {
9714 asc_dvc->err_code |= ASC_IERR_NO_BUS_TYPE;
9715 }
9716 AscSetChipControl(iop_base, CC_HALT);
9717 AscSetChipStatus(iop_base, 0);
9718 asc_dvc->bug_fix_cntl = 0;
9719 asc_dvc->pci_fix_asyn_xfer = 0;
9720 asc_dvc->pci_fix_asyn_xfer_always = 0;
9721
9722 asc_dvc->sdtr_done = 0;
9723 asc_dvc->cur_total_qng = 0;
9724 asc_dvc->is_in_int = 0;
9725 asc_dvc->in_critical_cnt = 0;
9726 asc_dvc->last_q_shortage = 0;
9727 asc_dvc->use_tagged_qng = 0;
9728 asc_dvc->no_scam = 0;
9729 asc_dvc->unit_not_ready = 0;
9730 asc_dvc->queue_full_or_busy = 0;
9731 asc_dvc->redo_scam = 0;
9732 asc_dvc->res2 = 0;
9733 asc_dvc->min_sdtr_index = 0;
9734 asc_dvc->cfg->can_tagged_qng = 0;
9735 asc_dvc->cfg->cmd_qng_enabled = 0;
9736 asc_dvc->dvc_cntl = ASC_DEF_DVC_CNTL;
9737 asc_dvc->init_sdtr = 0;
9738 asc_dvc->max_total_qng = ASC_DEF_MAX_TOTAL_QNG;
9739 asc_dvc->scsi_reset_wait = 3;
9740 asc_dvc->start_motor = ASC_SCSI_WIDTH_BIT_SET;
9741 asc_dvc->max_dma_count = AscGetMaxDmaCount(asc_dvc->bus_type);
9742 asc_dvc->cfg->sdtr_enable = ASC_SCSI_WIDTH_BIT_SET;
9743 asc_dvc->cfg->disc_enable = ASC_SCSI_WIDTH_BIT_SET;
9744 asc_dvc->cfg->chip_scsi_id = ASC_DEF_CHIP_SCSI_ID;
9745 chip_version = AscGetChipVersion(iop_base, asc_dvc->bus_type);
9746 asc_dvc->cfg->chip_version = chip_version;
9747 asc_dvc->sdtr_period_tbl = asc_syn_xfer_period;
9748 asc_dvc->max_sdtr_index = 7;
9749 if ((asc_dvc->bus_type & ASC_IS_PCI) &&
9750 (chip_version >= ASC_CHIP_VER_PCI_ULTRA_3150)) {
9751 asc_dvc->bus_type = ASC_IS_PCI_ULTRA;
9752 asc_dvc->sdtr_period_tbl = asc_syn_ultra_xfer_period;
9753 asc_dvc->max_sdtr_index = 15;
9754 if (chip_version == ASC_CHIP_VER_PCI_ULTRA_3150) {
9755 AscSetExtraControl(iop_base,
9756 (SEC_ACTIVE_NEGATE | SEC_SLEW_RATE));
9757 } else if (chip_version >= ASC_CHIP_VER_PCI_ULTRA_3050) {
9758 AscSetExtraControl(iop_base,
9759 (SEC_ACTIVE_NEGATE |
9760 SEC_ENABLE_FILTER));
9761 }
9762 }
9763 if (asc_dvc->bus_type == ASC_IS_PCI) {
9764 AscSetExtraControl(iop_base,
9765 (SEC_ACTIVE_NEGATE | SEC_SLEW_RATE));
9766 }
9767
9768 asc_dvc->cfg->isa_dma_speed = ASC_DEF_ISA_DMA_SPEED;
9769#ifdef CONFIG_ISA
9770 if ((asc_dvc->bus_type & ASC_IS_ISA) != 0) {
9771 if (chip_version >= ASC_CHIP_MIN_VER_ISA_PNP) {
9772 AscSetChipIFC(iop_base, IFC_INIT_DEFAULT);
9773 asc_dvc->bus_type = ASC_IS_ISAPNP;
9774 }
9775 asc_dvc->cfg->isa_dma_channel =
9776 (uchar)AscGetIsaDmaChannel(iop_base);
9777 }
9778#endif
9779 for (i = 0; i <= ASC_MAX_TID; i++) {
9780 asc_dvc->cur_dvc_qng[i] = 0;
9781 asc_dvc->max_dvc_qng[i] = ASC_MAX_SCSI1_QNG;
9782 asc_dvc->scsiq_busy_head[i] = (ASC_SCSI_Q *)0L;
9783 asc_dvc->scsiq_busy_tail[i] = (ASC_SCSI_Q *)0L;
9784 asc_dvc->cfg->max_tag_qng[i] = ASC_MAX_INRAM_TAG_QNG;
9785 }
9786 return warn_code;
9787}
9788
9789static int __devinit AscWriteEEPCmdReg(PortAddr iop_base, uchar cmd_reg)
9790{
9791 int retry;
9792
9793 for (retry = 0; retry < ASC_EEP_MAX_RETRY; retry++) {
9794 unsigned char read_back;
9795 AscSetChipEEPCmd(iop_base, cmd_reg);
9796 mdelay(1);
9797 read_back = AscGetChipEEPCmd(iop_base);
9798 if (read_back == cmd_reg)
9799 return 1;
9800 }
9801 return 0;
9802}
9803
9804static void __devinit AscWaitEEPRead(void)
9805{
9806 mdelay(1);
9807}
9808
9809static ushort __devinit AscReadEEPWord(PortAddr iop_base, uchar addr)
9810{
9811 ushort read_wval;
9812 uchar cmd_reg;
9813
9814 AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_DISABLE);
9815 AscWaitEEPRead();
9816 cmd_reg = addr | ASC_EEP_CMD_READ;
9817 AscWriteEEPCmdReg(iop_base, cmd_reg);
9818 AscWaitEEPRead();
9819 read_wval = AscGetChipEEPData(iop_base);
9820 AscWaitEEPRead();
9821 return read_wval;
9822}
9823
9824static ushort __devinit
9825AscGetEEPConfig(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
9826{
9827 ushort wval;
9828 ushort sum;
9829 ushort *wbuf;
9830 int cfg_beg;
9831 int cfg_end;
9832 int uchar_end_in_config = ASC_EEP_MAX_DVC_ADDR - 2;
9833 int s_addr;
9834
9835 wbuf = (ushort *)cfg_buf;
9836 sum = 0;
9837
9838 for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
9839 *wbuf = AscReadEEPWord(iop_base, (uchar)s_addr);
9840 sum += *wbuf;
9841 }
9842 if (bus_type & ASC_IS_VL) {
9843 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
9844 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
9845 } else {
9846 cfg_beg = ASC_EEP_DVC_CFG_BEG;
9847 cfg_end = ASC_EEP_MAX_DVC_ADDR;
9848 }
9849 for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
9850 wval = AscReadEEPWord(iop_base, (uchar)s_addr);
9851 if (s_addr <= uchar_end_in_config) {
9852
9853
9854
9855
9856 *wbuf = le16_to_cpu(wval);
9857 } else {
9858
9859 *wbuf = wval;
9860 }
9861 sum += wval;
9862 }
9863
9864
9865
9866
9867 *wbuf = AscReadEEPWord(iop_base, (uchar)s_addr);
9868 return sum;
9869}
9870
9871static int __devinit AscTestExternalLram(ASC_DVC_VAR *asc_dvc)
9872{
9873 PortAddr iop_base;
9874 ushort q_addr;
9875 ushort saved_word;
9876 int sta;
9877
9878 iop_base = asc_dvc->iop_base;
9879 sta = 0;
9880 q_addr = ASC_QNO_TO_QADDR(241);
9881 saved_word = AscReadLramWord(iop_base, q_addr);
9882 AscSetChipLramAddr(iop_base, q_addr);
9883 AscSetChipLramData(iop_base, 0x55AA);
9884 mdelay(10);
9885 AscSetChipLramAddr(iop_base, q_addr);
9886 if (AscGetChipLramData(iop_base) == 0x55AA) {
9887 sta = 1;
9888 AscWriteLramWord(iop_base, q_addr, saved_word);
9889 }
9890 return (sta);
9891}
9892
9893static void __devinit AscWaitEEPWrite(void)
9894{
9895 mdelay(20);
9896}
9897
9898static int __devinit AscWriteEEPDataReg(PortAddr iop_base, ushort data_reg)
9899{
9900 ushort read_back;
9901 int retry;
9902
9903 retry = 0;
9904 while (TRUE) {
9905 AscSetChipEEPData(iop_base, data_reg);
9906 mdelay(1);
9907 read_back = AscGetChipEEPData(iop_base);
9908 if (read_back == data_reg) {
9909 return (1);
9910 }
9911 if (retry++ > ASC_EEP_MAX_RETRY) {
9912 return (0);
9913 }
9914 }
9915}
9916
9917static ushort __devinit
9918AscWriteEEPWord(PortAddr iop_base, uchar addr, ushort word_val)
9919{
9920 ushort read_wval;
9921
9922 read_wval = AscReadEEPWord(iop_base, addr);
9923 if (read_wval != word_val) {
9924 AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_ABLE);
9925 AscWaitEEPRead();
9926 AscWriteEEPDataReg(iop_base, word_val);
9927 AscWaitEEPRead();
9928 AscWriteEEPCmdReg(iop_base,
9929 (uchar)((uchar)ASC_EEP_CMD_WRITE | addr));
9930 AscWaitEEPWrite();
9931 AscWriteEEPCmdReg(iop_base, ASC_EEP_CMD_WRITE_DISABLE);
9932 AscWaitEEPRead();
9933 return (AscReadEEPWord(iop_base, addr));
9934 }
9935 return (read_wval);
9936}
9937
9938static int __devinit
9939AscSetEEPConfigOnce(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
9940{
9941 int n_error;
9942 ushort *wbuf;
9943 ushort word;
9944 ushort sum;
9945 int s_addr;
9946 int cfg_beg;
9947 int cfg_end;
9948 int uchar_end_in_config = ASC_EEP_MAX_DVC_ADDR - 2;
9949
9950 wbuf = (ushort *)cfg_buf;
9951 n_error = 0;
9952 sum = 0;
9953
9954 for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
9955 sum += *wbuf;
9956 if (*wbuf != AscWriteEEPWord(iop_base, (uchar)s_addr, *wbuf)) {
9957 n_error++;
9958 }
9959 }
9960 if (bus_type & ASC_IS_VL) {
9961 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
9962 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
9963 } else {
9964 cfg_beg = ASC_EEP_DVC_CFG_BEG;
9965 cfg_end = ASC_EEP_MAX_DVC_ADDR;
9966 }
9967 for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
9968 if (s_addr <= uchar_end_in_config) {
9969
9970
9971
9972
9973 word = cpu_to_le16(*wbuf);
9974 if (word !=
9975 AscWriteEEPWord(iop_base, (uchar)s_addr, word)) {
9976 n_error++;
9977 }
9978 } else {
9979
9980 if (*wbuf !=
9981 AscWriteEEPWord(iop_base, (uchar)s_addr, *wbuf)) {
9982 n_error++;
9983 }
9984 }
9985 sum += *wbuf;
9986 }
9987
9988 *wbuf = sum;
9989 if (sum != AscWriteEEPWord(iop_base, (uchar)s_addr, sum)) {
9990 n_error++;
9991 }
9992
9993
9994 wbuf = (ushort *)cfg_buf;
9995
9996
9997
9998 for (s_addr = 0; s_addr < 2; s_addr++, wbuf++) {
9999 if (*wbuf != AscReadEEPWord(iop_base, (uchar)s_addr)) {
10000 n_error++;
10001 }
10002 }
10003 if (bus_type & ASC_IS_VL) {
10004 cfg_beg = ASC_EEP_DVC_CFG_BEG_VL;
10005 cfg_end = ASC_EEP_MAX_DVC_ADDR_VL;
10006 } else {
10007 cfg_beg = ASC_EEP_DVC_CFG_BEG;
10008 cfg_end = ASC_EEP_MAX_DVC_ADDR;
10009 }
10010 for (s_addr = cfg_beg; s_addr <= (cfg_end - 1); s_addr++, wbuf++) {
10011 if (s_addr <= uchar_end_in_config) {
10012
10013
10014
10015
10016 word =
10017 le16_to_cpu(AscReadEEPWord
10018 (iop_base, (uchar)s_addr));
10019 } else {
10020
10021 word = AscReadEEPWord(iop_base, (uchar)s_addr);
10022 }
10023 if (*wbuf != word) {
10024 n_error++;
10025 }
10026 }
10027
10028 if (AscReadEEPWord(iop_base, (uchar)s_addr) != sum) {
10029 n_error++;
10030 }
10031 return n_error;
10032}
10033
10034static int __devinit
10035AscSetEEPConfig(PortAddr iop_base, ASCEEP_CONFIG *cfg_buf, ushort bus_type)
10036{
10037 int retry;
10038 int n_error;
10039
10040 retry = 0;
10041 while (TRUE) {
10042 if ((n_error = AscSetEEPConfigOnce(iop_base, cfg_buf,
10043 bus_type)) == 0) {
10044 break;
10045 }
10046 if (++retry > ASC_EEP_MAX_RETRY) {
10047 break;
10048 }
10049 }
10050 return n_error;
10051}
10052
10053static ushort __devinit AscInitFromEEP(ASC_DVC_VAR *asc_dvc)
10054{
10055 ASCEEP_CONFIG eep_config_buf;
10056 ASCEEP_CONFIG *eep_config;
10057 PortAddr iop_base;
10058 ushort chksum;
10059 ushort warn_code;
10060 ushort cfg_msw, cfg_lsw;
10061 int i;
10062 int write_eep = 0;
10063
10064 iop_base = asc_dvc->iop_base;
10065 warn_code = 0;
10066 AscWriteLramWord(iop_base, ASCV_HALTCODE_W, 0x00FE);
10067 AscStopQueueExe(iop_base);
10068 if ((AscStopChip(iop_base) == FALSE) ||
10069 (AscGetChipScsiCtrl(iop_base) != 0)) {
10070 asc_dvc->init_state |= ASC_INIT_RESET_SCSI_DONE;
10071 AscResetChipAndScsiBus(asc_dvc);
10072 mdelay(asc_dvc->scsi_reset_wait * 1000);
10073 }
10074 if (AscIsChipHalted(iop_base) == FALSE) {
10075 asc_dvc->err_code |= ASC_IERR_START_STOP_CHIP;
10076 return (warn_code);
10077 }
10078 AscSetPCAddr(iop_base, ASC_MCODE_START_ADDR);
10079 if (AscGetPCAddr(iop_base) != ASC_MCODE_START_ADDR) {
10080 asc_dvc->err_code |= ASC_IERR_SET_PC_ADDR;
10081 return (warn_code);
10082 }
10083 eep_config = (ASCEEP_CONFIG *)&eep_config_buf;
10084 cfg_msw = AscGetChipCfgMsw(iop_base);
10085 cfg_lsw = AscGetChipCfgLsw(iop_base);
10086 if ((cfg_msw & ASC_CFG_MSW_CLR_MASK) != 0) {
10087 cfg_msw &= ~ASC_CFG_MSW_CLR_MASK;
10088 warn_code |= ASC_WARN_CFG_MSW_RECOVER;
10089 AscSetChipCfgMsw(iop_base, cfg_msw);
10090 }
10091 chksum = AscGetEEPConfig(iop_base, eep_config, asc_dvc->bus_type);
10092 ASC_DBG(1, "chksum 0x%x\n", chksum);
10093 if (chksum == 0) {
10094 chksum = 0xaa55;
10095 }
10096 if (AscGetChipStatus(iop_base) & CSW_AUTO_CONFIG) {
10097 warn_code |= ASC_WARN_AUTO_CONFIG;
10098 if (asc_dvc->cfg->chip_version == 3) {
10099 if (eep_config->cfg_lsw != cfg_lsw) {
10100 warn_code |= ASC_WARN_EEPROM_RECOVER;
10101 eep_config->cfg_lsw =
10102 AscGetChipCfgLsw(iop_base);
10103 }
10104 if (eep_config->cfg_msw != cfg_msw) {
10105 warn_code |= ASC_WARN_EEPROM_RECOVER;
10106 eep_config->cfg_msw =
10107 AscGetChipCfgMsw(iop_base);
10108 }
10109 }
10110 }
10111 eep_config->cfg_msw &= ~ASC_CFG_MSW_CLR_MASK;
10112 eep_config->cfg_lsw |= ASC_CFG0_HOST_INT_ON;
10113 ASC_DBG(1, "eep_config->chksum 0x%x\n", eep_config->chksum);
10114 if (chksum != eep_config->chksum) {
10115 if (AscGetChipVersion(iop_base, asc_dvc->bus_type) ==
10116 ASC_CHIP_VER_PCI_ULTRA_3050) {
10117 ASC_DBG(1, "chksum error ignored; EEPROM-less board\n");
10118 eep_config->init_sdtr = 0xFF;
10119 eep_config->disc_enable = 0xFF;
10120 eep_config->start_motor = 0xFF;
10121 eep_config->use_cmd_qng = 0;
10122 eep_config->max_total_qng = 0xF0;
10123 eep_config->max_tag_qng = 0x20;
10124 eep_config->cntl = 0xBFFF;
10125 ASC_EEP_SET_CHIP_ID(eep_config, 7);
10126 eep_config->no_scam = 0;
10127 eep_config->adapter_info[0] = 0;
10128 eep_config->adapter_info[1] = 0;
10129 eep_config->adapter_info[2] = 0;
10130 eep_config->adapter_info[3] = 0;
10131 eep_config->adapter_info[4] = 0;
10132
10133 eep_config->adapter_info[5] = 0xBB;
10134 } else {
10135 ASC_PRINT
10136 ("AscInitFromEEP: EEPROM checksum error; Will try to re-write EEPROM.\n");
10137 write_eep = 1;
10138 warn_code |= ASC_WARN_EEPROM_CHKSUM;
10139 }
10140 }
10141 asc_dvc->cfg->sdtr_enable = eep_config->init_sdtr;
10142 asc_dvc->cfg->disc_enable = eep_config->disc_enable;
10143 asc_dvc->cfg->cmd_qng_enabled = eep_config->use_cmd_qng;
10144 asc_dvc->cfg->isa_dma_speed = ASC_EEP_GET_DMA_SPD(eep_config);
10145 asc_dvc->start_motor = eep_config->start_motor;
10146 asc_dvc->dvc_cntl = eep_config->cntl;
10147 asc_dvc->no_scam = eep_config->no_scam;
10148 asc_dvc->cfg->adapter_info[0] = eep_config->adapter_info[0];
10149 asc_dvc->cfg->adapter_info[1] = eep_config->adapter_info[1];
10150 asc_dvc->cfg->adapter_info[2] = eep_config->adapter_info[2];
10151 asc_dvc->cfg->adapter_info[3] = eep_config->adapter_info[3];
10152 asc_dvc->cfg->adapter_info[4] = eep_config->adapter_info[4];
10153 asc_dvc->cfg->adapter_info[5] = eep_config->adapter_info[5];
10154 if (!AscTestExternalLram(asc_dvc)) {
10155 if (((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) ==
10156 ASC_IS_PCI_ULTRA)) {
10157 eep_config->max_total_qng =
10158 ASC_MAX_PCI_ULTRA_INRAM_TOTAL_QNG;
10159 eep_config->max_tag_qng =
10160 ASC_MAX_PCI_ULTRA_INRAM_TAG_QNG;
10161 } else {
10162 eep_config->cfg_msw |= 0x0800;
10163 cfg_msw |= 0x0800;
10164 AscSetChipCfgMsw(iop_base, cfg_msw);
10165 eep_config->max_total_qng = ASC_MAX_PCI_INRAM_TOTAL_QNG;
10166 eep_config->max_tag_qng = ASC_MAX_INRAM_TAG_QNG;
10167 }
10168 } else {
10169 }
10170 if (eep_config->max_total_qng < ASC_MIN_TOTAL_QNG) {
10171 eep_config->max_total_qng = ASC_MIN_TOTAL_QNG;
10172 }
10173 if (eep_config->max_total_qng > ASC_MAX_TOTAL_QNG) {
10174 eep_config->max_total_qng = ASC_MAX_TOTAL_QNG;
10175 }
10176 if (eep_config->max_tag_qng > eep_config->max_total_qng) {
10177 eep_config->max_tag_qng = eep_config->max_total_qng;
10178 }
10179 if (eep_config->max_tag_qng < ASC_MIN_TAG_Q_PER_DVC) {
10180 eep_config->max_tag_qng = ASC_MIN_TAG_Q_PER_DVC;
10181 }
10182 asc_dvc->max_total_qng = eep_config->max_total_qng;
10183 if ((eep_config->use_cmd_qng & eep_config->disc_enable) !=
10184 eep_config->use_cmd_qng) {
10185 eep_config->disc_enable = eep_config->use_cmd_qng;
10186 warn_code |= ASC_WARN_CMD_QNG_CONFLICT;
10187 }
10188 ASC_EEP_SET_CHIP_ID(eep_config,
10189 ASC_EEP_GET_CHIP_ID(eep_config) & ASC_MAX_TID);
10190 asc_dvc->cfg->chip_scsi_id = ASC_EEP_GET_CHIP_ID(eep_config);
10191 if (((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) == ASC_IS_PCI_ULTRA) &&
10192 !(asc_dvc->dvc_cntl & ASC_CNTL_SDTR_ENABLE_ULTRA)) {
10193 asc_dvc->min_sdtr_index = ASC_SDTR_ULTRA_PCI_10MB_INDEX;
10194 }
10195
10196 for (i = 0; i <= ASC_MAX_TID; i++) {
10197 asc_dvc->dos_int13_table[i] = eep_config->dos_int13_table[i];
10198 asc_dvc->cfg->max_tag_qng[i] = eep_config->max_tag_qng;
10199 asc_dvc->cfg->sdtr_period_offset[i] =
10200 (uchar)(ASC_DEF_SDTR_OFFSET |
10201 (asc_dvc->min_sdtr_index << 4));
10202 }
10203 eep_config->cfg_msw = AscGetChipCfgMsw(iop_base);
10204 if (write_eep) {
10205 if ((i = AscSetEEPConfig(iop_base, eep_config,
10206 asc_dvc->bus_type)) != 0) {
10207 ASC_PRINT1
10208 ("AscInitFromEEP: Failed to re-write EEPROM with %d errors.\n",
10209 i);
10210 } else {
10211 ASC_PRINT
10212 ("AscInitFromEEP: Successfully re-wrote EEPROM.\n");
10213 }
10214 }
10215 return (warn_code);
10216}
10217
10218static int __devinit AscInitGetConfig(struct Scsi_Host *shost)
10219{
10220 struct asc_board *board = shost_priv(shost);
10221 ASC_DVC_VAR *asc_dvc = &board->dvc_var.asc_dvc_var;
10222 unsigned short warn_code = 0;
10223
10224 asc_dvc->init_state = ASC_INIT_STATE_BEG_GET_CFG;
10225 if (asc_dvc->err_code != 0)
10226 return asc_dvc->err_code;
10227
10228 if (AscFindSignature(asc_dvc->iop_base)) {
10229 warn_code |= AscInitAscDvcVar(asc_dvc);
10230 warn_code |= AscInitFromEEP(asc_dvc);
10231 asc_dvc->init_state |= ASC_INIT_STATE_END_GET_CFG;
10232 if (asc_dvc->scsi_reset_wait > ASC_MAX_SCSI_RESET_WAIT)
10233 asc_dvc->scsi_reset_wait = ASC_MAX_SCSI_RESET_WAIT;
10234 } else {
10235 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
10236 }
10237
10238 switch (warn_code) {
10239 case 0:
10240 break;
10241 case ASC_WARN_IO_PORT_ROTATE:
10242 shost_printk(KERN_WARNING, shost, "I/O port address "
10243 "modified\n");
10244 break;
10245 case ASC_WARN_AUTO_CONFIG:
10246 shost_printk(KERN_WARNING, shost, "I/O port increment switch "
10247 "enabled\n");
10248 break;
10249 case ASC_WARN_EEPROM_CHKSUM:
10250 shost_printk(KERN_WARNING, shost, "EEPROM checksum error\n");
10251 break;
10252 case ASC_WARN_IRQ_MODIFIED:
10253 shost_printk(KERN_WARNING, shost, "IRQ modified\n");
10254 break;
10255 case ASC_WARN_CMD_QNG_CONFLICT:
10256 shost_printk(KERN_WARNING, shost, "tag queuing enabled w/o "
10257 "disconnects\n");
10258 break;
10259 default:
10260 shost_printk(KERN_WARNING, shost, "unknown warning: 0x%x\n",
10261 warn_code);
10262 break;
10263 }
10264
10265 if (asc_dvc->err_code != 0)
10266 shost_printk(KERN_ERR, shost, "error 0x%x at init_state "
10267 "0x%x\n", asc_dvc->err_code, asc_dvc->init_state);
10268
10269 return asc_dvc->err_code;
10270}
10271
10272static int __devinit AscInitSetConfig(struct pci_dev *pdev, struct Scsi_Host *shost)
10273{
10274 struct asc_board *board = shost_priv(shost);
10275 ASC_DVC_VAR *asc_dvc = &board->dvc_var.asc_dvc_var;
10276 PortAddr iop_base = asc_dvc->iop_base;
10277 unsigned short cfg_msw;
10278 unsigned short warn_code = 0;
10279
10280 asc_dvc->init_state |= ASC_INIT_STATE_BEG_SET_CFG;
10281 if (asc_dvc->err_code != 0)
10282 return asc_dvc->err_code;
10283 if (!AscFindSignature(asc_dvc->iop_base)) {
10284 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
10285 return asc_dvc->err_code;
10286 }
10287
10288 cfg_msw = AscGetChipCfgMsw(iop_base);
10289 if ((cfg_msw & ASC_CFG_MSW_CLR_MASK) != 0) {
10290 cfg_msw &= ~ASC_CFG_MSW_CLR_MASK;
10291 warn_code |= ASC_WARN_CFG_MSW_RECOVER;
10292 AscSetChipCfgMsw(iop_base, cfg_msw);
10293 }
10294 if ((asc_dvc->cfg->cmd_qng_enabled & asc_dvc->cfg->disc_enable) !=
10295 asc_dvc->cfg->cmd_qng_enabled) {
10296 asc_dvc->cfg->disc_enable = asc_dvc->cfg->cmd_qng_enabled;
10297 warn_code |= ASC_WARN_CMD_QNG_CONFLICT;
10298 }
10299 if (AscGetChipStatus(iop_base) & CSW_AUTO_CONFIG) {
10300 warn_code |= ASC_WARN_AUTO_CONFIG;
10301 }
10302#ifdef CONFIG_PCI
10303 if (asc_dvc->bus_type & ASC_IS_PCI) {
10304 cfg_msw &= 0xFFC0;
10305 AscSetChipCfgMsw(iop_base, cfg_msw);
10306 if ((asc_dvc->bus_type & ASC_IS_PCI_ULTRA) == ASC_IS_PCI_ULTRA) {
10307 } else {
10308 if ((pdev->device == PCI_DEVICE_ID_ASP_1200A) ||
10309 (pdev->device == PCI_DEVICE_ID_ASP_ABP940)) {
10310 asc_dvc->bug_fix_cntl |= ASC_BUG_FIX_IF_NOT_DWB;
10311 asc_dvc->bug_fix_cntl |=
10312 ASC_BUG_FIX_ASYN_USE_SYN;
10313 }
10314 }
10315 } else
10316#endif
10317 if (asc_dvc->bus_type == ASC_IS_ISAPNP) {
10318 if (AscGetChipVersion(iop_base, asc_dvc->bus_type)
10319 == ASC_CHIP_VER_ASYN_BUG) {
10320 asc_dvc->bug_fix_cntl |= ASC_BUG_FIX_ASYN_USE_SYN;
10321 }
10322 }
10323 if (AscSetChipScsiID(iop_base, asc_dvc->cfg->chip_scsi_id) !=
10324 asc_dvc->cfg->chip_scsi_id) {
10325 asc_dvc->err_code |= ASC_IERR_SET_SCSI_ID;
10326 }
10327#ifdef CONFIG_ISA
10328 if (asc_dvc->bus_type & ASC_IS_ISA) {
10329 AscSetIsaDmaChannel(iop_base, asc_dvc->cfg->isa_dma_channel);
10330 AscSetIsaDmaSpeed(iop_base, asc_dvc->cfg->isa_dma_speed);
10331 }
10332#endif
10333
10334 asc_dvc->init_state |= ASC_INIT_STATE_END_SET_CFG;
10335
10336 switch (warn_code) {
10337 case 0:
10338 break;
10339 case ASC_WARN_IO_PORT_ROTATE:
10340 shost_printk(KERN_WARNING, shost, "I/O port address "
10341 "modified\n");
10342 break;
10343 case ASC_WARN_AUTO_CONFIG:
10344 shost_printk(KERN_WARNING, shost, "I/O port increment switch "
10345 "enabled\n");
10346 break;
10347 case ASC_WARN_EEPROM_CHKSUM:
10348 shost_printk(KERN_WARNING, shost, "EEPROM checksum error\n");
10349 break;
10350 case ASC_WARN_IRQ_MODIFIED:
10351 shost_printk(KERN_WARNING, shost, "IRQ modified\n");
10352 break;
10353 case ASC_WARN_CMD_QNG_CONFLICT:
10354 shost_printk(KERN_WARNING, shost, "tag queuing w/o "
10355 "disconnects\n");
10356 break;
10357 default:
10358 shost_printk(KERN_WARNING, shost, "unknown warning: 0x%x\n",
10359 warn_code);
10360 break;
10361 }
10362
10363 if (asc_dvc->err_code != 0)
10364 shost_printk(KERN_ERR, shost, "error 0x%x at init_state "
10365 "0x%x\n", asc_dvc->err_code, asc_dvc->init_state);
10366
10367 return asc_dvc->err_code;
10368}
10369
10370
10371
10372
10373
10374
10375
10376
10377
10378
10379
10380
10381
10382
10383
10384
10385
10386static ADVEEP_3550_CONFIG Default_3550_EEPROM_Config __devinitdata = {
10387 ADV_EEPROM_BIOS_ENABLE,
10388 0x0000,
10389 0xFFFF,
10390 0xFFFF,
10391 0xFFFF,
10392 0xFFFF,
10393 0xFFFF,
10394 0xFFFF,
10395 0,
10396 7,
10397 0,
10398 3,
10399 0,
10400 0,
10401 0,
10402 0xFFE7,
10403 0xFFFF,
10404 0,
10405 ASC_DEF_MAX_HOST_QNG,
10406 ASC_DEF_MAX_DVC_QNG,
10407 0,
10408 0,
10409 0,
10410 0,
10411 0,
10412 0,
10413 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
10414 ,
10415 0,
10416 0,
10417 0,
10418 0,
10419 0,
10420 0,
10421 0
10422};
10423
10424static ADVEEP_3550_CONFIG ADVEEP_3550_Config_Field_IsChar __devinitdata = {
10425 0,
10426 0,
10427 0,
10428 0,
10429 0,
10430 0,
10431 0,
10432 0,
10433 0,
10434 1,
10435 1,
10436 1,
10437 1,
10438 1,
10439 1,
10440 0,
10441 0,
10442 0,
10443 1,
10444 1,
10445 0,
10446 0,
10447 0,
10448 0,
10449 0,
10450 0,
10451 {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
10452 ,
10453 0,
10454 0,
10455 0,
10456 0,
10457 0,
10458 0,
10459 0
10460};
10461
10462static ADVEEP_38C0800_CONFIG Default_38C0800_EEPROM_Config __devinitdata = {
10463 ADV_EEPROM_BIOS_ENABLE,
10464 0x0000,
10465 0xFFFF,
10466 0xFFFF,
10467 0x4444,
10468 0xFFFF,
10469 0xFFFF,
10470 0xFFFF,
10471 0,
10472 7,
10473 0,
10474 3,
10475 0,
10476 0,
10477 0,
10478 0xFFE7,
10479 0x4444,
10480 0x4444,
10481 ASC_DEF_MAX_HOST_QNG,
10482 ASC_DEF_MAX_DVC_QNG,
10483 0,
10484 0x4444,
10485 0,
10486 0,
10487 0,
10488 0,
10489 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
10490 ,
10491 0,
10492 0,
10493 0,
10494 0,
10495 0,
10496 0,
10497 0,
10498 0,
10499 0,
10500 0,
10501 0,
10502 0,
10503 0,
10504 0,
10505 0,
10506 0,
10507 0,
10508 0,
10509 0,
10510 0,
10511 0,
10512 0,
10513 0,
10514 0,
10515 0,
10516 0,
10517 0,
10518 0,
10519 PCI_VENDOR_ID_ASP,
10520 PCI_DEVICE_ID_38C0800_REV1,
10521 0,
10522 0,
10523 0,
10524 0
10525};
10526
10527static ADVEEP_38C0800_CONFIG ADVEEP_38C0800_Config_Field_IsChar __devinitdata = {
10528 0,
10529 0,
10530 0,
10531 0,
10532 0,
10533 0,
10534 0,
10535 0,
10536 0,
10537 1,
10538 1,
10539 1,
10540 1,
10541 1,
10542 1,
10543 0,
10544 0,
10545 0,
10546 1,
10547 1,
10548 0,
10549 0,
10550 0,
10551 0,
10552 0,
10553 0,
10554 {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
10555 ,
10556 0,
10557 0,
10558 0,
10559 0,
10560 0,
10561 0,
10562 0,
10563 0,
10564 0,
10565 0,
10566 0,
10567 0,
10568 0,
10569 0,
10570 0,
10571 0,
10572 0,
10573 0,
10574 0,
10575 0,
10576 0,
10577 0,
10578 0,
10579 0,
10580 0,
10581 0,
10582 0,
10583 0,
10584 0,
10585 0,
10586 0,
10587 0,
10588 0,
10589 0
10590};
10591
10592static ADVEEP_38C1600_CONFIG Default_38C1600_EEPROM_Config __devinitdata = {
10593 ADV_EEPROM_BIOS_ENABLE,
10594 0x0000,
10595 0xFFFF,
10596 0xFFFF,
10597 0x5555,
10598 0xFFFF,
10599 0xFFFF,
10600 0xFFFF,
10601 0,
10602 7,
10603 0,
10604 3,
10605 0,
10606 0,
10607 0,
10608 0xFFE7,
10609 0x5555,
10610 0x5555,
10611 ASC_DEF_MAX_HOST_QNG,
10612 ASC_DEF_MAX_DVC_QNG,
10613 0,
10614 0x5555,
10615 0,
10616 0,
10617 0,
10618 0,
10619 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
10620 ,
10621 0,
10622 0,
10623 0,
10624 0,
10625 0,
10626 0,
10627 0,
10628 0,
10629 0,
10630 0,
10631 0,
10632 0,
10633 0,
10634 0,
10635 0,
10636 0,
10637 0,
10638 0,
10639 0,
10640 0,
10641 0,
10642 0,
10643 0,
10644 0,
10645 0,
10646 0,
10647 0,
10648 0,
10649 PCI_VENDOR_ID_ASP,
10650 PCI_DEVICE_ID_38C1600_REV1,
10651 0,
10652 0,
10653 0,
10654 0
10655};
10656
10657static ADVEEP_38C1600_CONFIG ADVEEP_38C1600_Config_Field_IsChar __devinitdata = {
10658 0,
10659 0,
10660 0,
10661 0,
10662 0,
10663 0,
10664 0,
10665 0,
10666 0,
10667 1,
10668 1,
10669 1,
10670 1,
10671 1,
10672 1,
10673 0,
10674 0,
10675 0,
10676 1,
10677 1,
10678 0,
10679 0,
10680 0,
10681 0,
10682 0,
10683 0,
10684 {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
10685 ,
10686 0,
10687 0,
10688 0,
10689 0,
10690 0,
10691 0,
10692 0,
10693 0,
10694 0,
10695 0,
10696 0,
10697 0,
10698 0,
10699 0,
10700 0,
10701 0,
10702 0,
10703 0,
10704 0,
10705 0,
10706 0,
10707 0,
10708 0,
10709 0,
10710 0,
10711 0,
10712 0,
10713 0,
10714 0,
10715 0,
10716 0,
10717 0,
10718 0,
10719 0
10720};
10721
10722#ifdef CONFIG_PCI
10723
10724
10725
10726static void __devinit AdvWaitEEPCmd(AdvPortAddr iop_base)
10727{
10728 int eep_delay_ms;
10729
10730 for (eep_delay_ms = 0; eep_delay_ms < ADV_EEP_DELAY_MS; eep_delay_ms++) {
10731 if (AdvReadWordRegister(iop_base, IOPW_EE_CMD) &
10732 ASC_EEP_CMD_DONE) {
10733 break;
10734 }
10735 mdelay(1);
10736 }
10737 if ((AdvReadWordRegister(iop_base, IOPW_EE_CMD) & ASC_EEP_CMD_DONE) ==
10738 0)
10739 BUG();
10740}
10741
10742
10743
10744
10745static ushort __devinit AdvReadEEPWord(AdvPortAddr iop_base, int eep_word_addr)
10746{
10747 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10748 ASC_EEP_CMD_READ | eep_word_addr);
10749 AdvWaitEEPCmd(iop_base);
10750 return AdvReadWordRegister(iop_base, IOPW_EE_DATA);
10751}
10752
10753
10754
10755
10756static void __devinit
10757AdvSet3550EEPConfig(AdvPortAddr iop_base, ADVEEP_3550_CONFIG *cfg_buf)
10758{
10759 ushort *wbuf;
10760 ushort addr, chksum;
10761 ushort *charfields;
10762
10763 wbuf = (ushort *)cfg_buf;
10764 charfields = (ushort *)&ADVEEP_3550_Config_Field_IsChar;
10765 chksum = 0;
10766
10767 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
10768 AdvWaitEEPCmd(iop_base);
10769
10770
10771
10772
10773 for (addr = ADV_EEP_DVC_CFG_BEGIN;
10774 addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
10775 ushort word;
10776
10777 if (*charfields++) {
10778 word = cpu_to_le16(*wbuf);
10779 } else {
10780 word = *wbuf;
10781 }
10782 chksum += *wbuf;
10783 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10784 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10785 ASC_EEP_CMD_WRITE | addr);
10786 AdvWaitEEPCmd(iop_base);
10787 mdelay(ADV_EEP_DELAY_MS);
10788 }
10789
10790
10791
10792
10793 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
10794 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
10795 AdvWaitEEPCmd(iop_base);
10796 wbuf++;
10797 charfields++;
10798
10799
10800
10801
10802 for (addr = ADV_EEP_DVC_CTL_BEGIN;
10803 addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
10804 ushort word;
10805
10806 if (*charfields++) {
10807 word = cpu_to_le16(*wbuf);
10808 } else {
10809 word = *wbuf;
10810 }
10811 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10812 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10813 ASC_EEP_CMD_WRITE | addr);
10814 AdvWaitEEPCmd(iop_base);
10815 }
10816 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
10817 AdvWaitEEPCmd(iop_base);
10818}
10819
10820
10821
10822
10823static void __devinit
10824AdvSet38C0800EEPConfig(AdvPortAddr iop_base, ADVEEP_38C0800_CONFIG *cfg_buf)
10825{
10826 ushort *wbuf;
10827 ushort *charfields;
10828 ushort addr, chksum;
10829
10830 wbuf = (ushort *)cfg_buf;
10831 charfields = (ushort *)&ADVEEP_38C0800_Config_Field_IsChar;
10832 chksum = 0;
10833
10834 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
10835 AdvWaitEEPCmd(iop_base);
10836
10837
10838
10839
10840 for (addr = ADV_EEP_DVC_CFG_BEGIN;
10841 addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
10842 ushort word;
10843
10844 if (*charfields++) {
10845 word = cpu_to_le16(*wbuf);
10846 } else {
10847 word = *wbuf;
10848 }
10849 chksum += *wbuf;
10850 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10851 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10852 ASC_EEP_CMD_WRITE | addr);
10853 AdvWaitEEPCmd(iop_base);
10854 mdelay(ADV_EEP_DELAY_MS);
10855 }
10856
10857
10858
10859
10860 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
10861 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
10862 AdvWaitEEPCmd(iop_base);
10863 wbuf++;
10864 charfields++;
10865
10866
10867
10868
10869 for (addr = ADV_EEP_DVC_CTL_BEGIN;
10870 addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
10871 ushort word;
10872
10873 if (*charfields++) {
10874 word = cpu_to_le16(*wbuf);
10875 } else {
10876 word = *wbuf;
10877 }
10878 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10879 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10880 ASC_EEP_CMD_WRITE | addr);
10881 AdvWaitEEPCmd(iop_base);
10882 }
10883 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
10884 AdvWaitEEPCmd(iop_base);
10885}
10886
10887
10888
10889
10890static void __devinit
10891AdvSet38C1600EEPConfig(AdvPortAddr iop_base, ADVEEP_38C1600_CONFIG *cfg_buf)
10892{
10893 ushort *wbuf;
10894 ushort *charfields;
10895 ushort addr, chksum;
10896
10897 wbuf = (ushort *)cfg_buf;
10898 charfields = (ushort *)&ADVEEP_38C1600_Config_Field_IsChar;
10899 chksum = 0;
10900
10901 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_ABLE);
10902 AdvWaitEEPCmd(iop_base);
10903
10904
10905
10906
10907 for (addr = ADV_EEP_DVC_CFG_BEGIN;
10908 addr < ADV_EEP_DVC_CFG_END; addr++, wbuf++) {
10909 ushort word;
10910
10911 if (*charfields++) {
10912 word = cpu_to_le16(*wbuf);
10913 } else {
10914 word = *wbuf;
10915 }
10916 chksum += *wbuf;
10917 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10918 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10919 ASC_EEP_CMD_WRITE | addr);
10920 AdvWaitEEPCmd(iop_base);
10921 mdelay(ADV_EEP_DELAY_MS);
10922 }
10923
10924
10925
10926
10927 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, chksum);
10928 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE | addr);
10929 AdvWaitEEPCmd(iop_base);
10930 wbuf++;
10931 charfields++;
10932
10933
10934
10935
10936 for (addr = ADV_EEP_DVC_CTL_BEGIN;
10937 addr < ADV_EEP_MAX_WORD_ADDR; addr++, wbuf++) {
10938 ushort word;
10939
10940 if (*charfields++) {
10941 word = cpu_to_le16(*wbuf);
10942 } else {
10943 word = *wbuf;
10944 }
10945 AdvWriteWordRegister(iop_base, IOPW_EE_DATA, word);
10946 AdvWriteWordRegister(iop_base, IOPW_EE_CMD,
10947 ASC_EEP_CMD_WRITE | addr);
10948 AdvWaitEEPCmd(iop_base);
10949 }
10950 AdvWriteWordRegister(iop_base, IOPW_EE_CMD, ASC_EEP_CMD_WRITE_DISABLE);
10951 AdvWaitEEPCmd(iop_base);
10952}
10953
10954
10955
10956
10957
10958
10959static ushort __devinit
10960AdvGet3550EEPConfig(AdvPortAddr iop_base, ADVEEP_3550_CONFIG *cfg_buf)
10961{
10962 ushort wval, chksum;
10963 ushort *wbuf;
10964 int eep_addr;
10965 ushort *charfields;
10966
10967 charfields = (ushort *)&ADVEEP_3550_Config_Field_IsChar;
10968 wbuf = (ushort *)cfg_buf;
10969 chksum = 0;
10970
10971 for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
10972 eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
10973 wval = AdvReadEEPWord(iop_base, eep_addr);
10974 chksum += wval;
10975 if (*charfields++) {
10976 *wbuf = le16_to_cpu(wval);
10977 } else {
10978 *wbuf = wval;
10979 }
10980 }
10981
10982 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
10983 wbuf++;
10984 charfields++;
10985
10986
10987 for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
10988 eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
10989 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
10990 if (*charfields++) {
10991 *wbuf = le16_to_cpu(*wbuf);
10992 }
10993 }
10994 return chksum;
10995}
10996
10997
10998
10999
11000
11001
11002static ushort __devinit
11003AdvGet38C0800EEPConfig(AdvPortAddr iop_base, ADVEEP_38C0800_CONFIG *cfg_buf)
11004{
11005 ushort wval, chksum;
11006 ushort *wbuf;
11007 int eep_addr;
11008 ushort *charfields;
11009
11010 charfields = (ushort *)&ADVEEP_38C0800_Config_Field_IsChar;
11011 wbuf = (ushort *)cfg_buf;
11012 chksum = 0;
11013
11014 for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
11015 eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
11016 wval = AdvReadEEPWord(iop_base, eep_addr);
11017 chksum += wval;
11018 if (*charfields++) {
11019 *wbuf = le16_to_cpu(wval);
11020 } else {
11021 *wbuf = wval;
11022 }
11023 }
11024
11025 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
11026 wbuf++;
11027 charfields++;
11028
11029
11030 for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
11031 eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
11032 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
11033 if (*charfields++) {
11034 *wbuf = le16_to_cpu(*wbuf);
11035 }
11036 }
11037 return chksum;
11038}
11039
11040
11041
11042
11043
11044
11045static ushort __devinit
11046AdvGet38C1600EEPConfig(AdvPortAddr iop_base, ADVEEP_38C1600_CONFIG *cfg_buf)
11047{
11048 ushort wval, chksum;
11049 ushort *wbuf;
11050 int eep_addr;
11051 ushort *charfields;
11052
11053 charfields = (ushort *)&ADVEEP_38C1600_Config_Field_IsChar;
11054 wbuf = (ushort *)cfg_buf;
11055 chksum = 0;
11056
11057 for (eep_addr = ADV_EEP_DVC_CFG_BEGIN;
11058 eep_addr < ADV_EEP_DVC_CFG_END; eep_addr++, wbuf++) {
11059 wval = AdvReadEEPWord(iop_base, eep_addr);
11060 chksum += wval;
11061 if (*charfields++) {
11062 *wbuf = le16_to_cpu(wval);
11063 } else {
11064 *wbuf = wval;
11065 }
11066 }
11067
11068 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
11069 wbuf++;
11070 charfields++;
11071
11072
11073 for (eep_addr = ADV_EEP_DVC_CTL_BEGIN;
11074 eep_addr < ADV_EEP_MAX_WORD_ADDR; eep_addr++, wbuf++) {
11075 *wbuf = AdvReadEEPWord(iop_base, eep_addr);
11076 if (*charfields++) {
11077 *wbuf = le16_to_cpu(*wbuf);
11078 }
11079 }
11080 return chksum;
11081}
11082
11083
11084
11085
11086
11087
11088
11089
11090
11091
11092
11093
11094
11095static int __devinit AdvInitFrom3550EEP(ADV_DVC_VAR *asc_dvc)
11096{
11097 AdvPortAddr iop_base;
11098 ushort warn_code;
11099 ADVEEP_3550_CONFIG eep_config;
11100
11101 iop_base = asc_dvc->iop_base;
11102
11103 warn_code = 0;
11104
11105
11106
11107
11108
11109
11110 if (AdvGet3550EEPConfig(iop_base, &eep_config) != eep_config.check_sum) {
11111 warn_code |= ASC_WARN_EEPROM_CHKSUM;
11112
11113
11114
11115
11116 memcpy(&eep_config, &Default_3550_EEPROM_Config,
11117 sizeof(ADVEEP_3550_CONFIG));
11118
11119
11120
11121
11122
11123 eep_config.serial_number_word3 =
11124 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
11125
11126 eep_config.serial_number_word2 =
11127 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
11128
11129 eep_config.serial_number_word1 =
11130 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
11131
11132 AdvSet3550EEPConfig(iop_base, &eep_config);
11133 }
11134
11135
11136
11137
11138
11139
11140 asc_dvc->wdtr_able = eep_config.wdtr_able;
11141 asc_dvc->sdtr_able = eep_config.sdtr_able;
11142 asc_dvc->ultra_able = eep_config.ultra_able;
11143 asc_dvc->tagqng_able = eep_config.tagqng_able;
11144 asc_dvc->cfg->disc_enable = eep_config.disc_enable;
11145 asc_dvc->max_host_qng = eep_config.max_host_qng;
11146 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11147 asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ADV_MAX_TID);
11148 asc_dvc->start_motor = eep_config.start_motor;
11149 asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
11150 asc_dvc->bios_ctrl = eep_config.bios_ctrl;
11151 asc_dvc->no_scam = eep_config.scam_tolerant;
11152 asc_dvc->cfg->serial1 = eep_config.serial_number_word1;
11153 asc_dvc->cfg->serial2 = eep_config.serial_number_word2;
11154 asc_dvc->cfg->serial3 = eep_config.serial_number_word3;
11155
11156
11157
11158
11159
11160 if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
11161 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11162 } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
11163
11164 if (eep_config.max_host_qng == 0) {
11165 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11166 } else {
11167 eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
11168 }
11169 }
11170
11171 if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
11172 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11173 } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
11174
11175 if (eep_config.max_dvc_qng == 0) {
11176 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11177 } else {
11178 eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
11179 }
11180 }
11181
11182
11183
11184
11185
11186 if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
11187 eep_config.max_dvc_qng = eep_config.max_host_qng;
11188 }
11189
11190
11191
11192
11193
11194 asc_dvc->max_host_qng = eep_config.max_host_qng;
11195 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11196
11197
11198
11199
11200
11201
11202
11203
11204
11205 if (eep_config.termination == 0) {
11206 asc_dvc->cfg->termination = 0;
11207 } else {
11208
11209 if (eep_config.termination == 1) {
11210 asc_dvc->cfg->termination = TERM_CTL_SEL;
11211
11212
11213 } else if (eep_config.termination == 2) {
11214 asc_dvc->cfg->termination = TERM_CTL_SEL | TERM_CTL_H;
11215
11216
11217 } else if (eep_config.termination == 3) {
11218 asc_dvc->cfg->termination =
11219 TERM_CTL_SEL | TERM_CTL_H | TERM_CTL_L;
11220 } else {
11221
11222
11223
11224
11225 asc_dvc->cfg->termination = 0;
11226 warn_code |= ASC_WARN_EEPROM_TERMINATION;
11227 }
11228 }
11229
11230 return warn_code;
11231}
11232
11233
11234
11235
11236
11237
11238
11239
11240
11241
11242
11243
11244
11245static int __devinit AdvInitFrom38C0800EEP(ADV_DVC_VAR *asc_dvc)
11246{
11247 AdvPortAddr iop_base;
11248 ushort warn_code;
11249 ADVEEP_38C0800_CONFIG eep_config;
11250 uchar tid, termination;
11251 ushort sdtr_speed = 0;
11252
11253 iop_base = asc_dvc->iop_base;
11254
11255 warn_code = 0;
11256
11257
11258
11259
11260
11261
11262 if (AdvGet38C0800EEPConfig(iop_base, &eep_config) !=
11263 eep_config.check_sum) {
11264 warn_code |= ASC_WARN_EEPROM_CHKSUM;
11265
11266
11267
11268
11269 memcpy(&eep_config, &Default_38C0800_EEPROM_Config,
11270 sizeof(ADVEEP_38C0800_CONFIG));
11271
11272
11273
11274
11275
11276 eep_config.serial_number_word3 =
11277 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
11278
11279 eep_config.serial_number_word2 =
11280 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
11281
11282 eep_config.serial_number_word1 =
11283 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
11284
11285 AdvSet38C0800EEPConfig(iop_base, &eep_config);
11286 }
11287
11288
11289
11290
11291
11292
11293 asc_dvc->wdtr_able = eep_config.wdtr_able;
11294 asc_dvc->sdtr_speed1 = eep_config.sdtr_speed1;
11295 asc_dvc->sdtr_speed2 = eep_config.sdtr_speed2;
11296 asc_dvc->sdtr_speed3 = eep_config.sdtr_speed3;
11297 asc_dvc->sdtr_speed4 = eep_config.sdtr_speed4;
11298 asc_dvc->tagqng_able = eep_config.tagqng_able;
11299 asc_dvc->cfg->disc_enable = eep_config.disc_enable;
11300 asc_dvc->max_host_qng = eep_config.max_host_qng;
11301 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11302 asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ADV_MAX_TID);
11303 asc_dvc->start_motor = eep_config.start_motor;
11304 asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
11305 asc_dvc->bios_ctrl = eep_config.bios_ctrl;
11306 asc_dvc->no_scam = eep_config.scam_tolerant;
11307 asc_dvc->cfg->serial1 = eep_config.serial_number_word1;
11308 asc_dvc->cfg->serial2 = eep_config.serial_number_word2;
11309 asc_dvc->cfg->serial3 = eep_config.serial_number_word3;
11310
11311
11312
11313
11314
11315 asc_dvc->sdtr_able = 0;
11316 for (tid = 0; tid <= ADV_MAX_TID; tid++) {
11317 if (tid == 0) {
11318 sdtr_speed = asc_dvc->sdtr_speed1;
11319 } else if (tid == 4) {
11320 sdtr_speed = asc_dvc->sdtr_speed2;
11321 } else if (tid == 8) {
11322 sdtr_speed = asc_dvc->sdtr_speed3;
11323 } else if (tid == 12) {
11324 sdtr_speed = asc_dvc->sdtr_speed4;
11325 }
11326 if (sdtr_speed & ADV_MAX_TID) {
11327 asc_dvc->sdtr_able |= (1 << tid);
11328 }
11329 sdtr_speed >>= 4;
11330 }
11331
11332
11333
11334
11335
11336 if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
11337 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11338 } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
11339
11340 if (eep_config.max_host_qng == 0) {
11341 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11342 } else {
11343 eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
11344 }
11345 }
11346
11347 if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
11348 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11349 } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
11350
11351 if (eep_config.max_dvc_qng == 0) {
11352 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11353 } else {
11354 eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
11355 }
11356 }
11357
11358
11359
11360
11361
11362 if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
11363 eep_config.max_dvc_qng = eep_config.max_host_qng;
11364 }
11365
11366
11367
11368
11369
11370 asc_dvc->max_host_qng = eep_config.max_host_qng;
11371 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11372
11373
11374
11375
11376
11377
11378
11379
11380
11381 if (eep_config.termination_se == 0) {
11382 termination = 0;
11383 } else {
11384
11385 if (eep_config.termination_se == 1) {
11386 termination = 0;
11387
11388
11389 } else if (eep_config.termination_se == 2) {
11390 termination = TERM_SE_HI;
11391
11392
11393 } else if (eep_config.termination_se == 3) {
11394 termination = TERM_SE;
11395 } else {
11396
11397
11398
11399
11400 termination = 0;
11401 warn_code |= ASC_WARN_EEPROM_TERMINATION;
11402 }
11403 }
11404
11405 if (eep_config.termination_lvd == 0) {
11406 asc_dvc->cfg->termination = termination;
11407 } else {
11408
11409 if (eep_config.termination_lvd == 1) {
11410 asc_dvc->cfg->termination = termination;
11411
11412
11413 } else if (eep_config.termination_lvd == 2) {
11414 asc_dvc->cfg->termination = termination | TERM_LVD_HI;
11415
11416
11417 } else if (eep_config.termination_lvd == 3) {
11418 asc_dvc->cfg->termination = termination | TERM_LVD;
11419 } else {
11420
11421
11422
11423
11424 asc_dvc->cfg->termination = termination;
11425 warn_code |= ASC_WARN_EEPROM_TERMINATION;
11426 }
11427 }
11428
11429 return warn_code;
11430}
11431
11432
11433
11434
11435
11436
11437
11438
11439
11440
11441
11442
11443
11444static int __devinit AdvInitFrom38C1600EEP(ADV_DVC_VAR *asc_dvc)
11445{
11446 AdvPortAddr iop_base;
11447 ushort warn_code;
11448 ADVEEP_38C1600_CONFIG eep_config;
11449 uchar tid, termination;
11450 ushort sdtr_speed = 0;
11451
11452 iop_base = asc_dvc->iop_base;
11453
11454 warn_code = 0;
11455
11456
11457
11458
11459
11460
11461 if (AdvGet38C1600EEPConfig(iop_base, &eep_config) !=
11462 eep_config.check_sum) {
11463 struct pci_dev *pdev = adv_dvc_to_pdev(asc_dvc);
11464 warn_code |= ASC_WARN_EEPROM_CHKSUM;
11465
11466
11467
11468
11469 memcpy(&eep_config, &Default_38C1600_EEPROM_Config,
11470 sizeof(ADVEEP_38C1600_CONFIG));
11471
11472 if (PCI_FUNC(pdev->devfn) != 0) {
11473 u8 ints;
11474
11475
11476
11477
11478
11479 eep_config.cfg_lsw &= ~ADV_EEPROM_BIOS_ENABLE;
11480
11481
11482
11483
11484
11485
11486
11487
11488
11489
11490
11491
11492
11493 AdvWriteByteRegister(iop_base, IOPB_GPIO_CNTL, 0);
11494 ints = AdvReadByteRegister(iop_base, IOPB_GPIO_DATA);
11495 if ((ints & 0x01) == 0)
11496 eep_config.cfg_lsw &= ~ADV_EEPROM_INTAB;
11497 }
11498
11499
11500
11501
11502
11503 eep_config.serial_number_word3 =
11504 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 1);
11505 eep_config.serial_number_word2 =
11506 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 2);
11507 eep_config.serial_number_word1 =
11508 AdvReadEEPWord(iop_base, ADV_EEP_DVC_CFG_END - 3);
11509
11510 AdvSet38C1600EEPConfig(iop_base, &eep_config);
11511 }
11512
11513
11514
11515
11516
11517
11518
11519 asc_dvc->wdtr_able = eep_config.wdtr_able;
11520 asc_dvc->sdtr_speed1 = eep_config.sdtr_speed1;
11521 asc_dvc->sdtr_speed2 = eep_config.sdtr_speed2;
11522 asc_dvc->sdtr_speed3 = eep_config.sdtr_speed3;
11523 asc_dvc->sdtr_speed4 = eep_config.sdtr_speed4;
11524 asc_dvc->ppr_able = 0;
11525 asc_dvc->tagqng_able = eep_config.tagqng_able;
11526 asc_dvc->cfg->disc_enable = eep_config.disc_enable;
11527 asc_dvc->max_host_qng = eep_config.max_host_qng;
11528 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11529 asc_dvc->chip_scsi_id = (eep_config.adapter_scsi_id & ASC_MAX_TID);
11530 asc_dvc->start_motor = eep_config.start_motor;
11531 asc_dvc->scsi_reset_wait = eep_config.scsi_reset_delay;
11532 asc_dvc->bios_ctrl = eep_config.bios_ctrl;
11533 asc_dvc->no_scam = eep_config.scam_tolerant;
11534
11535
11536
11537
11538
11539 asc_dvc->sdtr_able = 0;
11540 for (tid = 0; tid <= ASC_MAX_TID; tid++) {
11541 if (tid == 0) {
11542 sdtr_speed = asc_dvc->sdtr_speed1;
11543 } else if (tid == 4) {
11544 sdtr_speed = asc_dvc->sdtr_speed2;
11545 } else if (tid == 8) {
11546 sdtr_speed = asc_dvc->sdtr_speed3;
11547 } else if (tid == 12) {
11548 sdtr_speed = asc_dvc->sdtr_speed4;
11549 }
11550 if (sdtr_speed & ASC_MAX_TID) {
11551 asc_dvc->sdtr_able |= (1 << tid);
11552 }
11553 sdtr_speed >>= 4;
11554 }
11555
11556
11557
11558
11559
11560 if (eep_config.max_host_qng > ASC_DEF_MAX_HOST_QNG) {
11561 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11562 } else if (eep_config.max_host_qng < ASC_DEF_MIN_HOST_QNG) {
11563
11564 if (eep_config.max_host_qng == 0) {
11565 eep_config.max_host_qng = ASC_DEF_MAX_HOST_QNG;
11566 } else {
11567 eep_config.max_host_qng = ASC_DEF_MIN_HOST_QNG;
11568 }
11569 }
11570
11571 if (eep_config.max_dvc_qng > ASC_DEF_MAX_DVC_QNG) {
11572 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11573 } else if (eep_config.max_dvc_qng < ASC_DEF_MIN_DVC_QNG) {
11574
11575 if (eep_config.max_dvc_qng == 0) {
11576 eep_config.max_dvc_qng = ASC_DEF_MAX_DVC_QNG;
11577 } else {
11578 eep_config.max_dvc_qng = ASC_DEF_MIN_DVC_QNG;
11579 }
11580 }
11581
11582
11583
11584
11585
11586 if (eep_config.max_dvc_qng > eep_config.max_host_qng) {
11587 eep_config.max_dvc_qng = eep_config.max_host_qng;
11588 }
11589
11590
11591
11592
11593
11594 asc_dvc->max_host_qng = eep_config.max_host_qng;
11595 asc_dvc->max_dvc_qng = eep_config.max_dvc_qng;
11596
11597
11598
11599
11600
11601
11602
11603
11604
11605 if (eep_config.termination_se == 0) {
11606 termination = 0;
11607 } else {
11608
11609 if (eep_config.termination_se == 1) {
11610 termination = 0;
11611
11612
11613 } else if (eep_config.termination_se == 2) {
11614 termination = TERM_SE_HI;
11615
11616
11617 } else if (eep_config.termination_se == 3) {
11618 termination = TERM_SE;
11619 } else {
11620
11621
11622
11623
11624 termination = 0;
11625 warn_code |= ASC_WARN_EEPROM_TERMINATION;
11626 }
11627 }
11628
11629 if (eep_config.termination_lvd == 0) {
11630 asc_dvc->cfg->termination = termination;
11631 } else {
11632
11633 if (eep_config.termination_lvd == 1) {
11634 asc_dvc->cfg->termination = termination;
11635
11636
11637 } else if (eep_config.termination_lvd == 2) {
11638 asc_dvc->cfg->termination = termination | TERM_LVD_HI;
11639
11640
11641 } else if (eep_config.termination_lvd == 3) {
11642 asc_dvc->cfg->termination = termination | TERM_LVD;
11643 } else {
11644
11645
11646
11647
11648 asc_dvc->cfg->termination = termination;
11649 warn_code |= ASC_WARN_EEPROM_TERMINATION;
11650 }
11651 }
11652
11653 return warn_code;
11654}
11655
11656
11657
11658
11659
11660
11661
11662
11663
11664static int __devinit
11665AdvInitGetConfig(struct pci_dev *pdev, struct Scsi_Host *shost)
11666{
11667 struct asc_board *board = shost_priv(shost);
11668 ADV_DVC_VAR *asc_dvc = &board->dvc_var.adv_dvc_var;
11669 unsigned short warn_code = 0;
11670 AdvPortAddr iop_base = asc_dvc->iop_base;
11671 u16 cmd;
11672 int status;
11673
11674 asc_dvc->err_code = 0;
11675
11676
11677
11678
11679
11680
11681
11682 asc_dvc->cfg->control_flag = 0;
11683 pci_read_config_word(pdev, PCI_COMMAND, &cmd);
11684 if ((cmd & PCI_COMMAND_PARITY) == 0)
11685 asc_dvc->cfg->control_flag |= CONTROL_FLAG_IGNORE_PERR;
11686
11687 asc_dvc->cfg->chip_version =
11688 AdvGetChipVersion(iop_base, asc_dvc->bus_type);
11689
11690 ASC_DBG(1, "iopb_chip_id_1: 0x%x 0x%x\n",
11691 (ushort)AdvReadByteRegister(iop_base, IOPB_CHIP_ID_1),
11692 (ushort)ADV_CHIP_ID_BYTE);
11693
11694 ASC_DBG(1, "iopw_chip_id_0: 0x%x 0x%x\n",
11695 (ushort)AdvReadWordRegister(iop_base, IOPW_CHIP_ID_0),
11696 (ushort)ADV_CHIP_ID_WORD);
11697
11698
11699
11700
11701 if (AdvFindSignature(iop_base) == 0) {
11702 asc_dvc->err_code = ASC_IERR_BAD_SIGNATURE;
11703 return ADV_ERROR;
11704 } else {
11705
11706
11707
11708 if (asc_dvc->chip_type != ADV_CHIP_ASC3550 &&
11709 asc_dvc->chip_type != ADV_CHIP_ASC38C0800 &&
11710 asc_dvc->chip_type != ADV_CHIP_ASC38C1600) {
11711 asc_dvc->err_code |= ASC_IERR_BAD_CHIPTYPE;
11712 return ADV_ERROR;
11713 }
11714
11715
11716
11717
11718 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
11719 ADV_CTRL_REG_CMD_RESET);
11720 mdelay(100);
11721 AdvWriteWordRegister(iop_base, IOPW_CTRL_REG,
11722 ADV_CTRL_REG_CMD_WR_IO_REG);
11723
11724 if (asc_dvc->chip_type == ADV_CHIP_ASC38C1600) {
11725 status = AdvInitFrom38C1600EEP(asc_dvc);
11726 } else if (asc_dvc->chip_type == ADV_CHIP_ASC38C0800) {
11727 status = AdvInitFrom38C0800EEP(asc_dvc);
11728 } else {
11729 status = AdvInitFrom3550EEP(asc_dvc);
11730 }
11731 warn_code |= status;
11732 }
11733
11734 if (warn_code != 0)
11735 shost_printk(KERN_WARNING, shost, "warning: 0x%x\n", warn_code);
11736
11737 if (asc_dvc->err_code)
11738 shost_printk(KERN_ERR, shost, "error code 0x%x\n",
11739 asc_dvc->err_code);
11740
11741 return asc_dvc->err_code;
11742}
11743#endif
11744
11745static struct scsi_host_template advansys_template = {
11746 .proc_name = DRV_NAME,
11747#ifdef CONFIG_PROC_FS
11748 .proc_info = advansys_proc_info,
11749#endif
11750 .name = DRV_NAME,
11751 .info = advansys_info,
11752 .queuecommand = advansys_queuecommand,
11753 .eh_bus_reset_handler = advansys_reset,
11754 .bios_param = advansys_biosparam,
11755 .slave_configure = advansys_slave_configure,
11756
11757
11758
11759
11760
11761 .unchecked_isa_dma = 1,
11762
11763
11764
11765
11766
11767
11768
11769 .use_clustering = ENABLE_CLUSTERING,
11770};
11771
11772static int __devinit advansys_wide_init_chip(struct Scsi_Host *shost)
11773{
11774 struct asc_board *board = shost_priv(shost);
11775 struct adv_dvc_var *adv_dvc = &board->dvc_var.adv_dvc_var;
11776 int req_cnt = 0;
11777 adv_req_t *reqp = NULL;
11778 int sg_cnt = 0;
11779 adv_sgblk_t *sgp;
11780 int warn_code, err_code;
11781
11782
11783
11784
11785
11786 adv_dvc->carrier_buf = kmalloc(ADV_CARRIER_BUFSIZE, GFP_KERNEL);
11787 ASC_DBG(1, "carrier_buf 0x%p\n", adv_dvc->carrier_buf);
11788
11789 if (!adv_dvc->carrier_buf)
11790 goto kmalloc_failed;
11791
11792
11793
11794
11795
11796
11797 for (req_cnt = adv_dvc->max_host_qng; req_cnt > 0; req_cnt--) {
11798 reqp = kmalloc(sizeof(adv_req_t) * req_cnt, GFP_KERNEL);
11799
11800 ASC_DBG(1, "reqp 0x%p, req_cnt %d, bytes %lu\n", reqp, req_cnt,
11801 (ulong)sizeof(adv_req_t) * req_cnt);
11802
11803 if (reqp)
11804 break;
11805 }
11806
11807 if (!reqp)
11808 goto kmalloc_failed;
11809
11810 adv_dvc->orig_reqp = reqp;
11811
11812
11813
11814
11815
11816 board->adv_sgblkp = NULL;
11817 for (sg_cnt = 0; sg_cnt < ADV_TOT_SG_BLOCK; sg_cnt++) {
11818 sgp = kmalloc(sizeof(adv_sgblk_t), GFP_KERNEL);
11819
11820 if (!sgp)
11821 break;
11822
11823 sgp->next_sgblkp = board->adv_sgblkp;
11824 board->adv_sgblkp = sgp;
11825
11826 }
11827
11828 ASC_DBG(1, "sg_cnt %d * %lu = %lu bytes\n", sg_cnt, sizeof(adv_sgblk_t),
11829 sizeof(adv_sgblk_t) * sg_cnt);
11830
11831 if (!board->adv_sgblkp)
11832 goto kmalloc_failed;
11833
11834
11835
11836
11837
11838 req_cnt--;
11839 reqp[req_cnt].next_reqp = NULL;
11840 for (; req_cnt > 0; req_cnt--) {
11841 reqp[req_cnt - 1].next_reqp = &reqp[req_cnt];
11842 }
11843 board->adv_reqp = &reqp[0];
11844
11845 if (adv_dvc->chip_type == ADV_CHIP_ASC3550) {
11846 ASC_DBG(2, "AdvInitAsc3550Driver()\n");
11847 warn_code = AdvInitAsc3550Driver(adv_dvc);
11848 } else if (adv_dvc->chip_type == ADV_CHIP_ASC38C0800) {
11849 ASC_DBG(2, "AdvInitAsc38C0800Driver()\n");
11850 warn_code = AdvInitAsc38C0800Driver(adv_dvc);
11851 } else {
11852 ASC_DBG(2, "AdvInitAsc38C1600Driver()\n");
11853 warn_code = AdvInitAsc38C1600Driver(adv_dvc);
11854 }
11855 err_code = adv_dvc->err_code;
11856
11857 if (warn_code || err_code) {
11858 shost_printk(KERN_WARNING, shost, "error: warn 0x%x, error "
11859 "0x%x\n", warn_code, err_code);
11860 }
11861
11862 goto exit;
11863
11864 kmalloc_failed:
11865 shost_printk(KERN_ERR, shost, "error: kmalloc() failed\n");
11866 err_code = ADV_ERROR;
11867 exit:
11868 return err_code;
11869}
11870
11871static void advansys_wide_free_mem(struct asc_board *board)
11872{
11873 struct adv_dvc_var *adv_dvc = &board->dvc_var.adv_dvc_var;
11874 kfree(adv_dvc->carrier_buf);
11875 adv_dvc->carrier_buf = NULL;
11876 kfree(adv_dvc->orig_reqp);
11877 adv_dvc->orig_reqp = board->adv_reqp = NULL;
11878 while (board->adv_sgblkp) {
11879 adv_sgblk_t *sgp = board->adv_sgblkp;
11880 board->adv_sgblkp = sgp->next_sgblkp;
11881 kfree(sgp);
11882 }
11883}
11884
11885static int __devinit advansys_board_found(struct Scsi_Host *shost,
11886 unsigned int iop, int bus_type)
11887{
11888 struct pci_dev *pdev;
11889 struct asc_board *boardp = shost_priv(shost);
11890 ASC_DVC_VAR *asc_dvc_varp = NULL;
11891 ADV_DVC_VAR *adv_dvc_varp = NULL;
11892 int share_irq, warn_code, ret;
11893
11894 pdev = (bus_type == ASC_IS_PCI) ? to_pci_dev(boardp->dev) : NULL;
11895
11896 if (ASC_NARROW_BOARD(boardp)) {
11897 ASC_DBG(1, "narrow board\n");
11898 asc_dvc_varp = &boardp->dvc_var.asc_dvc_var;
11899 asc_dvc_varp->bus_type = bus_type;
11900 asc_dvc_varp->drv_ptr = boardp;
11901 asc_dvc_varp->cfg = &boardp->dvc_cfg.asc_dvc_cfg;
11902 asc_dvc_varp->iop_base = iop;
11903 } else {
11904#ifdef CONFIG_PCI
11905 adv_dvc_varp = &boardp->dvc_var.adv_dvc_var;
11906 adv_dvc_varp->drv_ptr = boardp;
11907 adv_dvc_varp->cfg = &boardp->dvc_cfg.adv_dvc_cfg;
11908 if (pdev->device == PCI_DEVICE_ID_ASP_ABP940UW) {
11909 ASC_DBG(1, "wide board ASC-3550\n");
11910 adv_dvc_varp->chip_type = ADV_CHIP_ASC3550;
11911 } else if (pdev->device == PCI_DEVICE_ID_38C0800_REV1) {
11912 ASC_DBG(1, "wide board ASC-38C0800\n");
11913 adv_dvc_varp->chip_type = ADV_CHIP_ASC38C0800;
11914 } else {
11915 ASC_DBG(1, "wide board ASC-38C1600\n");
11916 adv_dvc_varp->chip_type = ADV_CHIP_ASC38C1600;
11917 }
11918
11919 boardp->asc_n_io_port = pci_resource_len(pdev, 1);
11920 boardp->ioremap_addr = pci_ioremap_bar(pdev, 1);
11921 if (!boardp->ioremap_addr) {
11922 shost_printk(KERN_ERR, shost, "ioremap(%lx, %d) "
11923 "returned NULL\n",
11924 (long)pci_resource_start(pdev, 1),
11925 boardp->asc_n_io_port);
11926 ret = -ENODEV;
11927 goto err_shost;
11928 }
11929 adv_dvc_varp->iop_base = (AdvPortAddr)boardp->ioremap_addr;
11930 ASC_DBG(1, "iop_base: 0x%p\n", adv_dvc_varp->iop_base);
11931
11932
11933
11934
11935
11936
11937 boardp->ioport = iop;
11938
11939 ASC_DBG(1, "iopb_chip_id_1 0x%x, iopw_chip_id_0 0x%x\n",
11940 (ushort)inp(iop + 1), (ushort)inpw(iop));
11941#endif
11942 }
11943
11944#ifdef CONFIG_PROC_FS
11945
11946
11947
11948
11949 boardp->prtbuf = kmalloc(ASC_PRTBUF_SIZE, GFP_KERNEL);
11950 if (!boardp->prtbuf) {
11951 shost_printk(KERN_ERR, shost, "kmalloc(%d) returned NULL\n",
11952 ASC_PRTBUF_SIZE);
11953 ret = -ENOMEM;
11954 goto err_unmap;
11955 }
11956#endif
11957
11958 if (ASC_NARROW_BOARD(boardp)) {
11959
11960
11961
11962
11963 switch (asc_dvc_varp->bus_type) {
11964#ifdef CONFIG_ISA
11965 case ASC_IS_ISA:
11966 shost->unchecked_isa_dma = TRUE;
11967 share_irq = 0;
11968 break;
11969 case ASC_IS_VL:
11970 shost->unchecked_isa_dma = FALSE;
11971 share_irq = 0;
11972 break;
11973 case ASC_IS_EISA:
11974 shost->unchecked_isa_dma = FALSE;
11975 share_irq = IRQF_SHARED;
11976 break;
11977#endif
11978#ifdef CONFIG_PCI
11979 case ASC_IS_PCI:
11980 shost->unchecked_isa_dma = FALSE;
11981 share_irq = IRQF_SHARED;
11982 break;
11983#endif
11984 default:
11985 shost_printk(KERN_ERR, shost, "unknown adapter type: "
11986 "%d\n", asc_dvc_varp->bus_type);
11987 shost->unchecked_isa_dma = TRUE;
11988 share_irq = 0;
11989 break;
11990 }
11991
11992
11993
11994
11995
11996
11997
11998 ASC_DBG(2, "AscInitGetConfig()\n");
11999 ret = AscInitGetConfig(shost) ? -ENODEV : 0;
12000 } else {
12001#ifdef CONFIG_PCI
12002
12003
12004
12005
12006 shost->unchecked_isa_dma = FALSE;
12007 share_irq = IRQF_SHARED;
12008 ASC_DBG(2, "AdvInitGetConfig()\n");
12009
12010 ret = AdvInitGetConfig(pdev, shost) ? -ENODEV : 0;
12011#endif
12012 }
12013
12014 if (ret)
12015 goto err_free_proc;
12016
12017
12018
12019
12020
12021 if (ASC_NARROW_BOARD(boardp)) {
12022
12023 ASCEEP_CONFIG *ep;
12024
12025
12026
12027
12028 boardp->init_tidmask |=
12029 ADV_TID_TO_TIDMASK(asc_dvc_varp->cfg->chip_scsi_id);
12030
12031
12032
12033
12034 ep = &boardp->eep_config.asc_eep;
12035
12036 ep->init_sdtr = asc_dvc_varp->cfg->sdtr_enable;
12037 ep->disc_enable = asc_dvc_varp->cfg->disc_enable;
12038 ep->use_cmd_qng = asc_dvc_varp->cfg->cmd_qng_enabled;
12039 ASC_EEP_SET_DMA_SPD(ep, asc_dvc_varp->cfg->isa_dma_speed);
12040 ep->start_motor = asc_dvc_varp->start_motor;
12041 ep->cntl = asc_dvc_varp->dvc_cntl;
12042 ep->no_scam = asc_dvc_varp->no_scam;
12043 ep->max_total_qng = asc_dvc_varp->max_total_qng;
12044 ASC_EEP_SET_CHIP_ID(ep, asc_dvc_varp->cfg->chip_scsi_id);
12045
12046 ep->max_tag_qng = asc_dvc_varp->cfg->max_tag_qng[0];
12047 ep->adapter_info[0] = asc_dvc_varp->cfg->adapter_info[0];
12048 ep->adapter_info[1] = asc_dvc_varp->cfg->adapter_info[1];
12049 ep->adapter_info[2] = asc_dvc_varp->cfg->adapter_info[2];
12050 ep->adapter_info[3] = asc_dvc_varp->cfg->adapter_info[3];
12051 ep->adapter_info[4] = asc_dvc_varp->cfg->adapter_info[4];
12052 ep->adapter_info[5] = asc_dvc_varp->cfg->adapter_info[5];
12053
12054
12055
12056
12057 ASC_DBG(2, "AscInitSetConfig()\n");
12058 ret = AscInitSetConfig(pdev, shost) ? -ENODEV : 0;
12059 if (ret)
12060 goto err_free_proc;
12061 } else {
12062 ADVEEP_3550_CONFIG *ep_3550;
12063 ADVEEP_38C0800_CONFIG *ep_38C0800;
12064 ADVEEP_38C1600_CONFIG *ep_38C1600;
12065
12066
12067
12068
12069 if (adv_dvc_varp->chip_type == ADV_CHIP_ASC3550) {
12070 ep_3550 = &boardp->eep_config.adv_3550_eep;
12071
12072 ep_3550->adapter_scsi_id = adv_dvc_varp->chip_scsi_id;
12073 ep_3550->max_host_qng = adv_dvc_varp->max_host_qng;
12074 ep_3550->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
12075 ep_3550->termination = adv_dvc_varp->cfg->termination;
12076 ep_3550->disc_enable = adv_dvc_varp->cfg->disc_enable;
12077 ep_3550->bios_ctrl = adv_dvc_varp->bios_ctrl;
12078 ep_3550->wdtr_able = adv_dvc_varp->wdtr_able;
12079 ep_3550->sdtr_able = adv_dvc_varp->sdtr_able;
12080 ep_3550->ultra_able = adv_dvc_varp->ultra_able;
12081 ep_3550->tagqng_able = adv_dvc_varp->tagqng_able;
12082 ep_3550->start_motor = adv_dvc_varp->start_motor;
12083 ep_3550->scsi_reset_delay =
12084 adv_dvc_varp->scsi_reset_wait;
12085 ep_3550->serial_number_word1 =
12086 adv_dvc_varp->cfg->serial1;
12087 ep_3550->serial_number_word2 =
12088 adv_dvc_varp->cfg->serial2;
12089 ep_3550->serial_number_word3 =
12090 adv_dvc_varp->cfg->serial3;
12091 } else if (adv_dvc_varp->chip_type == ADV_CHIP_ASC38C0800) {
12092 ep_38C0800 = &boardp->eep_config.adv_38C0800_eep;
12093
12094 ep_38C0800->adapter_scsi_id =
12095 adv_dvc_varp->chip_scsi_id;
12096 ep_38C0800->max_host_qng = adv_dvc_varp->max_host_qng;
12097 ep_38C0800->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
12098 ep_38C0800->termination_lvd =
12099 adv_dvc_varp->cfg->termination;
12100 ep_38C0800->disc_enable =
12101 adv_dvc_varp->cfg->disc_enable;
12102 ep_38C0800->bios_ctrl = adv_dvc_varp->bios_ctrl;
12103 ep_38C0800->wdtr_able = adv_dvc_varp->wdtr_able;
12104 ep_38C0800->tagqng_able = adv_dvc_varp->tagqng_able;
12105 ep_38C0800->sdtr_speed1 = adv_dvc_varp->sdtr_speed1;
12106 ep_38C0800->sdtr_speed2 = adv_dvc_varp->sdtr_speed2;
12107 ep_38C0800->sdtr_speed3 = adv_dvc_varp->sdtr_speed3;
12108 ep_38C0800->sdtr_speed4 = adv_dvc_varp->sdtr_speed4;
12109 ep_38C0800->tagqng_able = adv_dvc_varp->tagqng_able;
12110 ep_38C0800->start_motor = adv_dvc_varp->start_motor;
12111 ep_38C0800->scsi_reset_delay =
12112 adv_dvc_varp->scsi_reset_wait;
12113 ep_38C0800->serial_number_word1 =
12114 adv_dvc_varp->cfg->serial1;
12115 ep_38C0800->serial_number_word2 =
12116 adv_dvc_varp->cfg->serial2;
12117 ep_38C0800->serial_number_word3 =
12118 adv_dvc_varp->cfg->serial3;
12119 } else {
12120 ep_38C1600 = &boardp->eep_config.adv_38C1600_eep;
12121
12122 ep_38C1600->adapter_scsi_id =
12123 adv_dvc_varp->chip_scsi_id;
12124 ep_38C1600->max_host_qng = adv_dvc_varp->max_host_qng;
12125 ep_38C1600->max_dvc_qng = adv_dvc_varp->max_dvc_qng;
12126 ep_38C1600->termination_lvd =
12127 adv_dvc_varp->cfg->termination;
12128 ep_38C1600->disc_enable =
12129 adv_dvc_varp->cfg->disc_enable;
12130 ep_38C1600->bios_ctrl = adv_dvc_varp->bios_ctrl;
12131 ep_38C1600->wdtr_able = adv_dvc_varp->wdtr_able;
12132 ep_38C1600->tagqng_able = adv_dvc_varp->tagqng_able;
12133 ep_38C1600->sdtr_speed1 = adv_dvc_varp->sdtr_speed1;
12134 ep_38C1600->sdtr_speed2 = adv_dvc_varp->sdtr_speed2;
12135 ep_38C1600->sdtr_speed3 = adv_dvc_varp->sdtr_speed3;
12136 ep_38C1600->sdtr_speed4 = adv_dvc_varp->sdtr_speed4;
12137 ep_38C1600->tagqng_able = adv_dvc_varp->tagqng_able;
12138 ep_38C1600->start_motor = adv_dvc_varp->start_motor;
12139 ep_38C1600->scsi_reset_delay =
12140 adv_dvc_varp->scsi_reset_wait;
12141 ep_38C1600->serial_number_word1 =
12142 adv_dvc_varp->cfg->serial1;
12143 ep_38C1600->serial_number_word2 =
12144 adv_dvc_varp->cfg->serial2;
12145 ep_38C1600->serial_number_word3 =
12146 adv_dvc_varp->cfg->serial3;
12147 }
12148
12149
12150
12151
12152 boardp->init_tidmask |=
12153 ADV_TID_TO_TIDMASK(adv_dvc_varp->chip_scsi_id);
12154 }
12155
12156
12157
12158
12159
12160
12161 shost->max_channel = 0;
12162 if (ASC_NARROW_BOARD(boardp)) {
12163 shost->max_id = ASC_MAX_TID + 1;
12164 shost->max_lun = ASC_MAX_LUN + 1;
12165 shost->max_cmd_len = ASC_MAX_CDB_LEN;
12166
12167 shost->io_port = asc_dvc_varp->iop_base;
12168 boardp->asc_n_io_port = ASC_IOADR_GAP;
12169 shost->this_id = asc_dvc_varp->cfg->chip_scsi_id;
12170
12171
12172 shost->can_queue = asc_dvc_varp->max_total_qng;
12173 } else {
12174 shost->max_id = ADV_MAX_TID + 1;
12175 shost->max_lun = ADV_MAX_LUN + 1;
12176 shost->max_cmd_len = ADV_MAX_CDB_LEN;
12177
12178
12179
12180
12181
12182
12183
12184 shost->io_port = iop;
12185
12186 shost->this_id = adv_dvc_varp->chip_scsi_id;
12187
12188
12189 shost->can_queue = adv_dvc_varp->max_host_qng;
12190 }
12191
12192
12193
12194
12195
12196
12197
12198
12199
12200
12201
12202
12203
12204
12205 shost->cmd_per_lun = 1;
12206
12207
12208
12209
12210
12211
12212
12213
12214 if (ASC_NARROW_BOARD(boardp)) {
12215
12216
12217
12218
12219
12220
12221 shost->sg_tablesize =
12222 (((asc_dvc_varp->max_total_qng - 2) / 2) *
12223 ASC_SG_LIST_PER_Q) + 1;
12224 } else {
12225 shost->sg_tablesize = ADV_MAX_SG_LIST;
12226 }
12227
12228
12229
12230
12231
12232
12233
12234 if (shost->sg_tablesize > SG_ALL) {
12235 shost->sg_tablesize = SG_ALL;
12236 }
12237
12238 ASC_DBG(1, "sg_tablesize: %d\n", shost->sg_tablesize);
12239
12240
12241 if (ASC_NARROW_BOARD(boardp)) {
12242 shost->base = AscGetChipBiosAddress(asc_dvc_varp->iop_base,
12243 asc_dvc_varp->bus_type);
12244 } else {
12245
12246
12247
12248
12249 AdvReadWordLram(adv_dvc_varp->iop_base,
12250 BIOS_SIGNATURE, boardp->bios_signature);
12251 AdvReadWordLram(adv_dvc_varp->iop_base,
12252 BIOS_VERSION, boardp->bios_version);
12253 AdvReadWordLram(adv_dvc_varp->iop_base,
12254 BIOS_CODESEG, boardp->bios_codeseg);
12255 AdvReadWordLram(adv_dvc_varp->iop_base,
12256 BIOS_CODELEN, boardp->bios_codelen);
12257
12258 ASC_DBG(1, "bios_signature 0x%x, bios_version 0x%x\n",
12259 boardp->bios_signature, boardp->bios_version);
12260
12261 ASC_DBG(1, "bios_codeseg 0x%x, bios_codelen 0x%x\n",
12262 boardp->bios_codeseg, boardp->bios_codelen);
12263
12264
12265
12266
12267
12268 if (boardp->bios_signature == 0x55AA) {
12269
12270
12271
12272
12273 shost->base = ((ulong)boardp->bios_codeseg << 4);
12274 } else {
12275 shost->base = 0;
12276 }
12277 }
12278
12279
12280
12281
12282
12283
12284 shost->dma_channel = NO_ISA_DMA;
12285#ifdef CONFIG_ISA
12286 if (ASC_NARROW_BOARD(boardp)) {
12287
12288 if (asc_dvc_varp->bus_type & ASC_IS_ISA) {
12289 shost->dma_channel = asc_dvc_varp->cfg->isa_dma_channel;
12290 ret = request_dma(shost->dma_channel, DRV_NAME);
12291 if (ret) {
12292 shost_printk(KERN_ERR, shost, "request_dma() "
12293 "%d failed %d\n",
12294 shost->dma_channel, ret);
12295 goto err_free_proc;
12296 }
12297 AscEnableIsaDma(shost->dma_channel);
12298 }
12299 }
12300#endif
12301
12302
12303 ASC_DBG(2, "request_irq(%d, %p)\n", boardp->irq, shost);
12304
12305 ret = request_irq(boardp->irq, advansys_interrupt, share_irq,
12306 DRV_NAME, shost);
12307
12308 if (ret) {
12309 if (ret == -EBUSY) {
12310 shost_printk(KERN_ERR, shost, "request_irq(): IRQ 0x%x "
12311 "already in use\n", boardp->irq);
12312 } else if (ret == -EINVAL) {
12313 shost_printk(KERN_ERR, shost, "request_irq(): IRQ 0x%x "
12314 "not valid\n", boardp->irq);
12315 } else {
12316 shost_printk(KERN_ERR, shost, "request_irq(): IRQ 0x%x "
12317 "failed with %d\n", boardp->irq, ret);
12318 }
12319 goto err_free_dma;
12320 }
12321
12322
12323
12324
12325 if (ASC_NARROW_BOARD(boardp)) {
12326 ASC_DBG(2, "AscInitAsc1000Driver()\n");
12327
12328 asc_dvc_varp->overrun_buf = kzalloc(ASC_OVERRUN_BSIZE, GFP_KERNEL);
12329 if (!asc_dvc_varp->overrun_buf) {
12330 ret = -ENOMEM;
12331 goto err_free_irq;
12332 }
12333 warn_code = AscInitAsc1000Driver(asc_dvc_varp);
12334
12335 if (warn_code || asc_dvc_varp->err_code) {
12336 shost_printk(KERN_ERR, shost, "error: init_state 0x%x, "
12337 "warn 0x%x, error 0x%x\n",
12338 asc_dvc_varp->init_state, warn_code,
12339 asc_dvc_varp->err_code);
12340 if (!asc_dvc_varp->overrun_dma) {
12341 ret = -ENODEV;
12342 goto err_free_mem;
12343 }
12344 }
12345 } else {
12346 if (advansys_wide_init_chip(shost)) {
12347 ret = -ENODEV;
12348 goto err_free_mem;
12349 }
12350 }
12351
12352 ASC_DBG_PRT_SCSI_HOST(2, shost);
12353
12354 ret = scsi_add_host(shost, boardp->dev);
12355 if (ret)
12356 goto err_free_mem;
12357
12358 scsi_scan_host(shost);
12359 return 0;
12360
12361 err_free_mem:
12362 if (ASC_NARROW_BOARD(boardp)) {
12363 if (asc_dvc_varp->overrun_dma)
12364 dma_unmap_single(boardp->dev, asc_dvc_varp->overrun_dma,
12365 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
12366 kfree(asc_dvc_varp->overrun_buf);
12367 } else
12368 advansys_wide_free_mem(boardp);
12369 err_free_irq:
12370 free_irq(boardp->irq, shost);
12371 err_free_dma:
12372#ifdef CONFIG_ISA
12373 if (shost->dma_channel != NO_ISA_DMA)
12374 free_dma(shost->dma_channel);
12375#endif
12376 err_free_proc:
12377 kfree(boardp->prtbuf);
12378 err_unmap:
12379 if (boardp->ioremap_addr)
12380 iounmap(boardp->ioremap_addr);
12381 err_shost:
12382 return ret;
12383}
12384
12385
12386
12387
12388
12389
12390static int advansys_release(struct Scsi_Host *shost)
12391{
12392 struct asc_board *board = shost_priv(shost);
12393 ASC_DBG(1, "begin\n");
12394 scsi_remove_host(shost);
12395 free_irq(board->irq, shost);
12396#ifdef CONFIG_ISA
12397 if (shost->dma_channel != NO_ISA_DMA) {
12398 ASC_DBG(1, "free_dma()\n");
12399 free_dma(shost->dma_channel);
12400 }
12401#endif
12402 if (ASC_NARROW_BOARD(board)) {
12403 dma_unmap_single(board->dev,
12404 board->dvc_var.asc_dvc_var.overrun_dma,
12405 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
12406 kfree(board->dvc_var.asc_dvc_var.overrun_buf);
12407 } else {
12408 iounmap(board->ioremap_addr);
12409 advansys_wide_free_mem(board);
12410 }
12411 kfree(board->prtbuf);
12412 scsi_host_put(shost);
12413 ASC_DBG(1, "end\n");
12414 return 0;
12415}
12416
12417#define ASC_IOADR_TABLE_MAX_IX 11
12418
12419static PortAddr _asc_def_iop_base[ASC_IOADR_TABLE_MAX_IX] = {
12420 0x100, 0x0110, 0x120, 0x0130, 0x140, 0x0150, 0x0190,
12421 0x0210, 0x0230, 0x0250, 0x0330
12422};
12423
12424
12425
12426
12427
12428
12429
12430
12431static unsigned int __devinit advansys_isa_irq_no(PortAddr iop_base)
12432{
12433 unsigned short cfg_lsw = AscGetChipCfgLsw(iop_base);
12434 unsigned int chip_irq = ((cfg_lsw >> 2) & 0x03) + 10;
12435 if (chip_irq == 13)
12436 chip_irq = 15;
12437 return chip_irq;
12438}
12439
12440static int __devinit advansys_isa_probe(struct device *dev, unsigned int id)
12441{
12442 int err = -ENODEV;
12443 PortAddr iop_base = _asc_def_iop_base[id];
12444 struct Scsi_Host *shost;
12445 struct asc_board *board;
12446
12447 if (!request_region(iop_base, ASC_IOADR_GAP, DRV_NAME)) {
12448 ASC_DBG(1, "I/O port 0x%x busy\n", iop_base);
12449 return -ENODEV;
12450 }
12451 ASC_DBG(1, "probing I/O port 0x%x\n", iop_base);
12452 if (!AscFindSignature(iop_base))
12453 goto release_region;
12454 if (!(AscGetChipVersion(iop_base, ASC_IS_ISA) & ASC_CHIP_VER_ISA_BIT))
12455 goto release_region;
12456
12457 err = -ENOMEM;
12458 shost = scsi_host_alloc(&advansys_template, sizeof(*board));
12459 if (!shost)
12460 goto release_region;
12461
12462 board = shost_priv(shost);
12463 board->irq = advansys_isa_irq_no(iop_base);
12464 board->dev = dev;
12465
12466 err = advansys_board_found(shost, iop_base, ASC_IS_ISA);
12467 if (err)
12468 goto free_host;
12469
12470 dev_set_drvdata(dev, shost);
12471 return 0;
12472
12473 free_host:
12474 scsi_host_put(shost);
12475 release_region:
12476 release_region(iop_base, ASC_IOADR_GAP);
12477 return err;
12478}
12479
12480static int __devexit advansys_isa_remove(struct device *dev, unsigned int id)
12481{
12482 int ioport = _asc_def_iop_base[id];
12483 advansys_release(dev_get_drvdata(dev));
12484 release_region(ioport, ASC_IOADR_GAP);
12485 return 0;
12486}
12487
12488static struct isa_driver advansys_isa_driver = {
12489 .probe = advansys_isa_probe,
12490 .remove = __devexit_p(advansys_isa_remove),
12491 .driver = {
12492 .owner = THIS_MODULE,
12493 .name = DRV_NAME,
12494 },
12495};
12496
12497
12498
12499
12500
12501
12502
12503
12504
12505
12506
12507
12508static unsigned int __devinit advansys_vlb_irq_no(PortAddr iop_base)
12509{
12510 unsigned short cfg_lsw = AscGetChipCfgLsw(iop_base);
12511 unsigned int chip_irq = ((cfg_lsw >> 2) & 0x07) + 9;
12512 if ((chip_irq < 10) || (chip_irq == 13) || (chip_irq > 15))
12513 return 0;
12514 return chip_irq;
12515}
12516
12517static int __devinit advansys_vlb_probe(struct device *dev, unsigned int id)
12518{
12519 int err = -ENODEV;
12520 PortAddr iop_base = _asc_def_iop_base[id];
12521 struct Scsi_Host *shost;
12522 struct asc_board *board;
12523
12524 if (!request_region(iop_base, ASC_IOADR_GAP, DRV_NAME)) {
12525 ASC_DBG(1, "I/O port 0x%x busy\n", iop_base);
12526 return -ENODEV;
12527 }
12528 ASC_DBG(1, "probing I/O port 0x%x\n", iop_base);
12529 if (!AscFindSignature(iop_base))
12530 goto release_region;
12531
12532
12533
12534
12535
12536 if (AscGetChipVersion(iop_base, ASC_IS_VL) > ASC_CHIP_MAX_VER_VL)
12537 goto release_region;
12538
12539 err = -ENOMEM;
12540 shost = scsi_host_alloc(&advansys_template, sizeof(*board));
12541 if (!shost)
12542 goto release_region;
12543
12544 board = shost_priv(shost);
12545 board->irq = advansys_vlb_irq_no(iop_base);
12546 board->dev = dev;
12547
12548 err = advansys_board_found(shost, iop_base, ASC_IS_VL);
12549 if (err)
12550 goto free_host;
12551
12552 dev_set_drvdata(dev, shost);
12553 return 0;
12554
12555 free_host:
12556 scsi_host_put(shost);
12557 release_region:
12558 release_region(iop_base, ASC_IOADR_GAP);
12559 return -ENODEV;
12560}
12561
12562static struct isa_driver advansys_vlb_driver = {
12563 .probe = advansys_vlb_probe,
12564 .remove = __devexit_p(advansys_isa_remove),
12565 .driver = {
12566 .owner = THIS_MODULE,
12567 .name = "advansys_vlb",
12568 },
12569};
12570
12571static struct eisa_device_id advansys_eisa_table[] __devinitdata = {
12572 { "ABP7401" },
12573 { "ABP7501" },
12574 { "" }
12575};
12576
12577MODULE_DEVICE_TABLE(eisa, advansys_eisa_table);
12578
12579
12580
12581
12582
12583struct eisa_scsi_data {
12584 struct Scsi_Host *host[2];
12585};
12586
12587
12588
12589
12590
12591
12592
12593
12594
12595
12596
12597
12598static unsigned int __devinit advansys_eisa_irq_no(struct eisa_device *edev)
12599{
12600 unsigned short cfg_lsw = inw(edev->base_addr + 0xc86);
12601 unsigned int chip_irq = ((cfg_lsw >> 8) & 0x07) + 10;
12602 if ((chip_irq == 13) || (chip_irq > 15))
12603 return 0;
12604 return chip_irq;
12605}
12606
12607static int __devinit advansys_eisa_probe(struct device *dev)
12608{
12609 int i, ioport, irq = 0;
12610 int err;
12611 struct eisa_device *edev = to_eisa_device(dev);
12612 struct eisa_scsi_data *data;
12613
12614 err = -ENOMEM;
12615 data = kzalloc(sizeof(*data), GFP_KERNEL);
12616 if (!data)
12617 goto fail;
12618 ioport = edev->base_addr + 0xc30;
12619
12620 err = -ENODEV;
12621 for (i = 0; i < 2; i++, ioport += 0x20) {
12622 struct asc_board *board;
12623 struct Scsi_Host *shost;
12624 if (!request_region(ioport, ASC_IOADR_GAP, DRV_NAME)) {
12625 printk(KERN_WARNING "Region %x-%x busy\n", ioport,
12626 ioport + ASC_IOADR_GAP - 1);
12627 continue;
12628 }
12629 if (!AscFindSignature(ioport)) {
12630 release_region(ioport, ASC_IOADR_GAP);
12631 continue;
12632 }
12633
12634
12635
12636
12637
12638
12639
12640
12641 inw(ioport + 4);
12642
12643 if (!irq)
12644 irq = advansys_eisa_irq_no(edev);
12645
12646 err = -ENOMEM;
12647 shost = scsi_host_alloc(&advansys_template, sizeof(*board));
12648 if (!shost)
12649 goto release_region;
12650
12651 board = shost_priv(shost);
12652 board->irq = irq;
12653 board->dev = dev;
12654
12655 err = advansys_board_found(shost, ioport, ASC_IS_EISA);
12656 if (!err) {
12657 data->host[i] = shost;
12658 continue;
12659 }
12660
12661 scsi_host_put(shost);
12662 release_region:
12663 release_region(ioport, ASC_IOADR_GAP);
12664 break;
12665 }
12666
12667 if (err)
12668 goto free_data;
12669 dev_set_drvdata(dev, data);
12670 return 0;
12671
12672 free_data:
12673 kfree(data->host[0]);
12674 kfree(data->host[1]);
12675 kfree(data);
12676 fail:
12677 return err;
12678}
12679
12680static __devexit int advansys_eisa_remove(struct device *dev)
12681{
12682 int i;
12683 struct eisa_scsi_data *data = dev_get_drvdata(dev);
12684
12685 for (i = 0; i < 2; i++) {
12686 int ioport;
12687 struct Scsi_Host *shost = data->host[i];
12688 if (!shost)
12689 continue;
12690 ioport = shost->io_port;
12691 advansys_release(shost);
12692 release_region(ioport, ASC_IOADR_GAP);
12693 }
12694
12695 kfree(data);
12696 return 0;
12697}
12698
12699static struct eisa_driver advansys_eisa_driver = {
12700 .id_table = advansys_eisa_table,
12701 .driver = {
12702 .name = DRV_NAME,
12703 .probe = advansys_eisa_probe,
12704 .remove = __devexit_p(advansys_eisa_remove),
12705 }
12706};
12707
12708
12709static struct pci_device_id advansys_pci_tbl[] __devinitdata = {
12710 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_1200A,
12711 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12712 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940,
12713 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12714 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940U,
12715 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12716 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_ASP_ABP940UW,
12717 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12718 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_38C0800_REV1,
12719 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12720 {PCI_VENDOR_ID_ASP, PCI_DEVICE_ID_38C1600_REV1,
12721 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
12722 {}
12723};
12724
12725MODULE_DEVICE_TABLE(pci, advansys_pci_tbl);
12726
12727static void __devinit advansys_set_latency(struct pci_dev *pdev)
12728{
12729 if ((pdev->device == PCI_DEVICE_ID_ASP_1200A) ||
12730 (pdev->device == PCI_DEVICE_ID_ASP_ABP940)) {
12731 pci_write_config_byte(pdev, PCI_LATENCY_TIMER, 0);
12732 } else {
12733 u8 latency;
12734 pci_read_config_byte(pdev, PCI_LATENCY_TIMER, &latency);
12735 if (latency < 0x20)
12736 pci_write_config_byte(pdev, PCI_LATENCY_TIMER, 0x20);
12737 }
12738}
12739
12740static int __devinit
12741advansys_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
12742{
12743 int err, ioport;
12744 struct Scsi_Host *shost;
12745 struct asc_board *board;
12746
12747 err = pci_enable_device(pdev);
12748 if (err)
12749 goto fail;
12750 err = pci_request_regions(pdev, DRV_NAME);
12751 if (err)
12752 goto disable_device;
12753 pci_set_master(pdev);
12754 advansys_set_latency(pdev);
12755
12756 err = -ENODEV;
12757 if (pci_resource_len(pdev, 0) == 0)
12758 goto release_region;
12759
12760 ioport = pci_resource_start(pdev, 0);
12761
12762 err = -ENOMEM;
12763 shost = scsi_host_alloc(&advansys_template, sizeof(*board));
12764 if (!shost)
12765 goto release_region;
12766
12767 board = shost_priv(shost);
12768 board->irq = pdev->irq;
12769 board->dev = &pdev->dev;
12770
12771 if (pdev->device == PCI_DEVICE_ID_ASP_ABP940UW ||
12772 pdev->device == PCI_DEVICE_ID_38C0800_REV1 ||
12773 pdev->device == PCI_DEVICE_ID_38C1600_REV1) {
12774 board->flags |= ASC_IS_WIDE_BOARD;
12775 }
12776
12777 err = advansys_board_found(shost, ioport, ASC_IS_PCI);
12778 if (err)
12779 goto free_host;
12780
12781 pci_set_drvdata(pdev, shost);
12782 return 0;
12783
12784 free_host:
12785 scsi_host_put(shost);
12786 release_region:
12787 pci_release_regions(pdev);
12788 disable_device:
12789 pci_disable_device(pdev);
12790 fail:
12791 return err;
12792}
12793
12794static void __devexit advansys_pci_remove(struct pci_dev *pdev)
12795{
12796 advansys_release(pci_get_drvdata(pdev));
12797 pci_release_regions(pdev);
12798 pci_disable_device(pdev);
12799}
12800
12801static struct pci_driver advansys_pci_driver = {
12802 .name = DRV_NAME,
12803 .id_table = advansys_pci_tbl,
12804 .probe = advansys_pci_probe,
12805 .remove = __devexit_p(advansys_pci_remove),
12806};
12807
12808static int __init advansys_init(void)
12809{
12810 int error;
12811
12812 error = isa_register_driver(&advansys_isa_driver,
12813 ASC_IOADR_TABLE_MAX_IX);
12814 if (error)
12815 goto fail;
12816
12817 error = isa_register_driver(&advansys_vlb_driver,
12818 ASC_IOADR_TABLE_MAX_IX);
12819 if (error)
12820 goto unregister_isa;
12821
12822 error = eisa_driver_register(&advansys_eisa_driver);
12823 if (error)
12824 goto unregister_vlb;
12825
12826 error = pci_register_driver(&advansys_pci_driver);
12827 if (error)
12828 goto unregister_eisa;
12829
12830 return 0;
12831
12832 unregister_eisa:
12833 eisa_driver_unregister(&advansys_eisa_driver);
12834 unregister_vlb:
12835 isa_unregister_driver(&advansys_vlb_driver);
12836 unregister_isa:
12837 isa_unregister_driver(&advansys_isa_driver);
12838 fail:
12839 return error;
12840}
12841
12842static void __exit advansys_exit(void)
12843{
12844 pci_unregister_driver(&advansys_pci_driver);
12845 eisa_driver_unregister(&advansys_eisa_driver);
12846 isa_unregister_driver(&advansys_vlb_driver);
12847 isa_unregister_driver(&advansys_isa_driver);
12848}
12849
12850module_init(advansys_init);
12851module_exit(advansys_exit);
12852
12853MODULE_LICENSE("GPL");
12854MODULE_FIRMWARE("advansys/mcode.bin");
12855MODULE_FIRMWARE("advansys/3550.bin");
12856MODULE_FIRMWARE("advansys/38C0800.bin");
12857MODULE_FIRMWARE("advansys/38C1600.bin");
12858