1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54#ifndef MPTBASE_H_INCLUDED
55#define MPTBASE_H_INCLUDED
56
57
58#include "linux_compat.h"
59#include "scsi3.h"
60
61#include "lsi/mpi_type.h"
62#include "lsi/mpi.h"
63#include "lsi/mpi_ioc.h"
64#include "lsi/mpi_cnfg.h"
65#include "lsi/mpi_init.h"
66#include "lsi/mpi_lan.h"
67#include "lsi/mpi_raid.h"
68
69#include "lsi/mpi_fc.h"
70#include "lsi/mpi_targ.h"
71#include "lsi/mpi_tool.h"
72#include "lsi/fc_log.h"
73
74
75
76#ifndef MODULEAUTHOR
77#define MODULEAUTHOR "LSI Logic Corporation"
78#endif
79
80#ifndef COPYRIGHT
81#define COPYRIGHT "Copyright (c) 1999-2004 " MODULEAUTHOR
82#endif
83
84#define MPT_LINUX_VERSION_COMMON "2.05.16"
85#define MPT_LINUX_PACKAGE_NAME "@(#)mptlinux-2.05.16"
86#define WHAT_MAGIC_STRING "@" "(" "#" ")"
87
88#define show_mptmod_ver(s,ver) \
89 printk(KERN_INFO "%s %s\n", s, ver);
90
91
92
93
94
95#define MPT_MAX_ADAPTERS 18
96#define MPT_MAX_PROTOCOL_DRIVERS 16
97#define MPT_MAX_BUS 1
98#define MPT_MAX_FC_DEVICES 255
99#define MPT_MAX_SCSI_DEVICES 16
100#define MPT_LAST_LUN 255
101#define MPT_SENSE_BUFFER_ALLOC 64
102
103#if MPT_SENSE_BUFFER_ALLOC >= 256
104# undef MPT_SENSE_BUFFER_ALLOC
105# define MPT_SENSE_BUFFER_ALLOC 256
106# define MPT_SENSE_BUFFER_SIZE 255
107#else
108# define MPT_SENSE_BUFFER_SIZE MPT_SENSE_BUFFER_ALLOC
109#endif
110
111#define MPT_NAME_LENGTH 32
112
113#define MPT_PROCFS_MPTBASEDIR "mpt"
114
115#define MPT_PROCFS_SUMMARY_ALL_NODE MPT_PROCFS_MPTBASEDIR "/summary"
116#define MPT_PROCFS_SUMMARY_ALL_PATHNAME "/proc/" MPT_PROCFS_SUMMARY_ALL_NODE
117#define MPT_FW_REV_MAGIC_ID_STRING "FwRev="
118
119#define MPT_MAX_REQ_DEPTH 1023
120#define MPT_DEFAULT_REQ_DEPTH 256
121#define MPT_MIN_REQ_DEPTH 128
122
123#define MPT_MAX_REPLY_DEPTH MPT_MAX_REQ_DEPTH
124#define MPT_DEFAULT_REPLY_DEPTH 128
125#define MPT_MIN_REPLY_DEPTH 8
126#define MPT_MAX_REPLIES_PER_ISR 32
127
128#define MPT_MAX_FRAME_SIZE 128
129#define MPT_DEFAULT_FRAME_SIZE 128
130
131#define MPT_REPLY_FRAME_SIZE 0x40
132
133#define MPT_SG_REQ_128_SCALE 1
134#define MPT_SG_REQ_96_SCALE 2
135#define MPT_SG_REQ_64_SCALE 4
136
137#define CAN_SLEEP 1
138#define NO_SLEEP 0
139
140#define MPT_COALESCING_TIMEOUT 0x10
141
142
143
144
145#define MPT_ULTRA320 0x08
146#define MPT_ULTRA160 0x09
147#define MPT_ULTRA2 0x0A
148#define MPT_ULTRA 0x0C
149#define MPT_FAST 0x19
150#define MPT_SCSI 0x32
151#define MPT_ASYNC 0xFF
152
153#define MPT_NARROW 0
154#define MPT_WIDE 1
155
156#define C0_1030 0x08
157#define XL_929 0x01
158
159#ifdef __KERNEL__
160
161
162#include <linux/proc_fs.h>
163
164
165
166
167
168
169
170#define MYIOC_s_INFO_FMT KERN_INFO MYNAM ": %s: "
171#define MYIOC_s_NOTE_FMT KERN_NOTICE MYNAM ": %s: "
172#define MYIOC_s_WARN_FMT KERN_WARNING MYNAM ": %s: WARNING - "
173#define MYIOC_s_ERR_FMT KERN_ERR MYNAM ": %s: ERROR - "
174
175
176
177
178
179typedef enum {
180 MPTBASE_DRIVER,
181 MPTCTL_DRIVER,
182 MPTSCSIH_DRIVER,
183 MPTLAN_DRIVER,
184 MPTSTM_DRIVER,
185 MPTDMP_DRIVER,
186 MPTUNKNOWN_DRIVER
187} MPT_DRIVER_CLASS;
188
189
190
191
192
193typedef union _MPT_FRAME_TRACKER {
194 struct {
195 struct _MPT_FRAME_HDR *forw;
196 struct _MPT_FRAME_HDR *back;
197 u32 arg1;
198 u32 pad;
199 void *argp1;
200#ifndef MPT_SCSI_USE_NEW_EH
201 void *argp2;
202#endif
203 } linkage;
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218 struct {
219 u32 __hdr[2];
220
221
222
223
224 union {
225 u32 MsgContext;
226 struct {
227 u16 req_idx;
228 u8 cb_idx;
229 u8 rsvd;
230 } fld;
231 } msgctxu;
232 } hwhdr;
233
234
235
236
237
238
239} MPT_FRAME_TRACKER;
240
241
242
243
244
245
246
247
248
249typedef struct _MPT_FRAME_HDR {
250 union {
251 MPIHeader_t hdr;
252 SCSIIORequest_t scsireq;
253 SCSIIOReply_t sreply;
254 ConfigReply_t configreply;
255 MPIDefaultReply_t reply;
256 MPT_FRAME_TRACKER frame;
257 } u;
258} MPT_FRAME_HDR;
259
260#define MPT_REQ_MSGFLAGS_DROPME 0x80
261
262
263
264
265typedef struct _MPT_Q_TRACKER {
266 MPT_FRAME_HDR *head;
267 MPT_FRAME_HDR *tail;
268} MPT_Q_TRACKER;
269
270
271typedef struct _MPT_SGL_HDR {
272 SGESimple32_t sge[1];
273} MPT_SGL_HDR;
274
275typedef struct _MPT_SGL64_HDR {
276 SGESimple64_t sge[1];
277} MPT_SGL64_HDR;
278
279
280typedef struct _Q_ITEM {
281 struct _Q_ITEM *forw;
282 struct _Q_ITEM *back;
283} Q_ITEM;
284
285typedef struct _Q_TRACKER {
286 struct _Q_ITEM *head;
287 struct _Q_ITEM *tail;
288} Q_TRACKER;
289
290typedef struct _MPT_DONE_Q {
291 struct _MPT_DONE_Q *forw;
292 struct _MPT_DONE_Q *back;
293 void *argp;
294} MPT_DONE_Q;
295
296typedef struct _DONE_Q_TRACKER {
297 MPT_DONE_Q *head;
298 MPT_DONE_Q *tail;
299} DONE_Q_TRACKER;
300
301
302
303
304
305
306typedef enum {
307 FC919X = 0x0819,
308 FC929X = 0x0829,
309 FC909 = 0x0909,
310 FC919 = 0x0919,
311 FC929 = 0x0929,
312 C1030 = 0x1030,
313 C1035 = 0x1035,
314 FCUNK = 0xFBAD
315} CHIP_TYPE;
316
317
318
319
320
321typedef struct _SYSIF_REGS
322{
323 u32 Doorbell;
324 u32 WriteSequence;
325 u32 Diagnostic;
326 u32 TestBase;
327 u32 DiagRwData;
328 u32 DiagRwAddress;
329 u32 Reserved1[6];
330 u32 IntStatus;
331 u32 IntMask;
332 u32 Reserved2[2];
333 u32 RequestFifo;
334 u32 ReplyFifo;
335 u32 Reserved3[2];
336 u32 HostIndex;
337 u32 Reserved4[15];
338 u32 Fubar;
339 u32 Reserved5[27];
340} SYSIF_REGS;
341
342
343
344
345
346
347
348
349
350
351#define DMP_MAX_PATHS 8
352
353typedef struct _PathInfo {
354 u8 ioc;
355 u8 target;
356 u8 pad;
357 u8 pflags;
358} PathInfo;
359
360#define PATHINFO_FLAGS_OWNED 0x01
361#define PATHINFO_FLAGS_EXISTS 0x02
362#define PATHINFO_FLAGS_AVAILABLE 0x04
363#define PATHINFO_FLAGS_SECONDARY 0x08
364
365#define PFLAGS_EXISTS_AND_AVAIL (PATHINFO_FLAGS_EXISTS|PATHINFO_FLAGS_AVAILABLE)
366#define PFLAGS_AVAIL_AND_OWNED (PATHINFO_FLAGS_AVAILABLE|PATHINFO_FLAGS_OWNED)
367
368typedef struct _ScsiCmndTracker {
369 void *head;
370 void *tail;
371} ScsiCmndTracker;
372
373
374
375
376
377
378typedef struct _VirtDevice {
379 struct _VirtDevice *forw;
380 struct _VirtDevice *back;
381 struct scsi_device *device;
382 rwlock_t VdevLock;
383 int ref_cnt;
384 u8 tflags;
385 u8 ioc_id;
386 u8 target_id;
387 u8 bus_id;
388 u8 minSyncFactor;
389 u8 maxOffset;
390 u8 maxWidth;
391 u8 negoFlags;
392 u8 raidVolume;
393 u8 type;
394 u8 cflags;
395 u8 rsvd1raid;
396 int npaths;
397 u16 fc_phys_lun;
398 u16 fc_xlat_lun;
399 int stall_detected;
400 PathInfo path[DMP_MAX_PATHS];
401 struct timer_list stall_timer;
402 struct timer_list retry_timer;
403 struct timer_list gone_timer;
404 ScsiCmndTracker WaitQ;
405 ScsiCmndTracker SentQ;
406 ScsiCmndTracker DoneQ;
407 u32 num_luns;
408 u32 luns[8];
409 u8 pad[4];
410 u8 inq_data[8];
411
412
413
414
415 u8 uniq_prepad[8];
416 u8 uniq_data[20];
417 u8 pad2[4];
418} VirtDevice;
419
420
421
422
423#define MPT_TARGET_DEFAULT_DV_STATUS 0
424#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,55)
425#define MPT_TARGET_FLAGS_CONFIGURED 0x02
426#define MPT_TARGET_FLAGS_Q_YES 0x08
427#else
428#define MPT_TARGET_FLAGS_VALID_NEGO 0x01
429#define MPT_TARGET_FLAGS_VALID_INQUIRY 0x02
430#define MPT_TARGET_FLAGS_Q_YES 0x08
431#define MPT_TARGET_FLAGS_VALID_56 0x10
432#define MPT_TARGET_FLAGS_SAF_TE_ISSUED 0x20
433#endif
434
435#define MPT_TARGET_NO_NEGO_WIDE 0x01
436#define MPT_TARGET_NO_NEGO_SYNC 0x02
437#define MPT_TARGET_NO_NEGO_QAS 0x04
438
439typedef struct _VirtDevTracker {
440 struct _VirtDevice *head;
441 struct _VirtDevice *tail;
442 rwlock_t VlistLock;
443 int pad;
444} VirtDevTracker;
445
446
447
448
449
450typedef struct {
451 const char *name;
452 mode_t mode;
453 int pad;
454 read_proc_t *read_proc;
455 write_proc_t *write_proc;
456} mpt_proc_entry_t;
457
458#define MPT_PROC_READ_RETURN(buf,start,offset,request,eof,len) \
459do { \
460 len -= offset; \
461 if (len < request) { \
462 *eof = 1; \
463 if (len <= 0) \
464 return 0; \
465 } else \
466 len = request; \
467 *start = buf + offset; \
468 return len; \
469} while (0)
470
471
472
473
474
475
476#define MPT_IOCTL_STATUS_DID_IOCRESET 0x01
477#define MPT_IOCTL_STATUS_RF_VALID 0x02
478#define MPT_IOCTL_STATUS_TIMER_ACTIVE 0x04
479#define MPT_IOCTL_STATUS_SENSE_VALID 0x08
480#define MPT_IOCTL_STATUS_COMMAND_GOOD 0x10
481#define MPT_IOCTL_STATUS_TMTIMER_ACTIVE 0x20
482#define MPT_IOCTL_STATUS_TM_FAILED 0x40
483
484#define MPTCTL_RESET_OK 0x01
485
486typedef struct _MPT_IOCTL {
487 struct _MPT_ADAPTER *ioc;
488 struct timer_list timer;
489 u8 ReplyFrame[MPT_DEFAULT_FRAME_SIZE];
490 u8 sense[MPT_SENSE_BUFFER_ALLOC];
491 int wait_done;
492 u8 rsvd;
493 u8 status;
494 u8 reset;
495 u8 target;
496 void *tmPtr;
497 struct timer_list TMtimer;
498} MPT_IOCTL;
499
500
501
502
503#define MPTCTL_EVENT_LOG_SIZE (0x0000000A)
504typedef struct _mpt_ioctl_events {
505 u32 event;
506 u32 eventContext;
507 int data[2];
508} MPT_IOCTL_EVENTS;
509
510
511
512
513#define MPT_CONFIG_GOOD MPI_IOCSTATUS_SUCCESS
514#define MPT_CONFIG_ERROR 0x002F
515
516
517
518
519
520#define MPT_SCSICFG_NEGOTIATE 0x01
521#define MPT_SCSICFG_NEED_DV 0x02
522#define MPT_SCSICFG_DV_PENDING 0x04
523#define MPT_SCSICFG_DV_NOT_DONE 0x08
524#define MPT_SCSICFG_BLK_NEGO 0x10
525#define MPT_SCSICFG_RELOAD_IOC_PG3 0x20
526
527#define MPT_SCSICFG_USE_NVRAM 0x01
528#define MPT_SCSICFG_ALL_IDS 0x02
529
530
531typedef struct _ScsiCfgData {
532 u32 PortFlags;
533 int *nvram;
534 IOCPage2_t *pIocPg2;
535 IOCPage3_t *pIocPg3;
536 IOCPage4_t *pIocPg4;
537 dma_addr_t IocPg4_dma;
538 int IocPg4Sz;
539 u8 dvStatus[MPT_MAX_SCSI_DEVICES];
540 int isRaid;
541 u8 minSyncFactor;
542 u8 maxSyncOffset;
543 u8 maxBusWidth;
544 u8 busType;
545 u8 sdp1version;
546 u8 sdp1length;
547 u8 sdp0version;
548 u8 sdp0length;
549 u8 dvScheduled;
550 u8 forceDv;
551 u8 noQas;
552 u8 Saf_Te;
553 u8 rsvd[1];
554} ScsiCfgData;
555
556
557
558
559typedef struct _MPT_ADAPTER
560{
561 struct _MPT_ADAPTER *forw;
562 struct _MPT_ADAPTER *back;
563 int id;
564 int pci_irq;
565 char name[MPT_NAME_LENGTH];
566 char *prod_name;
567 volatile SYSIF_REGS *chip;
568 volatile SYSIF_REGS *pio_chip;
569 u32 mem_phys;
570 u32 pio_mem_phys;
571 int mem_size;
572 int alloc_total;
573 u32 last_state;
574 int active;
575 u8 *reply_alloc;
576 dma_addr_t reply_alloc_dma;
577 MPT_FRAME_HDR *reply_frames;
578 dma_addr_t reply_frames_dma;
579 u32 reply_frames_low_dma;
580 int reply_depth;
581 int reply_sz;
582 CHIP_TYPE chip_type;
583
584 u8 *req_alloc;
585 dma_addr_t req_alloc_dma;
586 MPT_FRAME_HDR *req_frames;
587 dma_addr_t req_frames_dma;
588 u32 req_frames_low_dma;
589 int req_depth;
590 int req_sz;
591 spinlock_t FreeQlock;
592 MPT_Q_TRACKER FreeQ;
593
594
595
596
597 u8 *sense_buf_pool;
598 dma_addr_t sense_buf_pool_dma;
599 u32 sense_buf_low_dma;
600 int mtrr_reg;
601 struct pci_dev *pcidev;
602 u8 *memmap;
603 struct Scsi_Host *sh;
604 ScsiCfgData spi_data;
605 MPT_IOCTL *ioctl;
606 struct proc_dir_entry *ioc_dentry;
607 struct _MPT_ADAPTER *alt_ioc;
608 spinlock_t diagLock;
609 int diagPending;
610 u32 biosVersion;
611 int eventTypes;
612 int eventContext;
613 int eventLogSize;
614#ifdef MPTSCSIH_DBG_TIMEOUT
615 int timeout_hard;
616 int timeout_delta;
617 int timeout_cnt;
618 int timeout_maxcnt;
619#endif
620 struct _mpt_ioctl_events *events;
621 u8 *cached_fw;
622 dma_addr_t cached_fw_dma;
623 Q_TRACKER configQ;
624 int hs_reply_idx;
625#ifndef MFCNT
626 u32 pad0;
627#else
628 u32 mfcnt;
629#endif
630 u32 hs_req[MPT_MAX_FRAME_SIZE/sizeof(u32)];
631 u16 hs_reply[MPT_MAX_FRAME_SIZE/sizeof(u16)];
632 IOCFactsReply_t facts;
633 PortFactsReply_t pfacts[2];
634 FCPortPage0_t fc_port_page0[2];
635 LANPage0_t lan_cnfg_page0;
636 LANPage1_t lan_cnfg_page1;
637 u8 FirstWhoInit;
638 u8 upload_fw;
639 u8 reload_fw;
640 u8 pad1[5];
641} MPT_ADAPTER;
642
643
644typedef struct _MPT_ADAPTER_TRACKER {
645 MPT_ADAPTER *head;
646 MPT_ADAPTER *tail;
647} MPT_ADAPTER_TRACKER;
648
649
650
651
652
653
654typedef int (*MPT_CALLBACK)(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply);
655typedef int (*MPT_EVHANDLER)(MPT_ADAPTER *ioc, EventNotificationReply_t *evReply);
656typedef int (*MPT_RESETHANDLER)(MPT_ADAPTER *ioc, int reset_phase);
657
658#define MPT_IOC_PRE_RESET 0
659#define MPT_IOC_POST_RESET 1
660#define MPT_IOC_SETUP_RESET 2
661
662
663
664
665
666typedef struct _MPT_HOST_EVENT {
667 EventNotificationReply_t MpiEvent;
668 u32 pad[6];
669 void *next;
670} MPT_HOST_EVENT;
671
672#define MPT_HOSTEVENT_IOC_BRINGUP 0x91
673#define MPT_HOSTEVENT_IOC_RECOVER 0x92
674
675
676
677
678typedef struct _mpt_sge {
679 u32 FlagsLength;
680 dma_addr_t Address;
681} MptSge_t;
682
683#define mpt_addr_size() \
684 ((sizeof(dma_addr_t) == sizeof(u64)) ? MPI_SGE_FLAGS_64_BIT_ADDRESSING : \
685 MPI_SGE_FLAGS_32_BIT_ADDRESSING)
686
687#define mpt_msg_flags() \
688 ((sizeof(dma_addr_t) == sizeof(u64)) ? MPI_SCSIIO_MSGFLGS_SENSE_WIDTH_64 : \
689 MPI_SCSIIO_MSGFLGS_SENSE_WIDTH_32)
690
691
692
693
694
695#ifdef MPT_DEBUG
696#define dprintk(x) printk x
697#else
698#define dprintk(x)
699#endif
700
701#ifdef MPT_DEBUG_INIT
702#define dinitprintk(x) printk x
703#define DBG_DUMP_FW_REQUEST_FRAME(mfp) \
704 { int i, n = 10; \
705 u32 *m = (u32 *)(mfp); \
706 printk(KERN_INFO " "); \
707 for (i=0; i<n; i++) \
708 printk(" %08x", le32_to_cpu(m[i])); \
709 printk("\n"); \
710 }
711#else
712#define dinitprintk(x)
713#define DBG_DUMP_FW_REQUEST_FRAME(mfp)
714#endif
715
716#ifdef MPT_DEBUG_EXIT
717#define dexitprintk(x) printk x
718#else
719#define dexitprintk(x)
720#endif
721
722#ifdef MPT_DEBUG_RESET
723#define drsprintk(x) printk x
724#else
725#define drsprintk(x)
726#endif
727
728#ifdef MPT_DEBUG_HANDSHAKE
729#define dhsprintk(x) printk x
730#else
731#define dhsprintk(x)
732#endif
733
734
735#if defined(MPT_DEBUG_MSG_FRAME)
736#define dmfprintk(x) printk x
737#else
738#define dmfprintk(x)
739#endif
740
741#ifdef MPT_DEBUG_IRQ
742#define dirqprintk(x) printk x
743#else
744#define dirqprintk(x)
745#endif
746
747#ifdef MPT_DEBUG_SG
748#define dsgprintk(x) printk x
749#else
750#define dsgprintk(x)
751#endif
752
753#if defined(MPT_DEBUG_DL) || defined(MPT_DEBUG)
754#define ddlprintk(x) printk x
755#else
756#define ddlprintk(x)
757#endif
758
759
760#ifdef MPT_DEBUG_DV
761#define ddvprintk(x) printk x
762#else
763#define ddvprintk(x)
764#endif
765
766#if defined(MPT_DEBUG_DV) || defined(MPT_DEBUG_DV_TINY)
767#define ddvtprintk(x) printk x
768#else
769#define ddvtprintk(x)
770#endif
771
772#ifdef MPT_DEBUG_IOCTL
773#define dctlprintk(x) printk x
774#else
775#define dctlprintk(x)
776#endif
777
778#ifdef MPT_DEBUG_RESET
779#define dtmprintk(x) printk x
780#else
781#define dtmprintk(x)
782#endif
783
784#ifdef MPT_DEBUG_NEH
785#define nehprintk(x) printk x
786#else
787#define nehprintk(x)
788#endif
789
790#if defined(MPT_DEBUG_CONFIG) || defined(MPT_DEBUG)
791#define dcprintk(x) printk x
792#else
793#define dcprintk(x)
794#endif
795
796#if defined(MPT_DEBUG_SCSI) || defined(MPT_DEBUG) || defined(MPT_DEBUG_MSG_FRAME)
797#define dsprintk(x) printk x
798#else
799#define dsprintk(x)
800#endif
801
802
803#define MPT_INDEX_2_MFPTR(ioc,idx) \
804 (MPT_FRAME_HDR*)( (u8*)(ioc)->req_frames + (ioc)->req_sz * (idx) )
805
806#define MFPTR_2_MPT_INDEX(ioc,mf) \
807 (int)( ((u8*)mf - (u8*)(ioc)->req_frames) / (ioc)->req_sz )
808
809#define MPT_INDEX_2_RFPTR(ioc,idx) \
810 (MPT_FRAME_HDR*)( (u8*)(ioc)->reply_frames + (ioc)->req_sz * (idx) )
811
812#define Q_INIT(q,type) (q)->head = (q)->tail = (type*)(q)
813#define Q_IS_EMPTY(q) ((Q_ITEM*)(q)->head == (Q_ITEM*)(q))
814
815#define Q_ADD_TAIL(qt,i,type) { \
816 Q_TRACKER *_qt = (Q_TRACKER*)(qt); \
817 Q_ITEM *oldTail = _qt->tail; \
818 (i)->forw = (type*)_qt; \
819 (i)->back = (type*)oldTail; \
820 oldTail->forw = (Q_ITEM*)(i); \
821 _qt->tail = (Q_ITEM*)(i); \
822}
823
824#define Q_ADD_HEAD(qt,i,type) { \
825 Q_TRACKER *_qt = (Q_TRACKER*)(qt); \
826 Q_ITEM *oldHead = _qt->head; \
827 (i)->forw = (type*)oldHead; \
828 (i)->back = (type*)_qt; \
829 oldHead->back = (Q_ITEM*)(i); \
830 _qt->head = (Q_ITEM*)(i); \
831}
832
833#define Q_DEL_ITEM(i) { \
834 Q_ITEM *_forw = (Q_ITEM*)(i)->forw; \
835 Q_ITEM *_back = (Q_ITEM*)(i)->back; \
836 _back->forw = _forw; \
837 _forw->back = _back; \
838}
839
840#define SWAB4(value) \
841 (u32)( (((value) & 0x000000ff) << 24) \
842 | (((value) & 0x0000ff00) << 8) \
843 | (((value) & 0x00ff0000) >> 8) \
844 | (((value) & 0xff000000) >> 24) )
845
846
847#if defined(MPT_DEBUG) || defined(MPT_DEBUG_MSG_FRAME)
848#define DBG_DUMP_REPLY_FRAME(mfp) \
849 { u32 *m = (u32 *)(mfp); \
850 int i, n = (le32_to_cpu(m[0]) & 0x00FF0000) >> 16; \
851 printk(KERN_INFO " "); \
852 for (i=0; i<n; i++) \
853 printk(" %08x", le32_to_cpu(m[i])); \
854 printk("\n"); \
855 }
856#define DBG_DUMP_REQUEST_FRAME_HDR(mfp) \
857 { int i, n = 3; \
858 u32 *m = (u32 *)(mfp); \
859 printk(KERN_INFO " "); \
860 for (i=0; i<n; i++) \
861 printk(" %08x", le32_to_cpu(m[i])); \
862 printk("\n"); \
863 }
864#else
865#define DBG_DUMP_REPLY_FRAME(mfp)
866#define DBG_DUMP_REQUEST_FRAME_HDR(mfp)
867#endif
868
869
870
871
872
873
874
875
876
877
878
879
880typedef struct _MPT_LOCAL_REPLY {
881 ConfigPageHeader_t header;
882 int completion;
883 u8 sense[SCSI_STD_SENSE_BYTES];
884 u8 scsiStatus;
885 u8 skip;
886 u32 pad;
887} MPT_LOCAL_REPLY;
888
889#define MPT_HOST_BUS_UNKNOWN (0xFF)
890#define MPT_HOST_TOO_MANY_TM (0x05)
891#define MPT_HOST_NVRAM_INVALID (0xFFFFFFFF)
892#define MPT_HOST_NO_CHAIN (0xFFFFFFFF)
893#define MPT_NVRAM_MASK_TIMEOUT (0x000000FF)
894#define MPT_NVRAM_SYNC_MASK (0x0000FF00)
895#define MPT_NVRAM_SYNC_SHIFT (8)
896#define MPT_NVRAM_DISCONNECT_ENABLE (0x00010000)
897#define MPT_NVRAM_ID_SCAN_ENABLE (0x00020000)
898#define MPT_NVRAM_LUN_SCAN_ENABLE (0x00040000)
899#define MPT_NVRAM_TAG_QUEUE_ENABLE (0x00080000)
900#define MPT_NVRAM_WIDE_DISABLE (0x00100000)
901#define MPT_NVRAM_BOOT_CHOICE (0x00200000)
902
903#ifdef MPT_SCSI_USE_NEW_EH
904
905
906
907#define TM_STATE_NONE (0)
908#define TM_STATE_IN_PROGRESS (1)
909#define TM_STATE_ERROR (2)
910#endif
911
912typedef struct _MPT_SCSI_HOST {
913 MPT_ADAPTER *ioc;
914 int port;
915 u32 pad0;
916 struct scsi_cmnd **ScsiLookup;
917
918
919
920
921
922 int *ReqToChain;
923 int *ChainToChain;
924 u8 *ChainBuffer;
925 dma_addr_t ChainBufferDMA;
926 MPT_Q_TRACKER FreeChainQ;
927 spinlock_t FreeChainQlock;
928 u32 qtag_tick;
929 VirtDevice **Targets;
930 MPT_LOCAL_REPLY *pLocal;
931 struct timer_list timer;
932 struct timer_list TMtimer;
933
934
935
936 u8 *memQ;
937 DONE_Q_TRACKER freeQ;
938 DONE_Q_TRACKER doneQ;
939 DONE_Q_TRACKER pendingQ;
940 MPT_Q_TRACKER taskQ;
941 spinlock_t freedoneQlock;
942 int taskQcnt;
943 int num_chain;
944 int max_sge;
945 u8 numTMrequests;
946 u8 tmPending;
947 u8 resetPending;
948 u8 is_spi;
949 u8 negoNvram;
950 u8 is_multipath;
951#ifdef MPT_SCSI_USE_NEW_EH
952 u8 tmState;
953 u8 rsvd[1];
954#else
955 u8 rsvd[2];
956#endif
957 MPT_FRAME_HDR *tmPtr;
958 MPT_FRAME_HDR *cmdPtr;
959 struct scsi_cmnd *abortSCpnt;
960 MPT_LOCAL_REPLY localReply;
961 unsigned long hard_resets;
962 unsigned long soft_resets;
963 unsigned long timeouts;
964 ushort sel_timeout[MPT_MAX_FC_DEVICES];
965} MPT_SCSI_HOST;
966
967
968
969
970
971typedef struct _scPrivate {
972 struct scsi_cmnd *forw;
973 struct scsi_cmnd *back;
974 void *p1;
975 void *p2;
976 u8 io_path_id;
977 u8 pad[7];
978} scPrivate;
979
980
981
982
983
984
985
986struct scsi_cmnd;
987
988
989
990
991typedef struct _DmpServices {
992 VirtDevTracker VdevList;
993 struct semaphore *Daemon;
994 int (*ScsiPathSelect)
995 (struct scsi_cmnd *, MPT_SCSI_HOST **hd, int *target, int *lun);
996 int (*DmpIoDoneChk)
997 (MPT_SCSI_HOST *, struct scsi_cmnd *,
998 SCSIIORequest_t *,
999 SCSIIOReply_t *);
1000 void (*mptscsih_scanVlist)
1001 (MPT_SCSI_HOST *, int portnum);
1002 int (*ScsiAbort)
1003 (struct scsi_cmnd *);
1004 int (*ScsiBusReset)
1005 (struct scsi_cmnd *);
1006} DmpServices_t;
1007
1008
1009
1010
1011
1012typedef struct _x_config_parms {
1013 Q_ITEM linkage;
1014 struct timer_list timer;
1015 ConfigPageHeader_t *hdr;
1016 dma_addr_t physAddr;
1017 int wait_done;
1018 u32 pageAddr;
1019 u8 action;
1020 u8 dir;
1021 u8 timeout;
1022 u8 pad1;
1023 u16 status;
1024 u16 pad2;
1025} CONFIGPARMS;
1026
1027
1028
1029
1030
1031extern int mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass);
1032extern void mpt_deregister(int cb_idx);
1033extern int mpt_event_register(int cb_idx, MPT_EVHANDLER ev_cbfunc);
1034extern void mpt_event_deregister(int cb_idx);
1035extern int mpt_reset_register(int cb_idx, MPT_RESETHANDLER reset_func);
1036extern void mpt_reset_deregister(int cb_idx);
1037extern int mpt_register_ascqops_strings(void *ascqTable, int ascqtbl_sz, const char **opsTable);
1038extern void mpt_deregister_ascqops_strings(void);
1039extern MPT_FRAME_HDR *mpt_get_msg_frame(int handle, int iocid);
1040extern void mpt_free_msg_frame(int handle, int iocid, MPT_FRAME_HDR *mf);
1041extern void mpt_put_msg_frame(int handle, int iocid, MPT_FRAME_HDR *mf);
1042extern void mpt_add_sge(char *pAddr, u32 flagslength, dma_addr_t dma_addr);
1043extern void mpt_add_chain(char *pAddr, u8 next, u16 length, dma_addr_t dma_addr);
1044
1045extern int mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 *req, int sleepFlag);
1046extern int mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply, int maxwait, int sleepFlag);
1047extern int mpt_verify_adapter(int iocid, MPT_ADAPTER **iocpp);
1048extern MPT_ADAPTER *mpt_adapter_find_first(void);
1049extern MPT_ADAPTER *mpt_adapter_find_next(MPT_ADAPTER *prev);
1050extern u32 mpt_GetIocState(MPT_ADAPTER *ioc, int cooked);
1051extern void mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buf, int *size, int len, int showlan);
1052extern int mpt_HardResetHandler(MPT_ADAPTER *ioc, int sleepFlag);
1053extern int mpt_config(MPT_ADAPTER *ioc, CONFIGPARMS *cfg);
1054extern int mpt_toolbox(MPT_ADAPTER *ioc, CONFIGPARMS *cfg);
1055extern void mpt_alloc_fw_memory(MPT_ADAPTER *ioc, int size);
1056extern void mpt_free_fw_memory(MPT_ADAPTER *ioc);
1057extern int mpt_findImVolumes(MPT_ADAPTER *ioc);
1058extern int mpt_read_ioc_pg_3(MPT_ADAPTER *ioc);
1059
1060
1061
1062
1063extern MPT_ADAPTER *mpt_adapters[MPT_MAX_ADAPTERS];
1064extern struct proc_dir_entry *mpt_proc_root_dir;
1065extern DmpServices_t *DmpService;
1066
1067extern int mpt_lan_index;
1068extern int mpt_stm_index;
1069
1070extern void *mpt_v_ASCQ_TablePtr;
1071extern const char **mpt_ScsiOpcodesPtr;
1072extern int mpt_ASCQ_TableSz;
1073
1074
1075#endif
1076
1077
1078
1079
1080#ifndef MIN
1081#define MIN(a, b) (((a) < (b)) ? (a) : (b))
1082#endif
1083#ifndef MAX
1084#define MAX(a, b) (((a) > (b)) ? (a) : (b))
1085#endif
1086
1087#ifndef offsetof
1088#define offsetof(t, m) ((size_t) (&((t *)0)->m))
1089#endif
1090
1091#if defined(__alpha__) || defined(__sparc_v9__) || defined(__ia64__) || defined(__x86_64__)
1092#define CAST_U32_TO_PTR(x) ((void *)(u64)x)
1093#define CAST_PTR_TO_U32(x) ((u32)(u64)x)
1094#else
1095#define CAST_U32_TO_PTR(x) ((void *)x)
1096#define CAST_PTR_TO_U32(x) ((u32)x)
1097#endif
1098
1099#define MPT_PROTOCOL_FLAGS_c_c_c_c(pflags) \
1100 ((pflags) & MPI_PORTFACTS_PROTOCOL_INITIATOR) ? 'I' : 'i', \
1101 ((pflags) & MPI_PORTFACTS_PROTOCOL_TARGET) ? 'T' : 't', \
1102 ((pflags) & MPI_PORTFACTS_PROTOCOL_LAN) ? 'L' : 'l', \
1103 ((pflags) & MPI_PORTFACTS_PROTOCOL_LOGBUSADDR) ? 'B' : 'b'
1104
1105
1106
1107
1108
1109
1110#define MPT_TRANSFER_IOC_TO_HOST (0x00000000)
1111#define MPT_TRANSFER_HOST_TO_IOC (0x04000000)
1112#define MPT_SGE_FLAGS_LAST_ELEMENT (0x80000000)
1113#define MPT_SGE_FLAGS_END_OF_BUFFER (0x40000000)
1114#define MPT_SGE_FLAGS_LOCAL_ADDRESS (0x08000000)
1115#define MPT_SGE_FLAGS_DIRECTION (0x04000000)
1116#define MPT_SGE_FLAGS_ADDRESSING (mpt_addr_size() << MPI_SGE_FLAGS_SHIFT)
1117#define MPT_SGE_FLAGS_END_OF_LIST (0x01000000)
1118
1119#define MPT_SGE_FLAGS_TRANSACTION_ELEMENT (0x00000000)
1120#define MPT_SGE_FLAGS_SIMPLE_ELEMENT (0x10000000)
1121#define MPT_SGE_FLAGS_CHAIN_ELEMENT (0x30000000)
1122#define MPT_SGE_FLAGS_ELEMENT_MASK (0x30000000)
1123
1124#define MPT_SGE_FLAGS_SSIMPLE_READ \
1125 (MPT_SGE_FLAGS_LAST_ELEMENT | \
1126 MPT_SGE_FLAGS_END_OF_BUFFER | \
1127 MPT_SGE_FLAGS_END_OF_LIST | \
1128 MPT_SGE_FLAGS_SIMPLE_ELEMENT | \
1129 MPT_SGE_FLAGS_ADDRESSING | \
1130 MPT_TRANSFER_IOC_TO_HOST)
1131#define MPT_SGE_FLAGS_SSIMPLE_WRITE \
1132 (MPT_SGE_FLAGS_LAST_ELEMENT | \
1133 MPT_SGE_FLAGS_END_OF_BUFFER | \
1134 MPT_SGE_FLAGS_END_OF_LIST | \
1135 MPT_SGE_FLAGS_SIMPLE_ELEMENT | \
1136 MPT_SGE_FLAGS_ADDRESSING | \
1137 MPT_TRANSFER_HOST_TO_IOC)
1138
1139
1140#endif
1141
1142