1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at
9 * http://www.opensource.org/licenses/cddl1.txt.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright (c) 2004-2012 Emulex. All rights reserved.
24 * Use is subject to license terms.
25 * Copyright 2018 OmniOS Community Edition (OmniOSce) Association.
26 * Copyright 2020 RackTop Systems, Inc.
27 */
28
29#ifndef _EMLXS_FC_H
30#define	_EMLXS_FC_H
31
32#ifdef	__cplusplus
33extern "C" {
34#endif
35
36typedef struct emlxs_buf
37{
38	fc_packet_t		*pkt;		/* scsi_pkt reference */
39	struct emlxs_port	*port;		/* pointer to port */
40	void			*bmp;		/* Save the buffer pointer */
41						/* list for later use. */
42	struct emlxs_buf	*fc_fwd;	/* Use it by chip_Q */
43	struct emlxs_buf	*fc_bkwd;	/* Use it by chip_Q */
44	struct emlxs_buf	*next;		/* Use it when the iodone */
45	struct emlxs_node 	*node;
46	void			*channel;	/* Save channel and used by */
47						/* abort */
48	struct emlxs_buf	*fpkt;		/* Flush pkt pointer */
49	struct XRIobj		*xrip;		/* Exchange resource */
50	IOCBQ			iocbq;
51	kmutex_t		mtx;
52	uint32_t		pkt_flags;
53	uint32_t		iotag;		/* iotag for this cmd */
54	uint32_t		ticks;		/* save the timeout ticks */
55						/* for the fc_packet_t */
56	uint32_t		abort_attempts;
57	uint32_t		lun;
58#define	EMLXS_LUN_NONE		0xFFFFFFFF
59
60	uint32_t		class;		/* Save class and used by */
61						/* abort */
62	uint32_t		ucmd;		/* Unsolicted command that */
63						/* this packet is responding */
64						/* to, if any */
65	int32_t			flush_count;	/* Valid only in flush pkts */
66	uint32_t		did;
67
68#ifdef SFCT_SUPPORT
69	kmutex_t		fct_mtx;
70	fc_packet_t		*fct_pkt;
71	fct_cmd_t		*fct_cmd;
72
73	uint8_t			fct_type;
74
75#define	EMLXS_FCT_ELS_CMD		0x01	/* Unsolicted */
76#define	EMLXS_FCT_ELS_REQ		0x02	/* Solicited */
77#define	EMLXS_FCT_ELS_RSP		0x04
78#define	EMLXS_FCT_CT_REQ		0x08	/* Solicited */
79#define	EMLXS_FCT_FCP_CMD		0x10	/* Unsolicted */
80#define	EMLXS_FCT_FCP_DATA		0x20
81#define	EMLXS_FCT_FCP_STATUS		0x40
82
83
84	uint8_t			fct_flags;
85
86#define	EMLXS_FCT_SEND_STATUS		0x01
87#define	EMLXS_FCT_ABORT_INP		0x02
88#define	EMLXS_FCT_IO_INP		0x04
89#define	EMLXS_FCT_PLOGI_RECEIVED	0x10
90#define	EMLXS_FCT_REGISTERED		0x20
91
92	uint16_t		fct_state;
93
94#define	EMLXS_FCT_FCP_CMD_RECEIVED	1
95#define	EMLXS_FCT_ELS_CMD_RECEIVED	2
96#define	EMLXS_FCT_CMD_POSTED		3
97#define	EMLXS_FCT_CMD_WAITQ		4
98#define	EMLXS_FCT_SEND_CMD_RSP		5
99#define	EMLXS_FCT_SEND_ELS_RSP		6
100#define	EMLXS_FCT_SEND_ELS_REQ		7
101#define	EMLXS_FCT_SEND_CT_REQ		8
102#define	EMLXS_FCT_RSP_PENDING		9
103#define	EMLXS_FCT_REQ_PENDING		10
104#define	EMLXS_FCT_REG_PENDING		11
105#define	EMLXS_FCT_REG_COMPLETE		12
106#define	EMLXS_FCT_OWNED			13
107#define	EMLXS_FCT_SEND_FCP_DATA		14
108#define	EMLXS_FCT_SEND_FCP_STATUS	15
109#define	EMLXS_FCT_DATA_PENDING		16
110#define	EMLXS_FCT_STATUS_PENDING	17
111#define	EMLXS_FCT_PKT_COMPLETE		18
112#define	EMLXS_FCT_PKT_FCPRSP_COMPLETE	19
113#define	EMLXS_FCT_PKT_ELSRSP_COMPLETE	20
114#define	EMLXS_FCT_PKT_ELSCMD_COMPLETE	21
115#define	EMLXS_FCT_PKT_CTCMD_COMPLETE	22
116#define	EMLXS_FCT_REQ_COMPLETE		23
117#define	EMLXS_FCT_CLOSE_PENDING		24
118#define	EMLXS_FCT_ABORT_PENDING		25
119#define	EMLXS_FCT_ABORT_DONE		26
120#define	EMLXS_FCT_IO_DONE		27
121
122#define	EMLXS_FCT_IOCB_ISSUED		256 /* For tracing only */
123#define	EMLXS_FCT_IOCB_COMPLETE		257 /* For tracing only */
124
125	stmf_data_buf_t		*fct_buf;
126
127#endif /* SFCT_SUPPORT */
128
129#ifdef SAN_DIAG_SUPPORT
130	hrtime_t		sd_start_time;
131#endif /* SAN_DIAG_SUPPORT */
132
133} emlxs_buf_t;
134
135
136
137#ifdef FCT_IO_TRACE
138#define	EMLXS_FCT_STATE_CHG(_fct_cmd, _cmd_sbp, _state)	\
139	(_cmd_sbp)->fct_state = _state;			\
140	emlxs_fct_io_trace((_cmd_sbp)->port, _fct_cmd, _state)
141#else
142/* define to set fct_state */
143#define	EMLXS_FCT_STATE_CHG(_fct_cmd, _cmd_sbp, _state)	\
144	(_cmd_sbp)->fct_state = _state
145#endif /* FCT_IO_TRACE */
146
147
148/* pkt_flags */
149#define	PACKET_IN_COMPLETION	0x00000001
150#define	PACKET_IN_TXQ		0x00000002
151#define	PACKET_IN_CHIPQ		0x00000004
152#define	PACKET_IN_DONEQ		0x00000008
153
154#define	PACKET_FCP_RESET	0x00000030
155#define	PACKET_FCP_TGT_RESET	0x00000010
156#define	PACKET_FCP_LUN_RESET	0x00000020
157#define	PACKET_POLLED		0x00000040
158
159#ifdef EMLXS_I386
160#define	PACKET_FCP_SWAPPED	0x00000100
161#define	PACKET_ELS_SWAPPED	0x00000200
162#define	PACKET_CT_SWAPPED	0x00000400
163#define	PACKET_CSP_SWAPPED	0x00000800
164#endif	/* EMLXS_I386 */
165
166#define	PACKET_STALE		0x00001000
167
168#define	PACKET_IN_TIMEOUT	0x00010000
169#define	PACKET_IN_FLUSH		0x00020000
170#define	PACKET_IN_ABORT		0x00040000
171#define	PACKET_XRI_CLOSED	0x00080000 /* An XRI abort/close was issued */
172
173#define	PACKET_CHIP_COMP	0x00100000
174#define	PACKET_COMPLETED	0x00200000
175#define	PACKET_ULP_OWNED	0x00400000
176
177#define	PACKET_STATE_VALID	0x01000000
178#define	PACKET_FCP_RSP_VALID	0x02000000
179#define	PACKET_ELS_RSP_VALID	0x04000000
180#define	PACKET_CT_RSP_VALID	0x08000000
181
182#define	PACKET_DELAY_REQUIRED	0x10000000
183#define	PACKET_ALLOCATED	0x40000000
184#define	PACKET_VALID		0x80000000
185
186
187#define	STALE_PACKET		((emlxs_buf_t *)0xFFFFFFFF)
188
189
190/*
191 * From fc_error.h pkt_reason (except for state = NPORT_RJT, FABRIC_RJT,
192 * NPORT_BSY, FABRIC_BSY, LS_RJT, BA_RJT, FS_RJT)
193 *
194 * FCA unique error codes can begin after FC_REASON_FCA_UNIQUE.
195 * Each FCA defines its own set with values greater >= 0x7F
196 */
197#define	FC_REASON_FCA_DEFINED   0x100
198
199
200/*
201 * Device VPD save area
202 */
203
204typedef struct emlxs_vpd
205{
206	uint32_t	biuRev;
207	uint32_t	smRev;
208	uint32_t	smFwRev;
209	uint32_t	endecRev;
210	uint16_t	rBit;
211	uint8_t		fcphHigh;
212	uint8_t		fcphLow;
213	uint8_t		feaLevelHigh;
214	uint8_t		feaLevelLow;
215
216	uint32_t	postKernRev;
217	char		postKernName[32];
218
219	uint32_t	opFwRev;
220	char		opFwName[32];
221	char		opFwLabel[32];
222
223	uint32_t	sli1FwRev;
224	char		sli1FwName[32];
225	char		sli1FwLabel[32];
226
227	uint32_t	sli2FwRev;
228	char		sli2FwName[32];
229	char		sli2FwLabel[32];
230
231	uint32_t	sli3FwRev;
232	char		sli3FwName[32];
233	char		sli3FwLabel[32];
234
235	uint32_t	sli4FwRev;
236	char		sli4FwName[32];
237	char		sli4FwLabel[32];
238
239	char		fw_version[32];
240	char		fw_label[32];
241
242	char		fcode_version[32];
243	char		boot_version[32];
244
245	char		serial_num[32];
246	char		part_num[32];
247	char		port_num[20];
248	char		eng_change[32];
249	char		manufacturer[80];
250	char		model[80];
251	char		model_desc[256];
252	char		prog_types[256];
253	char		id[256];
254
255	uint32_t	port_index;
256	uint16_t	link_speed;
257} emlxs_vpd_t;
258
259
260typedef struct emlxs_queue
261{
262	void		*q_first;	/* queue first element */
263	void		*q_last;	/* queue last element */
264	uint16_t	q_cnt;	/* current length of queue */
265	uint16_t	q_max;	/* max length queue can get */
266} emlxs_queue_t;
267typedef emlxs_queue_t Q;
268
269
270
271/*
272 * This structure is used when allocating a buffer pool.
273 * Note: this should be identical to gasket buf_info (fldl.h).
274 */
275typedef struct emlxs_buf_info
276{
277	int32_t		size;	/* Specifies the number of bytes to allocate. */
278	int32_t		align;	/* The desired address boundary. */
279
280	int32_t		flags;
281
282#define	FC_MBUF_DMA		0x01	/* blocks are for DMA */
283#define	FC_MBUF_PHYSONLY	0x02	/* For malloc - map a given virtual */
284					/* address to physical address (skip */
285					/* the malloc). */
286					/* For free - just unmap the given */
287					/* physical address (skip the free). */
288#define	FC_MBUF_IOCTL		0x04	/* called from dfc_ioctl */
289#define	FC_MBUF_UNLOCK		0x08	/* called with driver unlocked */
290#define	FC_MBUF_SNGLSG		0x10	/* allocate a single contiguous */
291					/* physical memory */
292
293	uint64_t	phys;		/* specifies physical buffer pointer */
294	void		*virt;		/* specifies virtual buffer pointer */
295	void		*data_handle;
296	void		*dma_handle;
297} emlxs_buf_info_t;
298typedef emlxs_buf_info_t MBUF_INFO;
299
300
301#define	EMLXS_MAX_HBQ   	16	/* Max HBQs handled by firmware */
302#define	EMLXS_ELS_HBQ_ID	0
303#define	EMLXS_IP_HBQ_ID		1
304#define	EMLXS_CT_HBQ_ID		2
305#define	EMLXS_FCT_HBQ_ID	3
306
307#ifdef SFCT_SUPPORT
308#define	EMLXS_NUM_HBQ		4	/* Number of HBQs supported by driver */
309#else
310#define	EMLXS_NUM_HBQ		3	/* Number of HBQs supported by driver */
311#endif /* SFCT_SUPPORT */
312
313
314/*
315 * An IO Channel is a object that comprises a xmit/cmpl
316 * path for IOs.
317 * For SLI3, an IO path maps to a ring (cmd/rsp)
318 * For SLI4, an IO path map to a queue pair (WQ/CQ)
319 */
320typedef struct emlxs_channel
321{
322	struct emlxs_hba *hba;			/* ptr to hba for channel */
323	void		*iopath;		/* ptr to SLI3/4 io path */
324
325	kmutex_t	rsp_lock;
326	IOCBQ		*rsp_head;	/* deferred completion head */
327	IOCBQ		*rsp_tail;	/* deferred completion tail */
328	emlxs_thread_t  intr_thread;
329
330
331	uint16_t	channelno;
332	uint16_t	chan_flag;
333
334#define	EMLXS_NEEDS_TRIGGER 1
335
336	/* Protected by EMLXS_TX_CHANNEL_LOCK */
337	emlxs_queue_t	nodeq;			/* Node service queue */
338
339	kmutex_t	channel_cmd_lock;
340	uint32_t	timeout;
341
342	/* Channel command counters */
343	uint32_t	ulpSendCmd;
344	uint32_t	ulpCmplCmd;
345	uint32_t	hbaSendCmd;
346	uint32_t	hbaCmplCmd;
347	uint32_t	hbaSendCmd_sbp;
348	uint32_t	hbaCmplCmd_sbp;
349
350} emlxs_channel_t;
351typedef emlxs_channel_t CHANNEL;
352
353/*
354 * Should be able to handle max number of io paths for a
355 * SLI4 HBA (EMLXS_MAX_WQS) or for a SLI3 HBA (MAX_RINGS)
356 */
357#define	MAX_CHANNEL EMLXS_MSI_MAX_INTRS
358
359
360/* Structure used to access adapter rings */
361typedef struct emlxs_ring
362{
363	void		*fc_cmdringaddr;	/* virtual offset for cmd */
364						/* rings */
365	void		*fc_rspringaddr;	/* virtual offset for rsp */
366						/* rings */
367
368	void		*fc_mpon;		/* index ptr for match */
369						/* structure */
370	void		*fc_mpoff;		/* index ptr for match */
371						/* structure */
372	struct emlxs_hba *hba;			/* ptr to hba for ring */
373
374	uint8_t		fc_numCiocb;		/* number of command iocb's */
375						/* per ring */
376	uint8_t		fc_numRiocb;		/* number of response iocb's */
377						/* per ring */
378	uint8_t		fc_rspidx;		/* current index in response */
379						/* ring */
380	uint8_t		fc_cmdidx;		/* current index in command */
381						/* ring */
382	uint8_t		fc_port_rspidx;
383	uint8_t		fc_port_cmdidx;
384	uint8_t		ringno;
385
386	uint16_t	fc_missbufcnt;		/* buf cnt we need to repost */
387	CHANNEL		*channelp;
388
389
390} emlxs_ring_t;
391typedef emlxs_ring_t RING;
392
393
394#ifdef SAN_DIAG_SUPPORT
395/*
396 * Although right now it's just 1 field, SAN Diag anticipates that this
397 * structure will grow in the future.
398 */
399typedef struct sd_timestat_level0 {
400	int		count;
401} sd_timestat_level0_t;
402#endif
403
404typedef struct emlxs_node
405{
406	struct emlxs_node	*nlp_list_next;
407	struct emlxs_node	*nlp_list_prev;
408
409	NAME_TYPE		nlp_portname;	/* port name */
410	NAME_TYPE		nlp_nodename;	/* node name */
411
412	uint32_t		nlp_DID;	/* fibre channel D_ID */
413
414	uint16_t		nlp_Rpi;	/* login id returned by */
415						/* REG_LOGIN */
416	uint16_t		nlp_Xri;	/* login id returned by */
417						/* REG_LOGIN */
418
419	uint8_t			nlp_fcp_info;	/* Remote class info */
420
421	/* nlp_fcp_info */
422#define	NLP_FCP_TGT_DEVICE	0x10	/* FCP TGT device */
423#define	NLP_FCP_INI_DEVICE	0x20	/* FCP Initiator device */
424#define	NLP_FCP_2_DEVICE	0x40	/* FCP-2 TGT device */
425#define	NLP_EMLX_VPORT		0x80    /* Virtual port */
426
427	uint8_t			dfc_state;
428#define	EMLXS_SET_DFC_STATE(_n, _state)	if (_n && _n->nlp_active)\
429		{(_n)->dfc_state = (_state); }
430
431	uint32_t		nlp_force_rscn;
432	uint32_t		nlp_tag;	/* Tag used by port_offline */
433	uint32_t		flag;
434
435#define	NODE_POOL_ALLOCATED 	0x00000001
436
437	SERV_PARM		sparm;
438
439	/* Protected by EMLXS_TX_CHANNEL_LOCK */
440	uint32_t		nlp_active;	/* Node active flag */
441	uint32_t		nlp_base;
442	uint32_t		nlp_flag[MAX_CHANNEL];	/* Node level channel */
443							/* flags */
444
445	/* nlp_flag */
446#define	NLP_CLOSED		0x1
447#define	NLP_OFFLINE		0x2
448#define	NLP_RPI_XRI		0x4
449
450	uint32_t		nlp_tics[MAX_CHANNEL];	/* gate timeout */
451	emlxs_queue_t		nlp_tx[MAX_CHANNEL];	/* Transmit Q head */
452	emlxs_queue_t		nlp_ptx[MAX_CHANNEL];	/* Priority transmit */
453							/* Queue head */
454	void			*nlp_next[MAX_CHANNEL];	/* Service Request */
455							/* Queue pointer used */
456							/* when node needs */
457							/* servicing */
458#ifdef DHCHAP_SUPPORT
459	emlxs_node_dhc_t	node_dhc;
460#endif	/* DHCHAP_SUPPORT */
461
462#ifdef SAN_DIAG_SUPPORT
463	sd_timestat_level0_t	sd_dev_bucket[SD_IO_LATENCY_MAX_BUCKETS];
464#endif
465
466	struct RPIobj		*rpip;	/* SLI4 only */
467#define	EMLXS_NODE_TO_RPI(_p, _n)	\
468	((_n)?((_n->rpip)?_n->rpip:emlxs_rpi_find(_p, _n->nlp_Rpi)):NULL)
469
470#ifdef NODE_THROTTLE_SUPPORT
471	uint32_t io_throttle;
472	uint32_t io_active;
473#endif /* NODE_THROTTLE_SUPPORT */
474
475} emlxs_node_t;
476typedef emlxs_node_t NODELIST;
477
478
479
480#define	NADDR_LEN	6	/* MAC network address length */
481typedef struct emlxs_fcip_nethdr
482{
483	NAME_TYPE	fc_destname;	/* destination port name */
484	NAME_TYPE	fc_srcname;	/* source port name */
485} emlxs_fcip_nethdr_t;
486typedef emlxs_fcip_nethdr_t NETHDR;
487
488
489#define	MEM_NLP		0	/* memory segment to hold node list entries */
490#define	MEM_IOCB	1	/* memory segment to hold iocb commands */
491#define	MEM_MBOX	2	/* memory segment to hold mailbox cmds  */
492#define	MEM_BPL		3	/* and to hold buffer ptr lists - SLI2   */
493#define	MEM_BUF		4	/* memory segment to hold buffer data   */
494#define	MEM_ELSBUF	4	/* memory segment to hold buffer data   */
495#define	MEM_IPBUF	5	/* memory segment to hold IP buffer data */
496#define	MEM_CTBUF	6	/* memory segment to hold CT buffer data */
497#define	MEM_FCTBUF	7	/* memory segment to hold FCT buffer data */
498#define MEM_SGL1K	8	/* memory segment to hold 1K SGL entries */
499#define MEM_SGL2K	9	/* memory segment to hold 2K SGL entries */
500#define MEM_SGL4K	10	/* memory segment to hold 4K SGL entries */
501
502#ifdef SFCT_SUPPORT
503#define	FC_MAX_SEG	11
504#define	MEM_FCTSEG	13 /* must be greater than FC_MAX_SEG */
505#else
506#define	FC_MAX_SEG	10
507#endif /* SFCT_SUPPORT */
508
509
510/* A BPL entry is 12 bytes. Subtract 2 for command and response buffers */
511#define	BPL_TO_SGLLEN(_bpl)	((_bpl/12)-2)
512#define	MEM_BPL_SIZE		36 /* Default size */
513
514/* A SGL entry is 16 bytes. Subtract 2 for command and response buffers */
515#define	SGL_TO_SGLLEN(_sgl)	((_sgl/16)-2)
516#define	MEM_SGL_SIZE		4096 /* Default size */
517
518#define	MEM_BUF_SIZE		1024
519#define	MEM_BUF_COUNT		64
520
521#define	MEM_ELSBUF_SIZE   	MEM_BUF_SIZE
522#define	MEM_ELSBUF_COUNT  	hba->max_nodes
523#define	MEM_IPBUF_SIZE  	65535
524#define	MEM_IPBUF_COUNT		60
525#define	MEM_CTBUF_SIZE		MAX_CT_PAYLOAD	/* (1024*320) */
526#define	MEM_CTBUF_COUNT		8
527#define	MEM_FCTBUF_SIZE  	65535
528#define	MEM_FCTBUF_COUNT	128
529
530typedef struct emlxs_memseg
531{
532	void			*fc_memget_ptr;
533	void			*fc_memget_end;
534	void			*fc_memput_ptr;
535	void			*fc_memput_end;
536
537	uint32_t		fc_total_memsize;
538	uint32_t		fc_memsize;		/* size of mem blks */
539	uint32_t		fc_numblks;		/* no of mem blks */
540	uint32_t		fc_memget_cnt;		/* no of mem get blks */
541	uint32_t		fc_memput_cnt;		/* no of mem put blks */
542	uint32_t		fc_memflag;  /* emlxs_buf_info_t FLAGS */
543#define	FC_MEMSEG_PUT_ENABLED	0x20000000
544#define	FC_MEMSEG_GET_ENABLED	0x40000000
545#define	FC_MEMSEG_DYNAMIC	0x80000000
546
547	uint32_t		fc_memalign;
548	uint32_t		fc_memtag;
549	char			fc_label[32];
550
551	uint32_t		fc_hi_water;
552	uint32_t		fc_lo_water;
553	uint32_t		fc_step;  /* Dyn increment.  Zero = static */
554	uint32_t		fc_low;   /* Lowest free count (dyn only) */
555	uint32_t		fc_last;  /* Last fc_numblks (dyn only) */
556
557} emlxs_memseg_t;
558typedef emlxs_memseg_t MEMSEG;
559
560
561/* Board stat counters */
562typedef struct emlxs_stats
563{
564	uint32_t	LinkUp;
565	uint32_t	LinkDown;
566	uint32_t	LinkEvent;
567	uint32_t	LinkMultiEvent;
568
569	uint32_t	MboxIssued;
570	uint32_t	MboxCompleted;	/* MboxError + MbxGood */
571	uint32_t	MboxGood;
572	uint32_t	MboxError;
573	uint32_t	MboxBusy;
574	uint32_t	MboxInvalid;
575
576	uint32_t	IocbIssued[MAX_CHANNEL];
577	uint32_t	IocbReceived[MAX_CHANNEL];
578	uint32_t	IocbTxPut[MAX_CHANNEL];
579	uint32_t	IocbTxGet[MAX_CHANNEL];
580	uint32_t	IocbRingFull[MAX_CHANNEL];
581	uint32_t	IocbThrottled;
582
583	uint32_t	IntrEvent[8];
584
585	uint32_t	FcpIssued;
586	uint32_t	FcpCompleted;	/* FcpGood + FcpError */
587	uint32_t	FcpGood;
588	uint32_t	FcpError;
589
590	uint32_t	FcpEvent;	/* FcpStray + FcpCompleted */
591	uint32_t	FcpStray;
592#ifdef SFCT_SUPPORT
593	uint32_t	FctRingEvent;
594	uint32_t	FctRingError;
595	uint32_t	FctRingDropped;
596#endif /* SFCT_SUPPORT */
597
598	uint32_t	ElsEvent;	/* ElsStray + ElsCmplt (cmd + rsp) */
599	uint32_t	ElsStray;
600
601	uint32_t	ElsCmdIssued;
602	uint32_t	ElsCmdCompleted;	/* ElsCmdGood + ElsCmdError */
603	uint32_t	ElsCmdGood;
604	uint32_t	ElsCmdError;
605
606	uint32_t	ElsRspIssued;
607	uint32_t	ElsRspCompleted;
608
609	uint32_t	ElsRcvEvent;	/* ElsRcvErr + ElsRcvDrop + ElsCmdRcv */
610	uint32_t	ElsRcvError;
611	uint32_t	ElsRcvDropped;
612	uint32_t	ElsCmdReceived;	/* ElsRscnRcv + ElsPlogiRcv + ... */
613	uint32_t	ElsRscnReceived;
614	uint32_t	ElsFlogiReceived;
615	uint32_t	ElsPlogiReceived;
616	uint32_t	ElsPrliReceived;
617	uint32_t	ElsPrloReceived;
618	uint32_t	ElsLogoReceived;
619	uint32_t	ElsAdiscReceived;
620	uint32_t	ElsAuthReceived;
621	uint32_t	ElsGenReceived;
622
623	uint32_t	CtEvent;	/* CtStray + CtCompleted (cmd + rsp) */
624	uint32_t	CtStray;
625
626	uint32_t	CtCmdIssued;
627	uint32_t	CtCmdCompleted;	/* CtCmdGood + CtCmdError */
628	uint32_t	CtCmdGood;
629	uint32_t	CtCmdError;
630
631	uint32_t	CtRspIssued;
632	uint32_t	CtRspCompleted;
633
634	uint32_t	CtRcvEvent;	/* CtRcvError + CtRcvDrop + CtCmdRcvd */
635	uint32_t	CtRcvError;
636	uint32_t	CtRcvDropped;
637	uint32_t	CtCmdReceived;
638
639	uint32_t	IpEvent;	/* IpStray + IpSeqCmpl + IpBcastCmpl */
640	uint32_t	IpStray;
641
642	uint32_t	IpSeqIssued;
643	uint32_t	IpSeqCompleted;	/* IpSeqGood + IpSeqError */
644	uint32_t	IpSeqGood;
645	uint32_t	IpSeqError;
646
647	uint32_t	IpBcastIssued;
648	uint32_t	IpBcastCompleted;	/* IpBcastGood + IpBcastError */
649	uint32_t	IpBcastGood;
650	uint32_t	IpBcastError;
651
652	uint32_t	IpRcvEvent;	/* IpDrop + IpSeqRcv + IpBcastRcv */
653	uint32_t	IpDropped;
654	uint32_t	IpSeqReceived;
655	uint32_t	IpBcastReceived;
656
657	uint32_t	IpUbPosted;
658	uint32_t	ElsUbPosted;
659	uint32_t	CtUbPosted;
660#ifdef SFCT_SUPPORT
661	uint32_t	FctUbPosted;
662#endif /* SFCT_SUPPORT */
663
664	uint32_t	ResetTime;	/* Time of last reset */
665
666	uint32_t	ElsTestReceived;
667	uint32_t	ElsEstcReceived;
668	uint32_t	ElsFarprReceived;
669	uint32_t	ElsEchoReceived;
670	uint32_t	ElsRlsReceived;
671	uint32_t	ElsRtvReceived;
672
673} emlxs_stats_t;
674
675
676#define	FC_MAX_ADPTMSG   (8*28)	/* max size of a msg from adapter */
677
678#define	EMLXS_NUM_THREADS	8
679#define	EMLXS_MIN_TASKS		8
680#define	EMLXS_MAX_TASKS		8
681
682#define	EMLXS_NUM_HASH_QUES	32
683#define	EMLXS_DID_HASH(x)	((x) & (EMLXS_NUM_HASH_QUES - 1))
684
685
686/* pkt_tran_flag */
687#define	FC_TRAN_COMPLETED	0x8000
688
689
690typedef struct emlxs_dfc_event
691{
692	uint32_t	pid;
693	uint32_t	event;
694	uint32_t	last_id;
695
696	void		*dataout;
697	uint32_t	size;
698	uint32_t	mode;
699} emlxs_dfc_event_t;
700
701
702typedef struct emlxs_hba_event
703{
704	uint32_t	last_id;
705	uint32_t	new;
706	uint32_t	missed;
707} emlxs_hba_event_t;
708
709
710#ifdef SFCT_SUPPORT
711
712#define	TGTPORTSTAT			port->fct_stat
713
714/*
715 * FctP2IOXcnt will count IOs by their fcpDL. Counters
716 * are for buckets of various power of 2 sizes.
717 * Bucket 0  <  512  > 0
718 * Bucket 1  >= 512  < 1024
719 * Bucket 2  >= 1024 < 2048
720 * Bucket 3  >= 2048 < 4096
721 * Bucket 4  >= 4096 < 8192
722 * Bucket 5  >= 8192 < 16K
723 * Bucket 6  >= 16K  < 32K
724 * Bucket 7  >= 32K  < 64K
725 * Bucket 8  >= 64K  < 128K
726 * Bucket 9  >= 128K < 256K
727 * Bucket 10 >= 256K < 512K
728 * Bucket 11 >= 512K < 1MB
729 * Bucket 12 >= 1MB  < 2MB
730 * Bucket 13 >= 2MB  < 4MB
731 * Bucket 14 >= 4MB  < 8MB
732 * Bucket 15 >= 8MB
733 */
734#define	MAX_TGTPORT_IOCNT  16
735
736
737/*
738 * These routines will bump the right counter, based on
739 * the size of the IO inputed, with the least number of
740 * comparisions.  A max of 5 comparisions is only needed
741 * to classify the IO in one of 16 ranges. A binary search
742 * to locate the high bit in the size is used.
743 */
744#define	EMLXS_BUMP_RDIOCTR(port, cnt) \
745{ \
746	/* Use binary search to find the first high bit */ \
747	if (cnt & 0xffff0000) { \
748		if (cnt & 0xff800000) { \
749			TGTPORTSTAT.FctP2IORcnt[15]++; \
750		} \
751		else { \
752			/* It must be 0x007f0000 */ \
753			if (cnt & 0x00700000) { \
754				if (cnt & 0x00400000) { \
755					TGTPORTSTAT.FctP2IORcnt[14]++; \
756				} \
757				else { \
758					/* it must be 0x00300000 */ \
759					if (cnt & 0x00200000) { \
760						TGTPORTSTAT.FctP2IORcnt[13]++; \
761					} \
762					else { \
763						/* It must be 0x00100000 */ \
764						TGTPORTSTAT.FctP2IORcnt[12]++; \
765					} \
766				} \
767			} \
768			else { \
769				/* It must be 0x000f0000 */ \
770				if (cnt & 0x000c0000) {	\
771					if (cnt & 0x00080000) {	\
772						TGTPORTSTAT.FctP2IORcnt[11]++; \
773					} \
774					else { \
775						/* It must be 0x00040000 */ \
776						TGTPORTSTAT.FctP2IORcnt[10]++; \
777					} \
778				} \
779				else { \
780					/* It must be 0x00030000 */ \
781					if (cnt & 0x00020000) {	\
782						TGTPORTSTAT.FctP2IORcnt[9]++; \
783					} \
784					else { \
785						/* It must be 0x00010000 */ \
786						TGTPORTSTAT.FctP2IORcnt[8]++; \
787					} \
788				} \
789			} \
790		} \
791	} \
792	else { \
793		if (cnt & 0x0000fe00) { \
794			if (cnt & 0x0000f000) { \
795				if (cnt & 0x0000c000) { \
796					if (cnt & 0x00008000) { \
797						TGTPORTSTAT.FctP2IORcnt[7]++; \
798					} \
799					else { \
800						/* It must be 0x00004000 */ \
801						TGTPORTSTAT.FctP2IORcnt[6]++; \
802					} \
803				} \
804				else { \
805					/* It must be 0x00000300 */ \
806					if (cnt & 0x00000200) { \
807						TGTPORTSTAT.FctP2IORcnt[5]++; \
808					} \
809					else { \
810						/* It must be 0x00000100 */ \
811						TGTPORTSTAT.FctP2IORcnt[4]++; \
812					} \
813				} \
814			} \
815			else { \
816				/* It must be 0x00000e00 */ \
817				if (cnt & 0x00000800) { \
818					TGTPORTSTAT.FctP2IORcnt[3]++; \
819				} \
820				else { \
821					/* It must be 0x00000600 */ \
822					if (cnt & 0x00000400) { \
823						TGTPORTSTAT.FctP2IORcnt[2]++; \
824					} \
825					else { \
826						/* It must be 0x00000200 */ \
827						TGTPORTSTAT.FctP2IORcnt[1]++; \
828					} \
829				} \
830			} \
831		} \
832		else { \
833			/* It must be 0x000001ff */ \
834			TGTPORTSTAT.FctP2IORcnt[0]++; \
835		} \
836	} \
837}
838
839
840#define	EMLXS_BUMP_WRIOCTR(port, cnt) \
841{ \
842/* Use binary search to find the first high bit */ \
843	if (cnt & 0xffff0000) { \
844		if (cnt & 0xff800000) { \
845			TGTPORTSTAT.FctP2IOWcnt[15]++; \
846		} \
847		else { \
848			/* It must be 0x007f0000 */ \
849			if (cnt & 0x00700000) { \
850				if (cnt & 0x00400000) { \
851					TGTPORTSTAT.FctP2IOWcnt[14]++; \
852				} \
853				else { \
854					/* It must be 0x00300000 */ \
855					if (cnt & 0x00200000) { \
856						TGTPORTSTAT.FctP2IOWcnt[13]++; \
857					} \
858					else { \
859						/* It must be 0x00100000 */ \
860						TGTPORTSTAT.FctP2IOWcnt[12]++; \
861					} \
862				} \
863			} \
864			else { \
865				/* It must be 0x000f0000 */ \
866				if (cnt & 0x000c0000) { \
867					if (cnt & 0x00080000) { \
868						TGTPORTSTAT.FctP2IOWcnt[11]++; \
869					} \
870					else { \
871						/* it must be 0x00040000 */ \
872						TGTPORTSTAT.FctP2IOWcnt[10]++; \
873					} \
874				} \
875				else { \
876					/* It must be 0x00030000 */ \
877					if (cnt & 0x00020000) { \
878						TGTPORTSTAT.FctP2IOWcnt[9]++; \
879					} \
880					else { \
881						/* It must be 0x00010000 */ \
882						TGTPORTSTAT.FctP2IOWcnt[8]++; \
883					} \
884				} \
885			} \
886		} \
887	} \
888	else { \
889		if (cnt & 0x0000fe00) { \
890			if (cnt & 0x0000f000) { \
891				if (cnt & 0x0000c000) { \
892					if (cnt & 0x00008000) { \
893						TGTPORTSTAT.FctP2IOWcnt[7]++; \
894					} \
895					else { \
896						/* It must be 0x00004000 */ \
897						TGTPORTSTAT.FctP2IOWcnt[6]++; \
898					} \
899				} \
900				else { \
901					/* It must be 0x00000300 */ \
902					if (cnt & 0x00000200) { \
903						TGTPORTSTAT.FctP2IOWcnt[5]++; \
904					} \
905					else { \
906						/* It must be 0x00000100 */ \
907						TGTPORTSTAT.FctP2IOWcnt[4]++; \
908					} \
909				} \
910			} \
911			else { \
912				/* It must be 0x00000e00 */ \
913				if (cnt & 0x00000800) { \
914					TGTPORTSTAT.FctP2IOWcnt[3]++; \
915				} \
916				else { \
917					/* It must be 0x00000600 */ \
918					if (cnt & 0x00000400) { \
919						TGTPORTSTAT.FctP2IOWcnt[2]++; \
920					} \
921					else { \
922						/* It must be 0x00000200 */ \
923						TGTPORTSTAT.FctP2IOWcnt[1]++; \
924					} \
925				} \
926			} \
927		} \
928		else { \
929			/* It must be 0x000001ff */ \
930			TGTPORTSTAT.FctP2IOWcnt[0]++; \
931		} \
932	} \
933}
934
935typedef struct emlxs_tgtport_stat
936{
937	/* IO counters */
938	uint64_t	FctP2IOWcnt[MAX_TGTPORT_IOCNT]; /* Writes */
939	uint64_t	FctP2IORcnt[MAX_TGTPORT_IOCNT]; /* Reads  */
940	uint64_t	FctIOCmdCnt;			/* Other, ie TUR */
941	uint64_t	FctCmdReceived;			/* total IOs */
942	uint64_t	FctReadBytes;			/* total read bytes */
943	uint64_t	FctWriteBytes;			/* total write bytes */
944
945	/* IOCB handling counters */
946	uint64_t	FctEvent;	/* FctStray + FctCompleted */
947	uint64_t	FctCompleted;	/* FctCmplGood + FctCmplError */
948	uint64_t	FctCmplGood;
949
950	uint32_t	FctCmplError;
951	uint32_t	FctStray;
952
953	/* Fct event counters */
954	uint32_t	FctRcvDropped;
955	uint32_t	FctOverQDepth;
956	uint32_t	FctOutstandingIO;
957	uint32_t	FctFailedPortRegister;
958	uint32_t	FctPortRegister;
959	uint32_t	FctPortDeregister;
960
961	uint32_t	FctAbortSent;
962	uint32_t	FctNoBuffer;
963	uint32_t	FctScsiStatusErr;
964	uint32_t	FctScsiQfullErr;
965	uint32_t	FctScsiResidOver;
966	uint32_t	FctScsiResidUnder;
967	uint32_t	FctScsiSenseErr;
968
969	uint32_t	FctFiller1;
970} emlxs_tgtport_stat_t;
971
972#ifdef FCT_IO_TRACE
973#define	MAX_IO_TRACE	67
974typedef struct emlxs_iotrace
975{
976	fct_cmd_t	*fct_cmd;
977	uint32_t	xri;
978	uint8_t		marker;  /* 0xff */
979	uint8_t		trc[MAX_IO_TRACE]; /* trc[0] = index */
980} emlxs_iotrace_t;
981#endif /* FCT_IO_TRACE */
982#endif /* SFCT_SUPPORT */
983
984
985#include <emlxs_fcf.h>
986
987/*
988 *     Port Information Data Structure
989 */
990
991typedef struct emlxs_port
992{
993	struct emlxs_hba	*hba;
994
995	/* Virtual port management */
996	struct VPIobj		VPIobj;
997	struct VPIobj		*vpip; /* &VPIobj */
998
999	uint32_t		vpi;	/* Legacy vpi == vpip->index */
1000	uint32_t		mode;
1001	uint32_t		mode_mask; /* User configured */
1002#define	MODE_NONE			0x00000000
1003#define	MODE_INITIATOR			0x00000001
1004#define	MODE_TARGET			0x00000002
1005#define	MODE_ALL			0x00000003
1006
1007	uint32_t		flag;
1008#define	EMLXS_PORT_ENABLED		0x00000001 /* vport setting */
1009#define	EMLXS_PORT_CONFIG		0x00000002 /* vport setting */
1010
1011#define	EMLXS_INI_ENABLED		0x00000010 /* emlxs_mode_init */
1012#define	EMLXS_INI_BOUND			0x00000020 /* emlxs_fca_bind_port */
1013#define	EMLXS_TGT_ENABLED		0x00000040 /* emlxs_mode_init */
1014#define	EMLXS_TGT_BOUND			0x00000080 /* emlxs_fct_bind_port */
1015#define	EMLXS_PORT_BOUND		(EMLXS_INI_BOUND|EMLXS_TGT_BOUND)
1016
1017#define	EMLXS_PORT_IP_UP		0x00000100
1018#define	EMLXS_PORT_RESTRICTED		0x00000200 /* Restrict logins */
1019
1020#define	EMLXS_PORT_REG_VPI		0x00010000 /* SLI3 */
1021#define	EMLXS_PORT_REG_VPI_CMPL		0x00020000 /* SLI3 */
1022
1023#define	EMLXS_PORT_FLOGI_CMPL		0x01000000	/* Fabric login */
1024							/* completed */
1025
1026#define	EMLXS_PORT_RESET_MASK		0x0000FFFF	/* Flags to keep */
1027							/* across hard reset */
1028#define	EMLXS_PORT_LINKDOWN_MASK	0x00FFFFFF	/* Flags to keep */
1029							/* across link reset */
1030
1031	uint32_t		options;
1032#define	EMLXS_OPT_RESTRICT		0x00000001 /* Force restricted */
1033						/* logins */
1034#define	EMLXS_OPT_UNRESTRICT		0x00000002 /* Force Unrestricted */
1035						/* logins */
1036#define	EMLXS_OPT_RESTRICT_MASK		0x00000003
1037
1038
1039	/* FC world wide names */
1040	NAME_TYPE		wwnn;
1041	NAME_TYPE		wwpn;
1042	char			snn[256];
1043	char			spn[256];
1044
1045	/* Common service paramters */
1046	SERV_PARM		sparam;
1047	SERV_PARM		fabric_sparam;
1048	SERV_PARM		prev_fabric_sparam;
1049
1050	/* fc_id management */
1051	uint32_t		did;
1052	uint32_t		prev_did;
1053
1054	/* support FC_PORT_GET_P2P_INFO only */
1055	uint32_t		rdid;
1056
1057	/* FC_AL management */
1058	uint8_t			lip_type;
1059	uint8_t			granted_alpa;
1060	uint8_t			alpa_map[128];
1061
1062	/* Node management */
1063	emlxs_node_t		node_base;
1064	uint32_t		node_count;
1065	krwlock_t		node_rwlock;
1066	emlxs_node_t		*node_table[EMLXS_NUM_HASH_QUES];
1067
1068	/* Polled packet management */
1069	kcondvar_t		pkt_lock_cv;	/* pkt polling */
1070	kmutex_t		pkt_lock;	/* pkt polling */
1071
1072	/* ULP */
1073	uint32_t		ulp_busy;
1074	uint32_t		ulp_statec;
1075	void			(*ulp_statec_cb) ();	/* Port state change */
1076							/* callback routine */
1077	void			(*ulp_unsol_cb) ();	/* unsolicited event */
1078							/* callback routine */
1079	opaque_t		ulp_handle;
1080
1081	/* ULP unsolicited buffers */
1082	kmutex_t		ub_lock;
1083	uint32_t		ub_count;
1084	emlxs_unsol_buf_t	*ub_pool;
1085	uint32_t		ub_post[MAX_CHANNEL];
1086	uint32_t		ub_timer;
1087
1088	emlxs_ub_priv_t		*ub_wait_head;	/* Unsolicited IO received */
1089						/* before link up */
1090	emlxs_ub_priv_t		*ub_wait_tail;	/* Unsolicited IO received */
1091						/* before link up */
1092
1093#ifdef DHCHAP_SUPPORT
1094	emlxs_port_dhc_t	port_dhc;
1095#endif	/* DHCHAP_SUPPORT */
1096
1097#ifdef SFCT_SUPPORT
1098	emlxs_memseg_t	*fct_memseg; /* Array */
1099	uint32_t fct_memseg_cnt;
1100
1101/* Default buffer counts */
1102#define	FCT_BUF_COUNT_2K		16
1103#define	FCT_BUF_COUNT_4K		0
1104#define	FCT_BUF_COUNT_8K		16
1105#define	FCT_BUF_COUNT_16K		0
1106#define	FCT_BUF_COUNT_32K		0
1107#define	FCT_BUF_COUNT_64K		16
1108#define	FCT_BUF_COUNT_128K		16
1109#define	FCT_BUF_COUNT_256K		0
1110
1111	char			cfd_name[24];
1112	stmf_port_provider_t	*port_provider;
1113	fct_local_port_t	*fct_port;
1114	uint8_t			fct_els_only_bmap;
1115	uint32_t		fct_flags;
1116
1117#define	FCT_STATE_PORT_ONLINE		0x00000001
1118#define	FCT_STATE_NOT_ACKED		0x00000002
1119#define	FCT_STATE_LINK_UP		0x00000010
1120#define	FCT_STATE_LINK_UP_ACKED		0x00000020
1121#define	FCT_STATE_FLOGI_CMPL		0x00000040
1122
1123	emlxs_tgtport_stat_t	fct_stat;
1124
1125	/* Used to save fct_cmd for deferred unsol ELS commands, except FLOGI */
1126	emlxs_buf_t		*fct_wait_head;
1127	emlxs_buf_t		*fct_wait_tail;
1128
1129	/* Used to save context for deferred unsol FLOGIs */
1130	fct_flogi_xchg_t	fx;
1131
1132#ifdef FCT_IO_TRACE
1133	emlxs_iotrace_t		*iotrace;
1134	uint16_t		iotrace_cnt;
1135	uint16_t		iotrace_index;
1136	kmutex_t		iotrace_mtx;
1137#endif /* FCT_IO_TRACE */
1138
1139#endif /* SFCT_SUPPORT */
1140
1141	uint32_t		clean_address_timer;
1142	emlxs_buf_t		*clean_address_sbp;
1143
1144#ifdef SAN_DIAG_SUPPORT
1145	uint8_t			sd_io_latency_state;
1146#define	SD_INVALID	0x00
1147#define	SD_COLLECTING	0x01
1148#define	SD_STOPPED	0x02
1149
1150	/* SD event management list */
1151	uint32_t		sd_event_mask;   /* bit-mask */
1152	emlxs_dfc_event_t	sd_events[MAX_DFC_EVENTS];
1153#endif
1154
1155} emlxs_port_t;
1156
1157
1158/* Host Attn reg */
1159#define	FC_HA_REG(_hba)		((volatile uint32_t *) \
1160				    ((_hba)->sli.sli3.ha_reg_addr))
1161
1162/* Chip Attn reg */
1163#define	FC_CA_REG(_hba)		((volatile uint32_t *) \
1164				    ((_hba)->sli.sli3.ca_reg_addr))
1165
1166/* Host Status reg */
1167#define	FC_HS_REG(_hba)		((volatile uint32_t *) \
1168				    ((_hba)->sli.sli3.hs_reg_addr))
1169
1170/* Host Cntl reg */
1171#define	FC_HC_REG(_hba)		((volatile uint32_t *) \
1172				    ((_hba)->sli.sli3.hc_reg_addr))
1173
1174/* BIU Configuration reg */
1175#define	FC_BC_REG(_hba)		((volatile uint32_t *) \
1176				    ((_hba)->sli.sli3.bc_reg_addr))
1177
1178/* Used by SBUS adapter */
1179/* TITAN Cntl reg */
1180#define	FC_SHC_REG(_hba)	((volatile uint32_t *) \
1181				    ((_hba)->sli.sli3.shc_reg_addr))
1182
1183/* TITAN Status reg */
1184#define	FC_SHS_REG(_hba)	((volatile uint32_t *) \
1185				    ((_hba)->sli.sli3.shs_reg_addr))
1186
1187/* TITAN Update reg */
1188#define	FC_SHU_REG(_hba)	((volatile uint32_t *) \
1189				    ((_hba)->sli.sli3.shu_reg_addr))
1190
1191/* MPU Semaphore reg */
1192#define	FC_SEMA_REG(_hba)	((volatile uint32_t *)\
1193				    ((_hba)->sli.sli4.MPUEPSemaphore_reg_addr))
1194
1195/* Bootstrap Mailbox Doorbell reg */
1196#define	FC_MBDB_REG(_hba)	((volatile uint32_t *) \
1197				    ((_hba)->sli.sli4.MBDB_reg_addr))
1198
1199/* MQ Doorbell reg */
1200#define	FC_MQDB_REG(_hba)	((volatile uint32_t *) \
1201				    ((_hba)->sli.sli4.MQDB_reg_addr))
1202
1203/* CQ Doorbell reg */
1204#define	FC_CQDB_REG(_hba)	((volatile uint32_t *) \
1205				    ((_hba)->sli.sli4.CQDB_reg_addr))
1206
1207/* WQ Doorbell reg */
1208#define	FC_WQDB_REG(_hba)	((volatile uint32_t *) \
1209				    ((_hba)->sli.sli4.WQDB_reg_addr))
1210
1211/* RQ Doorbell reg */
1212#define	FC_RQDB_REG(_hba)	((volatile uint32_t *) \
1213				    ((_hba)->sli.sli4.RQDB_reg_addr))
1214
1215
1216#define	FC_SLIM2_MAILBOX(_hba)	((MAILBOX *)(_hba)->sli.sli3.slim2.virt)
1217
1218#define	FC_SLIM1_MAILBOX(_hba)	((MAILBOX *)(_hba)->sli.sli3.slim_addr)
1219
1220#define	FC_MAILBOX(_hba)	(((_hba)->flag & FC_SLIM2_MODE) ? \
1221	FC_SLIM2_MAILBOX(_hba) : FC_SLIM1_MAILBOX(_hba))
1222
1223#define	WRITE_CSR_REG(_hba, _regp, _value) ddi_put32(\
1224	(_hba)->sli.sli3.csr_acc_handle, (uint32_t *)(_regp), \
1225	(uint32_t)(_value))
1226
1227#define	READ_CSR_REG(_hba, _regp) ddi_get32(\
1228	(_hba)->sli.sli3.csr_acc_handle, (uint32_t *)(_regp))
1229
1230#define	WRITE_SLIM_ADDR(_hba, _regp, _value) ddi_put32(\
1231	(_hba)->sli.sli3.slim_acc_handle, (uint32_t *)(_regp), \
1232	(uint32_t)(_value))
1233
1234#define	READ_SLIM_ADDR(_hba, _regp) ddi_get32(\
1235	(_hba)->sli.sli3.slim_acc_handle, (uint32_t *)(_regp))
1236
1237#define	WRITE_SLIM_COPY(_hba, _bufp, _slimp, _wcnt) ddi_rep_put32(\
1238	(_hba)->sli.sli3.slim_acc_handle, (uint32_t *)(_bufp), \
1239	(uint32_t *)(_slimp), (_wcnt), DDI_DEV_AUTOINCR)
1240
1241#define	READ_SLIM_COPY(_hba, _bufp, _slimp, _wcnt) ddi_rep_get32(\
1242	(_hba)->sli.sli3.slim_acc_handle, (uint32_t *)(_bufp), \
1243	(uint32_t *)(_slimp), (_wcnt), DDI_DEV_AUTOINCR)
1244
1245/* Used by SBUS adapter */
1246#define	WRITE_SBUS_CSR_REG(_hba, _regp, _value)	ddi_put32(\
1247	(_hba)->sli.sli3.sbus_csr_handle, (uint32_t *)(_regp), \
1248	(uint32_t)(_value))
1249
1250#define	READ_SBUS_CSR_REG(_hba, _regp) ddi_get32(\
1251	(_hba)->sli.sli3.sbus_csr_handle, (uint32_t *)(_regp))
1252
1253#define	SBUS_WRITE_FLASH_COPY(_hba, _offset, _value) ddi_put8(\
1254	(_hba)->sli.sli3.sbus_flash_acc_handle, \
1255	(uint8_t *)((volatile uint8_t *)(_hba)->sli.sli3.sbus_flash_addr + \
1256	(_offset)), (uint8_t)(_value))
1257
1258#define	SBUS_READ_FLASH_COPY(_hba, _offset) ddi_get8(\
1259	(_hba)->sli.sli3.sbus_flash_acc_handle, \
1260	(uint8_t *)((volatile uint8_t *)(_hba)->sli.sli3.sbus_flash_addr + \
1261	(_offset)))
1262
1263/* SLI4 registers */
1264#define	WRITE_BAR0_REG(_hba, _regp, _value) ddi_put32(\
1265	(_hba)->sli.sli4.bar0_acc_handle, (uint32_t *)(_regp), \
1266	(uint32_t)(_value))
1267
1268#define	READ_BAR0_REG(_hba, _regp) ddi_get32(\
1269	(_hba)->sli.sli4.bar0_acc_handle, (uint32_t *)(_regp))
1270
1271#define	WRITE_BAR1_REG(_hba, _regp, _value) ddi_put32(\
1272	(_hba)->sli.sli4.bar1_acc_handle, (uint32_t *)(_regp), \
1273	(uint32_t)(_value))
1274
1275#define	READ_BAR1_REG(_hba, _regp) ddi_get32(\
1276	(_hba)->sli.sli4.bar1_acc_handle, (uint32_t *)(_regp))
1277
1278#define	WRITE_BAR2_REG(_hba, _regp, _value) ddi_put32(\
1279	(_hba)->sli.sli4.bar2_acc_handle, (uint32_t *)(_regp), \
1280	(uint32_t)(_value))
1281
1282#define	READ_BAR2_REG(_hba, _regp) ddi_get32(\
1283	(_hba)->sli.sli4.bar2_acc_handle, (uint32_t *)(_regp))
1284
1285
1286#define	EMLXS_STATE_CHANGE(_hba, _state)\
1287{									\
1288	mutex_enter(&EMLXS_PORT_LOCK);					\
1289	EMLXS_STATE_CHANGE_LOCKED((_hba), (_state));			\
1290	mutex_exit(&EMLXS_PORT_LOCK);					\
1291}
1292
1293/* Used when EMLXS_PORT_LOCK is already held */
1294#define	EMLXS_STATE_CHANGE_LOCKED(_hba, _state)			\
1295{									\
1296	if ((_hba)->state != (_state))					\
1297	{								\
1298		uint32_t _st = _state;					\
1299		EMLXS_MSGF(EMLXS_CONTEXT,				\
1300			&emlxs_state_msg, "%s --> %s",			\
1301			emlxs_ffstate_xlate((_hba)->state),		\
1302			emlxs_ffstate_xlate(_state));			\
1303			(_hba)->state = (_state);			\
1304		if ((_st) == FC_ERROR)					\
1305		{							\
1306			(_hba)->flag |= FC_HARDWARE_ERROR;		\
1307		}							\
1308	}								\
1309}
1310
1311#ifdef FMA_SUPPORT
1312#define	EMLXS_CHK_ACC_HANDLE(_hba, _acc) \
1313	if (emlxs_fm_check_acc_handle(_hba, _acc) != DDI_FM_OK) { \
1314		EMLXS_MSGF(EMLXS_CONTEXT, \
1315		    &emlxs_invalid_access_handle_msg, NULL); \
1316	}
1317#endif  /* FMA_SUPPORT */
1318
1319/*
1320 * This is the HBA control area for the adapter
1321 */
1322
1323#ifdef MODSYM_SUPPORT
1324
1325typedef struct emlxs_modsym
1326{
1327	ddi_modhandle_t  mod_fctl;	/* For Leadville */
1328
1329	/* Leadville (fctl) */
1330	int		(*fc_fca_attach)(dev_info_t *, fc_fca_tran_t *);
1331	int		(*fc_fca_detach)(dev_info_t *);
1332	int		(*fc_fca_init)(struct dev_ops *);
1333
1334#ifdef SFCT_SUPPORT
1335	uint32_t	fct_modopen;
1336	uint32_t	reserved;  /* Padding for alignment */
1337
1338	ddi_modhandle_t  mod_fct;	/* For Comstar */
1339	ddi_modhandle_t  mod_stmf;	/* For Comstar */
1340
1341	/* Comstar (fct) */
1342	void*	(*fct_alloc)(fct_struct_id_t, int, int);
1343	void	(*fct_free)(void *);
1344	void*	(*fct_scsi_task_alloc)(void *, uint16_t, uint32_t, uint8_t *,
1345			uint16_t, uint16_t);
1346	int	(*fct_register_local_port)(fct_local_port_t *);
1347	void	(*fct_deregister_local_port)(fct_local_port_t *);
1348	void	(*fct_handle_event)(fct_local_port_t *, int, uint32_t, caddr_t);
1349	void	(*fct_post_rcvd_cmd)(fct_cmd_t *, stmf_data_buf_t *);
1350	void	(*fct_ctl)(void *, int, void *);
1351	void	(*fct_queue_cmd_for_termination)(fct_cmd_t *, fct_status_t);
1352	void	(*fct_send_response_done)(fct_cmd_t *, fct_status_t, uint32_t);
1353	void	(*fct_send_cmd_done)(fct_cmd_t *, fct_status_t, uint32_t);
1354	void	(*fct_scsi_data_xfer_done)(fct_cmd_t *, stmf_data_buf_t *,
1355			uint32_t);
1356	fct_status_t	(*fct_port_shutdown)
1357				(fct_local_port_t *, uint32_t, char *);
1358	fct_status_t	(*fct_port_initialize)
1359				(fct_local_port_t *, uint32_t, char *);
1360	void		(*fct_cmd_fca_aborted)
1361				(fct_cmd_t *, fct_status_t, int);
1362	fct_status_t	(*fct_handle_rcvd_flogi)
1363				(fct_local_port_t *, fct_flogi_xchg_t *);
1364
1365	/* Comstar (stmf) */
1366	void*  (*stmf_alloc)(stmf_struct_id_t, int, int);
1367	void   (*stmf_free)(void *);
1368	void	(*stmf_deregister_port_provider) (stmf_port_provider_t *);
1369	int	(*stmf_register_port_provider) (stmf_port_provider_t *);
1370#endif /* SFCT_SUPPORT */
1371} emlxs_modsym_t;
1372extern emlxs_modsym_t emlxs_modsym;
1373
1374#define	MODSYM(_f)	emlxs_modsym._f
1375
1376#else
1377
1378#define	MODSYM(_f)	_f
1379
1380#endif /* MODSYM_SUPPORT */
1381
1382
1383
1384typedef struct RPIHdrTmplate
1385{
1386	uint32_t	Word[16];  /* 64 bytes */
1387} RPIHdrTmplate_t;
1388
1389
1390typedef struct EQ_DESC
1391{
1392	uint16_t	host_index;
1393	uint16_t	max_index;
1394	uint16_t	qid;
1395	uint16_t	msix_vector;
1396	kmutex_t	lastwq_lock;
1397	uint16_t	lastwq;
1398	MBUF_INFO	addr;
1399
1400	/* Statistics */
1401	uint32_t	max_proc;
1402	uint32_t	isr_count;
1403	uint32_t	num_proc;
1404} EQ_DESC_t;
1405
1406
1407typedef struct CQ_DESC
1408{
1409	uint16_t	host_index;
1410	uint16_t	max_index;
1411	uint16_t	qid;
1412	uint16_t	eqid;
1413	uint16_t	type;
1414#define	EMLXS_CQ_TYPE_GROUP1	1  /* associated with a MQ and async events */
1415#define	EMLXS_CQ_TYPE_GROUP2	2  /* associated with a WQ and RQ */
1416	uint16_t	rsvd;
1417
1418	MBUF_INFO	addr;
1419	CHANNEL		*channelp; /* ptr to CHANNEL associated with CQ */
1420
1421	/* Statistics */
1422	uint32_t	max_proc;
1423	uint32_t	isr_count;
1424	uint32_t	num_proc;
1425} CQ_DESC_t;
1426
1427
1428typedef struct WQ_DESC
1429{
1430	uint16_t	host_index;
1431	uint16_t	max_index;
1432	uint16_t	port_index;
1433	uint16_t	release_depth;
1434#define	WQE_RELEASE_DEPTH	(8 * EMLXS_NUM_WQ_PAGES)
1435	uint16_t	qid;
1436	uint16_t	cqid;
1437	MBUF_INFO	addr;
1438
1439	/* Statistics */
1440	uint32_t	num_proc;
1441	uint32_t	num_busy;
1442} WQ_DESC_t;
1443
1444
1445typedef struct RQ_DESC
1446{
1447	uint16_t	host_index;
1448	uint16_t	max_index;
1449	uint16_t	qid;
1450	uint16_t	cqid;
1451
1452	MBUF_INFO	addr;
1453	MBUF_INFO	rqb[RQ_DEPTH];
1454
1455	kmutex_t	lock;
1456
1457	/* Statistics */
1458	uint32_t	num_proc;
1459} RQ_DESC_t;
1460
1461
1462typedef struct RXQ_DESC
1463{
1464	kmutex_t	lock;
1465	emlxs_queue_t	active;
1466
1467} RXQ_DESC_t;
1468
1469
1470typedef struct MQ_DESC
1471{
1472	uint16_t	host_index;
1473	uint16_t	max_index;
1474	uint16_t	qid;
1475	uint16_t	cqid;
1476	MBUF_INFO	addr;
1477} MQ_DESC_t;
1478
1479
1480/* Define the number of queues the driver will be using */
1481#define	EMLXS_MAX_EQS	EMLXS_MSI_MAX_INTRS
1482#define	EMLXS_MAX_WQS	EMLXS_MAX_WQS_PER_EQ * EMLXS_MAX_EQS
1483#define	EMLXS_MAX_RQS	2	/* ONLY 1 pair is allowed */
1484#define	EMLXS_MAX_MQS	1
1485
1486/* One CQ for each WQ & (RQ pair) plus one for the MQ */
1487#define	EMLXS_MAX_CQS	(EMLXS_MAX_WQS + (EMLXS_MAX_RQS/2) + 1)
1488
1489/* The First CQ created is ALWAYS for mbox / event handling */
1490#define	EMLXS_CQ_MBOX		0
1491
1492/* The Second CQ created is ALWAYS for unsol rcv handling */
1493/* At this time we are allowing ONLY 1 pair of RQs */
1494#define	EMLXS_CQ_RCV		1
1495
1496/* The remaining CQs are for WQ completions */
1497#define	EMLXS_CQ_OFFSET_WQ	2
1498
1499
1500/* FCFI RQ Configuration */
1501#define	EMLXS_FCFI_RQ0_INDEX	0
1502#define	EMLXS_FCFI_RQ0_RMASK	0 /* match all */
1503#define	EMLXS_FCFI_RQ0_RCTL	0 /* match all */
1504#define	EMLXS_FCFI_RQ0_TMASK	0 /* match all */
1505#define	EMLXS_FCFI_RQ0_TYPE	0 /* match all */
1506
1507#define	EMLXS_RXQ_ELS		0
1508#define	EMLXS_RXQ_CT		1
1509#define	EMLXS_MAX_RXQS		2
1510
1511#define	PCI_CONFIG_SIZE   0x80
1512
1513typedef struct emlxs_sli3
1514{
1515	/* SLIM management */
1516	MATCHMAP	slim2;
1517
1518	/* HBQ management */
1519	uint32_t	hbq_count;	/* Total number of HBQs */
1520					/* configured */
1521	HBQ_INIT_t	hbq_table[EMLXS_NUM_HBQ];
1522
1523	/* Adapter memory management */
1524	caddr_t		csr_addr;
1525	caddr_t		slim_addr;
1526	ddi_acc_handle_t csr_acc_handle;
1527	ddi_acc_handle_t slim_acc_handle;
1528
1529	/* SBUS adapter management */
1530	caddr_t		sbus_flash_addr;	/* Virt addr of R/W */
1531						/* Flash */
1532	caddr_t		sbus_core_addr;		/* Virt addr of TITAN */
1533						/* CORE */
1534	caddr_t		sbus_csr_addr;		/* Virt addr of TITAN */
1535						/* CSR */
1536	ddi_acc_handle_t sbus_flash_acc_handle;
1537	ddi_acc_handle_t sbus_core_acc_handle;
1538	ddi_acc_handle_t sbus_csr_handle;
1539
1540	/* SLI 2/3 Adapter register management */
1541	uint32_t	*bc_reg_addr;	/* virtual offset for BIU */
1542					/* config reg */
1543	uint32_t	*ha_reg_addr;	/* virtual offset for host */
1544					/* attn reg */
1545	uint32_t	*hc_reg_addr;	/* virtual offset for host */
1546					/* ctl reg */
1547	uint32_t	*ca_reg_addr;	/* virtual offset for FF */
1548					/* attn reg */
1549	uint32_t	*hs_reg_addr;	/* virtual offset for */
1550					/* status reg */
1551	uint32_t	*shc_reg_addr;	/* virtual offset for SBUS */
1552					/* Ctrl reg */
1553	uint32_t	*shs_reg_addr;	/* virtual offset for SBUS */
1554					/* Status reg */
1555	uint32_t	*shu_reg_addr;	/* virtual offset for SBUS */
1556					/* Update reg */
1557	uint16_t	hgp_ring_offset;
1558	uint16_t	hgp_hbq_offset;
1559	uint16_t	iocb_cmd_size;
1560	uint16_t	iocb_rsp_size;
1561	uint32_t	hc_copy;	/* local copy of HC register */
1562
1563	/* Ring management */
1564	uint32_t	ring_count;
1565	emlxs_ring_t	ring[MAX_RINGS];
1566	kmutex_t	ring_cmd_lock[MAX_RINGS];
1567	uint8_t		ring_masks[4];	/* number of masks/rings used */
1568	uint8_t		ring_rval[6];
1569	uint8_t		ring_rmask[6];
1570	uint8_t		ring_tval[6];
1571	uint8_t		ring_tmask[6];
1572
1573	/* Protected by EMLXS_FCTAB_LOCK */
1574	MATCHMAP	**bpl_table; /* iotag table for */
1575					/* bpl buffers */
1576	uint32_t	mem_bpl_size;
1577} emlxs_sli3_t;
1578
1579typedef struct emlxs_sli4
1580{
1581	MATCHMAP	bootstrapmb;
1582	caddr_t		bar0_addr;
1583	caddr_t		bar1_addr;
1584	caddr_t		bar2_addr;
1585	ddi_acc_handle_t bar0_acc_handle;
1586	ddi_acc_handle_t bar1_acc_handle;
1587	ddi_acc_handle_t bar2_acc_handle;
1588
1589	/* SLI4 Adapter register management */
1590	uint32_t	*MPUEPSemaphore_reg_addr;
1591	uint32_t	*MBDB_reg_addr;
1592
1593	uint32_t	*CQDB_reg_addr;
1594	uint32_t	*MQDB_reg_addr;
1595	uint32_t	*WQDB_reg_addr;
1596	uint32_t	*RQDB_reg_addr;
1597	uint32_t	*SEMA_reg_addr;
1598	uint32_t	*STATUS_reg_addr;
1599	uint32_t	*CNTL_reg_addr;
1600	uint32_t	*ERR1_reg_addr;
1601	uint32_t	*ERR2_reg_addr;
1602	uint32_t	*PHYSDEV_reg_addr;
1603
1604	uint32_t	flag;
1605#define	EMLXS_SLI4_INTR_ENABLED		0x00000001
1606#define	EMLXS_SLI4_HW_ERROR		0x00000002
1607#define	EMLXS_SLI4_DOWN_LINK		0x00000004
1608#define	EMLXS_SLI4_PHON			0x00000008
1609#define	EMLXS_SLI4_PHWQ			0x00000010
1610#define	EMLXS_SLI4_NULL_XRI		0x00000020
1611
1612#define	EMLXS_SLI4_FCF_INIT		0x10000000
1613#define	EMLXS_SLI4_FCOE_MODE		0x80000000
1614
1615#define	SLI4_FCOE_MODE	(hba->sli.sli4.flag & EMLXS_SLI4_FCOE_MODE)
1616#define	SLI4_FC_MODE	(!SLI4_FCOE_MODE)
1617
1618
1619
1620	uint16_t	XRICount;
1621	uint16_t	XRIExtCount;
1622	uint16_t	XRIExtSize;
1623	uint16_t	XRIBase[MAX_EXTENTS];
1624
1625	uint16_t	RPICount;
1626	uint16_t	RPIExtCount;
1627	uint16_t	RPIExtSize;
1628	uint16_t	RPIBase[MAX_EXTENTS];
1629
1630	uint16_t	VPICount;
1631	uint16_t	VPIExtCount;
1632	uint16_t	VPIExtSize;
1633	uint16_t	VPIBase[MAX_EXTENTS];
1634
1635	uint16_t	VFICount;
1636	uint16_t	VFIExtCount;
1637	uint16_t	VFIExtSize;
1638	uint16_t	VFIBase[MAX_EXTENTS];
1639
1640	uint16_t	FCFICount;
1641
1642	kmutex_t	fcf_lock;
1643	FCFTable_t	fcftab;
1644	VFIobj_t	*VFI_table;
1645
1646	/* Save Config Region 23 info */
1647	tlv_fcoe_t	cfgFCOE;
1648	tlv_fcfconnectlist_t	cfgFCF;
1649
1650	MBUF_INFO	slim2;
1651	MBUF_INFO	dump_region;
1652#define	EMLXS_DUMP_REGION_SIZE	1024
1653
1654	RPIobj_t	*RPIp;
1655	MBUF_INFO	HeaderTmplate;
1656	XRIobj_t	*XRIp;
1657
1658	/* Double linked list for available XRIs */
1659	XRIobj_t	*XRIfree_f;
1660	XRIobj_t	*XRIfree_b;
1661	uint32_t	xrif_count;
1662	uint32_t	mem_sgl_size;
1663
1664	/* Double linked list for XRIs in use */
1665	XRIobj_t	*XRIinuse_f;
1666	XRIobj_t	*XRIinuse_b;
1667	uint32_t	xria_count;
1668
1669	kmutex_t	que_lock[EMLXS_MAX_WQS];
1670	EQ_DESC_t	eq[EMLXS_MAX_EQS];
1671	CQ_DESC_t	cq[EMLXS_MAX_CQS];
1672	WQ_DESC_t	wq[EMLXS_MAX_WQS];
1673	RQ_DESC_t	rq[EMLXS_MAX_RQS];
1674	RXQ_DESC_t	rxq[EMLXS_MAX_RXQS];
1675	MQ_DESC_t	mq;
1676	uint32_t	que_stat_timer;
1677
1678	uint32_t	ue_mask_lo;
1679	uint32_t	ue_mask_hi;
1680
1681	sli_params_t	param;
1682
1683	uint8_t port_name[4];
1684	uint32_t link_number;
1685
1686} emlxs_sli4_t;
1687
1688
1689typedef struct emlxs_sli_api
1690{
1691	int		(*sli_map_hdw)();
1692	void		(*sli_unmap_hdw)();
1693	int32_t		(*sli_online)();
1694	void		(*sli_offline)();
1695	uint32_t	(*sli_hba_reset)();
1696	void		(*sli_hba_kill)();
1697	void		(*sli_issue_iocb_cmd)();
1698	uint32_t	(*sli_issue_mbox_cmd)();
1699	uint32_t	(*sli_prep_fct_iocb)();
1700	uint32_t	(*sli_prep_fcp_iocb)();
1701	uint32_t	(*sli_prep_ip_iocb)();
1702	uint32_t	(*sli_prep_els_iocb)();
1703	uint32_t	(*sli_prep_ct_iocb)();
1704	void		(*sli_poll_intr)();
1705	int32_t		(*sli_intx_intr)();
1706	uint32_t	(*sli_msi_intr)();
1707	void		(*sli_disable_intr)();
1708	void		(*sli_timer)();
1709	void		(*sli_poll_erratt)();
1710	uint32_t	(*sli_reg_did)();
1711	uint32_t	(*sli_unreg_node)();
1712
1713} emlxs_sli_api_t;
1714
1715
1716typedef struct emlxs_hba
1717{
1718	dev_info_t	*dip;
1719	int32_t		emlxinst;
1720	int32_t		ddiinst;
1721	uint8_t		pci_function_number;
1722	uint8_t		pci_device_number;
1723	uint8_t		pci_bus_number;
1724	uint8_t		pci_cap_offset[PCI_CAP_MAX_PTR];
1725	uint16_t	pci_ecap_offset[PCI_EXT_CAP_MAX_PTR];
1726
1727#ifdef FMA_SUPPORT
1728	int32_t		fm_caps;	/* FMA capabilities */
1729#endif	/* FMA_SUPPORT */
1730	fc_fca_tran_t	*fca_tran;
1731
1732	/* DMA attributes */
1733	ddi_dma_attr_t	dma_attr;
1734	ddi_dma_attr_t	dma_attr_ro;
1735	ddi_dma_attr_t	dma_attr_1sg;
1736	ddi_dma_attr_t	dma_attr_fcip_rsp;
1737
1738	/* HBA Info */
1739	emlxs_model_t	model_info;
1740	emlxs_vpd_t	vpd;	/* vital product data */
1741	NAME_TYPE	wwnn;
1742	NAME_TYPE	wwpn;
1743	char		snn[256];
1744	char		spn[256];
1745	PROG_ID		load_list[MAX_LOAD_ENTRY];
1746	WAKE_UP_PARMS	wakeup_parms;
1747	uint32_t	max_nodes;
1748	uint32_t	io_throttle;
1749	uint32_t	io_active;
1750	uint32_t	bus_type;
1751#define	PCI_FC  	0
1752#define	SBUS_FC		1
1753	uint32_t	sli_intf;
1754#define	SLI_INTF_VALID_MASK		0xe0000000
1755#define	SLI_INTF_VALID			0xc0000000
1756
1757#define	SLI_INTF_HINT2_MASK		0x1f000000
1758#define	SLI_INTF_HINT2_0		0x00000000
1759
1760#define	SLI_INTF_HINT1_MASK		0x00ff0000
1761#define	SLI_INTF_HINT1_0		0x00000000
1762#define	SLI_INTF_HINT1_1		0x00010000
1763#define	SLI_INTF_HINT1_2		0x00020000
1764
1765#define	SLI_INTF_IF_TYPE_MASK		0x0000f000
1766#define	SLI_INTF_IF_TYPE_0		0x00000000
1767#define	SLI_INTF_IF_TYPE_1		0x00001000
1768#define	SLI_INTF_IF_TYPE_2		0x00002000
1769#define	SLI_INTF_IF_TYPE_3		0x00003000
1770
1771#define	SLI_INTF_FAMILY_MASK		0x00000f00
1772#define	SLI_INTF_FAMILY_BE2		0x00000000
1773#define	SLI_INTF_FAMILY_BE3		0x00000100
1774#define	SLI_INTF_FAMILY_LANCER_A	0x00000a00
1775#define	SLI_INTF_FAMILY_LANCER_B	0x00000b00
1776
1777#define	SLI_INTF_SLI_REV_MASK		0x000000f0
1778#define	SLI_INTF_SLI_REV_NONE		0x00000000
1779#define	SLI_INTF_SLI_REV_3		0x00000030
1780#define	SLI_INTF_SLI_REV_4		0x00000040
1781
1782#define	SLI_INTF_RESERVED1		0x0000000e
1783
1784#define	SLI_INTF_FUNC_TYPE_MASK		0x00000001
1785#define	SLI_INTF_FUNC_PF		0x00000000
1786#define	SLI_INTF_FUNC_VF		0x00000001
1787
1788	/* Link management */
1789	uint32_t	link_event_tag;
1790	uint8_t		topology;
1791	uint8_t		linkspeed;
1792	uint16_t	qos_linkspeed;
1793	uint32_t	linkup_wait_flag;
1794	kcondvar_t	linkup_lock_cv;
1795	kmutex_t	linkup_lock;
1796
1797	/* Memory Pool management */
1798	emlxs_memseg_t	memseg[FC_MAX_SEG];	/* memory for buffer */
1799							/* structures */
1800	kmutex_t	memget_lock;	/* locks all memory pools get */
1801	kmutex_t	memput_lock;	/* locks all memory pools put */
1802	uint32_t	mem_timer;
1803
1804	/* Fibre Channel Service Parameters */
1805	SERV_PARM	sparam;
1806	uint32_t	fc_edtov;	/* E_D_TOV timer value */
1807	uint32_t	fc_arbtov;	/* ARB_TOV timer value */
1808	uint32_t	fc_ratov;	/* R_A_TOV timer value */
1809	uint32_t	fc_rttov;	/* R_T_TOV timer value */
1810	uint32_t	fc_altov;	/* AL_TOV timer value */
1811	uint32_t	fc_crtov;	/* C_R_TOV timer value */
1812	uint32_t	fc_citov;	/* C_I_TOV timer value */
1813
1814	/* Adapter State management */
1815	int32_t		state;
1816#define	FC_ERROR		0x01	/* Adapter shutdown */
1817#define	FC_KILLED		0x02	/* Adapter interlocked/killed */
1818#define	FC_WARM_START		0x03	/* Adapter reset, but not restarted */
1819#define	FC_INIT_START		0x10	/* Adapter restarted */
1820#define	FC_INIT_NVPARAMS	0x11
1821#define	FC_INIT_REV		0x12
1822#define	FC_INIT_CFGPORT		0x13
1823#define	FC_INIT_CFGRING		0x14
1824#define	FC_INIT_INITLINK	0x15
1825#define	FC_LINK_DOWN		0x20
1826#define	FC_LINK_DOWN_PERSIST	0x21
1827#define	FC_LINK_UP		0x30
1828#define	FC_CLEAR_LA		0x31
1829#define	FC_READY		0x40
1830
1831	uint32_t	flag;
1832#define	FC_ONLINING_MODE	0x00000001
1833#define	FC_ONLINE_MODE		0x00000002
1834#define	FC_OFFLINING_MODE	0x00000004
1835#define	FC_OFFLINE_MODE		0x00000008
1836
1837#define	FC_NPIV_ENABLED		0x00000010	/* NPIV enabled on adapter    */
1838#define	FC_NPIV_SUPPORTED	0x00000020	/* NPIV supported on fabric   */
1839#define	FC_NPIV_UNSUPPORTED	0x00000040	/* NPIV unsupported on fabric */
1840#define	FC_NPIV_LINKUP		0x00000100	/* NPIV enabled, supported, */
1841						/* and link is ready */
1842#define	FC_NPIV_DELAY_REQUIRED	0x00000200	/* Delay issuing FLOGI/FDISC */
1843						/* and NameServer cmds */
1844
1845#define	FC_BOOTSTRAPMB_INIT	0x00000400
1846#define	FC_FIP_SUPPORTED	0x00000800	/* FIP supported */
1847
1848#define	FC_FABRIC_ATTACHED	0x00001000
1849#define	FC_PT_TO_PT		0x00002000
1850#define	FC_BYPASSED_MODE	0x00004000
1851#define	FC_MENLO_MODE		0x00008000	/* Menlo maintenance mode */
1852
1853#define	FC_DUMP_SAFE		0x00010000	/* Safe to DUMP */
1854#define	FC_DUMP_ACTIVE		0x00020000	/* DUMP in progress */
1855#define	FC_NEW_FABRIC		0x00040000
1856
1857#define	FC_SLIM2_MODE		0x00100000	/* SLIM in host memory */
1858#define	FC_INTERLOCKED		0x00200000
1859#define	FC_HBQ_ENABLED		0x00400000
1860#define	FC_ASYNC_EVENTS		0x00800000
1861
1862#define	FC_ILB_MODE		0x01000000
1863#define	FC_ELB_MODE		0x02000000
1864#define	FC_LOOPBACK_MODE	0x03000000	/* Loopback Mode Mask */
1865#define	FC_DUMP			0x04000000	/* DUMP in progress */
1866#define	FC_SHUTDOWN		0x08000000	/* SHUTDOWN in progress */
1867
1868#define	FC_OVERTEMP_EVENT	0x10000000	/* FC_ERROR reason: */
1869						/* over temperature event */
1870#define	FC_MBOX_TIMEOUT		0x20000000	/* FC_ERROR reason: */
1871						/* mailbox timeout event */
1872#define	FC_DMA_CHECK_ERROR	0x40000000	/* Shared memory (slim,..) */
1873						/* DMA handle went bad */
1874#define	FC_HARDWARE_ERROR	0x80000000	/* FC_ERROR state triggered */
1875
1876#define	FC_RESET_MASK		0x00030C1F	/* Bits to protect during */
1877						/* a hard reset */
1878#define	FC_LINKDOWN_MASK	0xFFF30C1F	/* Bits to protect during */
1879						/* a linkdown */
1880
1881	uint32_t fw_timer;
1882	uint32_t fw_flag;
1883#define	FW_UPDATE_NEEDED	0x00000001
1884#define	FW_UPDATE_KERNEL	0x00000002
1885
1886	uint32_t temperature;			/* Last reported temperature */
1887
1888	/* SBUS adapter management */
1889	caddr_t		sbus_pci_addr;		/* Virt addr of TITAN */
1890						/* pci config */
1891	ddi_acc_handle_t sbus_pci_handle;
1892
1893	/* PCI BUS adapter management */
1894	caddr_t		pci_addr;
1895	ddi_acc_handle_t pci_acc_handle;
1896
1897	uint32_t	sli_mode;
1898#define	EMLXS_HBA_SLI1_MODE	1
1899#define	EMLXS_HBA_SLI2_MODE	2
1900#define	EMLXS_HBA_SLI3_MODE	3
1901#define	EMLXS_HBA_SLI4_MODE	4
1902
1903	/* SLI private data */
1904	union {
1905		emlxs_sli3_t sli3;
1906		emlxs_sli4_t sli4;
1907	} sli;
1908
1909	/* SLI API entry point routines */
1910	emlxs_sli_api_t sli_api;
1911
1912	uint32_t	io_poll_count;	/* Number of poll commands */
1913					/* in progress */
1914
1915	/* IO Completion management */
1916	uint32_t	iodone_count;	/* Number of IO's on done Q */
1917	/* Protected by EMLXS_PORT_LOCK  */
1918	emlxs_buf_t	*iodone_list;	/* fc_packet being deferred */
1919	emlxs_buf_t	*iodone_tail;	/* fc_packet being deferred */
1920	emlxs_thread_t	iodone_thread;
1921	emlxs_thread_t	*spawn_thread_head;
1922	emlxs_thread_t	*spawn_thread_tail;
1923	kmutex_t	spawn_lock;
1924	uint32_t	spawn_open;
1925
1926	/* IO Channel management */
1927	int32_t		chan_count;
1928	emlxs_channel_t	chan[MAX_CHANNEL];
1929	kmutex_t	channel_tx_lock;
1930	uint8_t		channel_fcp;	/* Default channel to use for FCP IO */
1931#define	CHANNEL_FCT channel_fcp
1932	uint8_t		channel_ip;	/* Default channel to use for IP IO */
1933	uint8_t		channel_els;	/* Default channel to use for ELS IO */
1934	uint8_t		channel_ct;	/* Default channel to use for CT IO */
1935
1936	/* IOTag management */
1937	emlxs_buf_t	**fc_table;	/* sc_buf pointers indexed by */
1938					/* iotag */
1939	uint16_t	fc_iotag;	/* used to identify I/Os */
1940	uint16_t	fc_oor_iotag;	/* OutOfRange (fc_table) iotags */
1941					/* typically used for Abort/close */
1942#define	EMLXS_MAX_ABORT_TAG	0x7fff
1943	uint16_t	max_iotag;	/* ALL IOCBs except aborts */
1944	kmutex_t	iotag_lock;
1945	uint32_t	io_count;		/* No of IO holding */
1946						/* regular iotag */
1947	uint32_t	channel_tx_count;	/* No of IO on tx Q */
1948
1949	/* Mailbox Management */
1950	uint32_t	mbox_queue_flag;
1951	emlxs_queue_t	mbox_queue;
1952	void		*mbox_mqe;	/* active mbox mqe */
1953	void		*mbox_mbq;	/* active MAILBOXQ */
1954	kcondvar_t	mbox_lock_cv;	/* MBX_SLEEP */
1955	kmutex_t	mbox_lock;	/* MBX_SLEEP */
1956	uint32_t	mbox_timer;
1957
1958	/* Interrupt management */
1959	void		*intr_arg;
1960	uint32_t	intr_unclaimed;
1961	uint32_t	intr_autoClear;
1962	uint32_t	intr_busy_cnt;
1963
1964	uint32_t	intr_flags;
1965#define	EMLXS_INTX_INITED	0x0001
1966#define	EMLXS_INTX_ADDED	0x0002
1967#define	EMLXS_MSI_ENABLED	0x0010
1968#define	EMLXS_MSI_INITED	0x0020
1969#define	EMLXS_MSI_ADDED		0x0040
1970#define	EMLXS_INTR_INITED	(EMLXS_INTX_INITED|EMLXS_MSI_INITED)
1971#define	EMLXS_INTR_ADDED	(EMLXS_INTX_ADDED|EMLXS_MSI_ADDED)
1972
1973#ifdef MSI_SUPPORT
1974	ddi_intr_handle_t *intr_htable;
1975	uint32_t	*intr_pri;
1976	int32_t		*intr_cap;
1977	uint32_t	intr_count;
1978	uint32_t	intr_type;
1979	uint32_t	intr_cond;
1980	uint32_t	intr_map[EMLXS_MSI_MAX_INTRS];
1981	uint32_t	intr_mask;
1982
1983	kmutex_t	msiid_lock; /* for last_msiid */
1984	int		last_msiid;
1985
1986	kmutex_t	intr_lock[EMLXS_MSI_MAX_INTRS];
1987	int			chan2msi[MAX_CHANNEL];
1988					/* Index is the channel id */
1989	int			msi2chan[EMLXS_MSI_MAX_INTRS];
1990					/* Index is the MSX-X msg id */
1991#endif	/* MSI_SUPPORT */
1992
1993	uint32_t	heartbeat_timer;
1994	uint32_t	heartbeat_flag;
1995	uint32_t	heartbeat_active;
1996
1997	/* IOCTL management */
1998	kmutex_t	ioctl_lock;
1999	uint32_t	ioctl_flags;
2000#define	EMLXS_OPEN		0x00000001
2001#define	EMLXS_OPEN_EXCLUSIVE	0x00000002
2002
2003	/* Timer management */
2004	kcondvar_t	timer_lock_cv;
2005	kmutex_t	timer_lock;
2006	timeout_id_t	timer_id;
2007	uint32_t	timer_tics;
2008	uint32_t	timer_flags;
2009#define	EMLXS_TIMER_STARTED	0x0000001
2010#define	EMLXS_TIMER_BUSY	0x0000002
2011#define	EMLXS_TIMER_KILL	0x0000004
2012#define	EMLXS_TIMER_ENDED	0x0000008
2013
2014	/* Misc Timers */
2015	uint32_t	linkup_timer;
2016	uint32_t	discovery_timer;
2017	uint32_t	pkt_timer;
2018
2019	/* Power Management */
2020	uint32_t	pm_state;
2021	/* pm_state */
2022#define	EMLXS_PM_IN_ATTACH	0x00000001
2023#define	EMLXS_PM_IN_DETACH	0x00000002
2024#define	EMLXS_PM_IN_SOL_CB	0x00000010
2025#define	EMLXS_PM_IN_UNSOL_CB	0x00000020
2026#define	EMLXS_PM_IN_LINK_RESET	0x00000100
2027#define	EMLXS_PM_IN_HARD_RESET	0x00000200
2028#define	EMLXS_PM_SUSPENDED	0x01000000
2029
2030	uint32_t	pm_level;
2031	/* pm_level */
2032#define	EMLXS_PM_ADAPTER_DOWN	0
2033#define	EMLXS_PM_ADAPTER_UP	1
2034
2035	uint32_t	pm_busy;
2036	kmutex_t	pm_lock;
2037	uint8_t		pm_config[PCI_CONFIG_SIZE];
2038#ifdef IDLE_TIMER
2039	uint32_t	pm_idle_timer;
2040	uint32_t	pm_active;	/* Only used by timer */
2041#endif	/* IDLE_TIMER */
2042
2043	/* Loopback management */
2044	uint32_t	loopback_tics;
2045	void		*loopback_pkt;
2046
2047	/* Event management */
2048	emlxs_event_queue_t event_queue;
2049	uint32_t	event_mask;
2050	uint32_t	event_timer;
2051	emlxs_dfc_event_t dfc_event[MAX_DFC_EVENTS];
2052	emlxs_hba_event_t hba_event;
2053
2054	/* Parameter management */
2055	emlxs_config_t	config[NUM_CFG_PARAM];
2056
2057	/* Driver stat management */
2058	kstat_t		*kstat;
2059	emlxs_stats_t	stats;
2060
2061	/* Log management */
2062	emlxs_msg_log_t	log;
2063
2064	/* Port managment */
2065	uint32_t	vpi_max;
2066	uint32_t	vpi_high;
2067	uint32_t	num_of_ports;
2068
2069	kmutex_t	port_lock;	/* locks port, nodes, rings */
2070	emlxs_port_t	port[MAX_VPORTS + 1];	/* port specific info */
2071						/* Last one is for */
2072						/* NPIV ready test */
2073
2074#ifdef DHCHAP_SUPPORT
2075	kmutex_t	dhc_lock;
2076	kmutex_t	auth_lock;
2077	emlxs_auth_cfg_t	auth_cfg;	/* Default auth_cfg. */
2078						/* Points to list of entries. */
2079						/* Protected by auth_lock */
2080	uint32_t	auth_cfg_count;
2081	emlxs_auth_key_t	auth_key;	/* Default auth_key. */
2082						/* Points to list of entries. */
2083						/* Protected by auth_lock */
2084	uint32_t	auth_key_count;
2085	uint32_t	rdn_flag;
2086#endif	/* DHCHAP_SUPPORT */
2087
2088#ifdef TEST_SUPPORT
2089	uint32_t	underrun_counter;
2090#endif /* TEST_SUPPORT */
2091
2092#ifdef MODFW_SUPPORT
2093	ddi_modhandle_t	fw_modhandle;
2094#endif /* MODFW_SUPPORT */
2095
2096#ifdef DUMP_SUPPORT
2097	emlxs_file_t	dump_txtfile;
2098	emlxs_file_t	dump_dmpfile;
2099	emlxs_file_t	dump_ceefile;
2100	kmutex_t	dump_lock;
2101#define	EMLXS_DUMP_LOCK		hba->dump_lock
2102#define	EMLXS_TXT_FILE		1
2103#define	EMLXS_DMP_FILE		2
2104#define	EMLXS_CEE_FILE		3
2105
2106#define	EMLXS_DRV_DUMP		0
2107#define	EMLXS_TEMP_DUMP		1
2108#define	EMLXS_USER_DUMP		2
2109
2110#endif /* DUMP_SUPPORT */
2111
2112	uint32_t	reset_request;
2113#define	FC_LINK_RESET		1
2114#define	FC_PORT_RESET		2
2115
2116	uint32_t	reset_state;
2117#define	FC_LINK_RESET_INP		1
2118#define	FC_PORT_RESET_INP		2
2119
2120} emlxs_hba_t;
2121
2122#define	EMLXS_SLI_MAP_HDW 		(hba->sli_api.sli_map_hdw)
2123#define	EMLXS_SLI_UNMAP_HDW		(hba->sli_api.sli_unmap_hdw)
2124#define	EMLXS_SLI_ONLINE		(hba->sli_api.sli_online)
2125#define	EMLXS_SLI_OFFLINE		(hba->sli_api.sli_offline)
2126#define	EMLXS_SLI_HBA_RESET		(hba->sli_api.sli_hba_reset)
2127#define	EMLXS_SLI_HBA_KILL		(hba->sli_api.sli_hba_kill)
2128#define	EMLXS_SLI_ISSUE_IOCB_CMD	(hba->sli_api.sli_issue_iocb_cmd)
2129#define	EMLXS_SLI_ISSUE_MBOX_CMD	(hba->sli_api.sli_issue_mbox_cmd)
2130#define	EMLXS_SLI_PREP_FCT_IOCB		(hba->sli_api.sli_prep_fct_iocb)
2131#define	EMLXS_SLI_PREP_FCP_IOCB		(hba->sli_api.sli_prep_fcp_iocb)
2132#define	EMLXS_SLI_PREP_IP_IOCB		(hba->sli_api.sli_prep_ip_iocb)
2133#define	EMLXS_SLI_PREP_ELS_IOCB		(hba->sli_api.sli_prep_els_iocb)
2134#define	EMLXS_SLI_PREP_CT_IOCB		(hba->sli_api.sli_prep_ct_iocb)
2135#define	EMLXS_SLI_POLL_INTR		(hba->sli_api.sli_poll_intr)
2136#define	EMLXS_SLI_INTX_INTR		(hba->sli_api.sli_intx_intr)
2137#define	EMLXS_SLI_MSI_INTR		(hba->sli_api.sli_msi_intr)
2138#define	EMLXS_SLI_DISABLE_INTR		(hba->sli_api.sli_disable_intr)
2139#define	EMLXS_SLI_TIMER			(hba->sli_api.sli_timer)
2140#define	EMLXS_SLI_POLL_ERRATT		(hba->sli_api.sli_poll_erratt)
2141#define	EMLXS_SLI_REG_DID		(hba->sli_api.sli_reg_did)
2142#define	EMLXS_SLI_UNREG_NODE		(hba->sli_api.sli_unreg_node)
2143
2144#define	EMLXS_HBA_T  1  /* flag emlxs_hba_t is already typedefed */
2145
2146#ifdef MSI_SUPPORT
2147#define	EMLXS_INTR_INIT(_hba, _m)		emlxs_msi_init(_hba, _m)
2148#define	EMLXS_INTR_UNINIT(_hba)			emlxs_msi_uninit(_hba)
2149#define	EMLXS_INTR_ADD(_hba)			emlxs_msi_add(_hba)
2150#define	EMLXS_INTR_REMOVE(_hba)			emlxs_msi_remove(_hba)
2151#else
2152#define	EMLXS_INTR_INIT(_hba, _m)		emlxs_intx_init(_hba, _m)
2153#define	EMLXS_INTR_UNINIT(_hba)			emlxs_intx_uninit(_hba)
2154#define	EMLXS_INTR_ADD(_hba)			emlxs_intx_add(_hba)
2155#define	EMLXS_INTR_REMOVE(_hba)			emlxs_intx_remove(_hba)
2156#endif	/* MSI_SUPPORT */
2157
2158
2159/* Power Management Component */
2160#define	EMLXS_PM_ADAPTER	0
2161
2162
2163#define	DRV_TIME	(uint32_t)(ddi_get_time() - emlxs_device.drv_timestamp)
2164
2165#define	HBA			port->hba
2166#define	PPORT			hba->port[0]
2167#define	VPORT(x)		hba->port[x]
2168#define	EMLXS_TIMER_LOCK	hba->timer_lock
2169#define	VPD			hba->vpd
2170#define	CFG			hba->config[0]
2171#define	LOG			hba->log
2172#define	EVENTQ			hba->event_queue
2173#define	EMLXS_MBOX_LOCK		hba->mbox_lock
2174#define	EMLXS_MBOX_CV		hba->mbox_lock_cv
2175#define	EMLXS_LINKUP_LOCK	hba->linkup_lock
2176#define	EMLXS_LINKUP_CV		hba->linkup_lock_cv
2177#define	EMLXS_TX_CHANNEL_LOCK	hba->channel_tx_lock	/* ring txq lock */
2178#define	EMLXS_MEMGET_LOCK	hba->memget_lock	/* mempool get lock */
2179#define	EMLXS_MEMPUT_LOCK	hba->memput_lock	/* mempool put lock */
2180#define	EMLXS_IOCTL_LOCK	hba->ioctl_lock		/* ioctl lock */
2181#define	EMLXS_SPAWN_LOCK	hba->spawn_lock		/* spawn lock */
2182#define	EMLXS_PM_LOCK		hba->pm_lock		/* pm lock */
2183#define	HBASTATS		hba->stats
2184#define	EMLXS_CMD_RING_LOCK(n)	hba->sli.sli3.ring_cmd_lock[n]
2185
2186#define	EMLXS_QUE_LOCK(n)	hba->sli.sli4.que_lock[n]
2187#define	EMLXS_MSIID_LOCK	hba->msiid_lock
2188
2189#define	EMLXS_FCTAB_LOCK	hba->iotag_lock
2190
2191#define	EMLXS_FCF_LOCK		hba->sli.sli4.fcf_lock
2192
2193#define	EMLXS_PORT_LOCK		hba->port_lock		/* locks ports, */
2194							/* nodes, rings */
2195#define	EMLXS_INTR_LOCK(_id)	hba->intr_lock[_id]	/* locks intr threads */
2196
2197#define	EMLXS_PKT_LOCK		port->pkt_lock		/* used for pkt */
2198							/* polling */
2199#define	EMLXS_PKT_CV		port->pkt_lock_cv	/* Used for pkt */
2200							/* polling */
2201#define	EMLXS_UB_LOCK		port->ub_lock		/* locks unsolicited */
2202							/* buffer pool */
2203
2204/* These SWAPs will swap on any platform */
2205#define	SWAP32_BUFFER(_b, _c)		emlxs_swap32_buffer(_b, _c)
2206#define	SWAP32_BCOPY(_s, _d, _c)	emlxs_swap32_bcopy(_s, _d, _c)
2207
2208#define	SWAP64(_x)	((((uint64_t)(_x) & 0xFF)<<56) | \
2209			    (((uint64_t)(_x) & 0xFF00)<<40) | \
2210			    (((uint64_t)(_x) & 0xFF0000)<<24) | \
2211			    (((uint64_t)(_x) & 0xFF000000)<<8) | \
2212			    (((uint64_t)(_x) & 0xFF00000000)>>8) | \
2213			    (((uint64_t)(_x) & 0xFF0000000000)>>24) | \
2214			    (((uint64_t)(_x) & 0xFF000000000000)>>40) | \
2215			    (((uint64_t)(_x) & 0xFF00000000000000)>>56))
2216
2217#define	SWAP32(_x)	((((uint32_t)(_x) & 0xFF)<<24) | \
2218			    (((uint32_t)(_x) & 0xFF00)<<8) | \
2219			    (((uint32_t)(_x) & 0xFF0000)>>8) | \
2220			    (((uint32_t)(_x) & 0xFF000000)>>24))
2221
2222#define	SWAP16(_x)	((((uint16_t)(_x) & 0xFF)<<8) | \
2223			    (((uint16_t)(_x) & 0xFF00)>>8))
2224
2225#define	SWAP24_LO(_x)	((((uint32_t)(_x) & 0xFF)<<16) | \
2226			    ((uint32_t)(_x) & 0xFF00FF00) | \
2227			    (((uint32_t)(_x) & 0x00FF0000)>>16))
2228
2229#define	SWAP24_HI(_x)	(((uint32_t)(_x) & 0x00FF00FF) | \
2230			    (((uint32_t)(_x) & 0x0000FF00)<<16) | \
2231			    (((uint32_t)(_x) & 0xFF000000)>>16))
2232
2233/* These LE_SWAPs will only swap on a LE platform */
2234#ifdef EMLXS_LITTLE_ENDIAN
2235#define	LE_SWAP32_BUFFER(_b, _c)	SWAP32_BUFFER(_b, _c)
2236#define	LE_SWAP32_BCOPY(_s, _d, _c)	SWAP32_BCOPY(_s, _d, _c)
2237#define	LE_SWAP64(_x)			SWAP64(_x)
2238#define	LE_SWAP32(_x)			SWAP32(_x)
2239#define	LE_SWAP16(_x)			SWAP16(_x)
2240#define	LE_SWAP24_LO(_x)		SWAP24_LO(X)
2241#define	LE_SWAP24_HI(_x)		SWAP24_HI(X)
2242
2243#if (EMLXS_MODREVX == EMLXS_MODREV2X)
2244#undef	LE_SWAP24_LO
2245#define	LE_SWAP24_LO(_x)		(_x)
2246#undef	LE_SWAP24_HI
2247#define	LE_SWAP24_HI(_x)		(_x)
2248#endif	/* EMLXS_MODREV2X */
2249
2250#else /* BIG ENDIAN */
2251#define	LE_SWAP32_BUFFER(_b, _c)
2252#define	LE_SWAP32_BCOPY(_s, _d, _c)	bcopy(_s, _d, _c)
2253#define	LE_SWAP64(_x)			(_x)
2254#define	LE_SWAP32(_x)			(_x)
2255#define	LE_SWAP16(_x)			(_x)
2256#define	LE_SWAP24_LO(_x)		(_x)
2257#define	LE_SWAP24_HI(_x)		(_x)
2258#endif /* EMLXS_LITTLE_ENDIAN */
2259
2260/* These BE_SWAPs will only swap on a BE platform */
2261#ifdef EMLXS_BIG_ENDIAN
2262#define	BE_SWAP32_BUFFER(_b, _c)	SWAP32_BUFFER(_b, _c)
2263#define	BE_SWAP32_BCOPY(_s, _d, _c)	SWAP32_BCOPY(_s, _d, _c)
2264#define	BE_SWAP64(_x)			SWAP64(_x)
2265#define	BE_SWAP32(_x)			SWAP32(_x)
2266#define	BE_SWAP16(_x)			SWAP16(_x)
2267#else /* LITTLE ENDIAN */
2268#define	BE_SWAP32_BUFFER(_b, _c)
2269#define	BE_SWAP32_BCOPY(_s, _d, _c)	bcopy(_s, _d, _c)
2270#define	BE_SWAP64(_x)			(_x)
2271#define	BE_SWAP32(_x)			(_x)
2272#define	BE_SWAP16(_x)			(_x)
2273#endif /* EMLXS_BIG_ENDIAN */
2274
2275#define	EMLXS_DFC_RESET_ALL			0x10
2276#define	EMLXS_DFC_RESET_ALL_FORCE_DUMP		0x11
2277
2278#ifdef	__cplusplus
2279}
2280#endif
2281
2282#endif	/* _EMLXS_FC_H */
2283