1/* SPDX-License-Identifier: GPL-2.0-only */
2/*
3 * Copyright 2008 Cisco Systems, Inc.  All rights reserved.
4 * Copyright 2007 Nuova Systems, Inc.  All rights reserved.
5 */
6#ifndef _FCPIO_H_
7#define _FCPIO_H_
8
9#include <linux/if_ether.h>
10
11/*
12 * This header file includes all of the data structures used for
13 * communication by the host driver to the fcp firmware.
14 */
15
16/*
17 * Exchange and sequence id space allocated to the host driver
18 */
19#define FCPIO_HOST_EXCH_RANGE_START         0x1000
20#define FCPIO_HOST_EXCH_RANGE_END           0x1fff
21#define FCPIO_HOST_SEQ_ID_RANGE_START       0x80
22#define FCPIO_HOST_SEQ_ID_RANGE_END         0xff
23
24/*
25 * Command entry type
26 */
27enum fcpio_type {
28	/*
29	 * Initiator request types
30	 */
31	FCPIO_ICMND_16 = 0x1,
32	FCPIO_ICMND_32,
33	FCPIO_ICMND_CMPL,
34	FCPIO_ITMF,
35	FCPIO_ITMF_CMPL,
36
37	/*
38	 * Target request types
39	 */
40	FCPIO_TCMND_16 = 0x11,
41	FCPIO_TCMND_32,
42	FCPIO_TDATA,
43	FCPIO_TXRDY,
44	FCPIO_TRSP,
45	FCPIO_TDRSP_CMPL,
46	FCPIO_TTMF,
47	FCPIO_TTMF_ACK,
48	FCPIO_TABORT,
49	FCPIO_TABORT_CMPL,
50
51	/*
52	 * Misc request types
53	 */
54	FCPIO_ACK = 0x20,
55	FCPIO_RESET,
56	FCPIO_RESET_CMPL,
57	FCPIO_FLOGI_REG,
58	FCPIO_FLOGI_REG_CMPL,
59	FCPIO_ECHO,
60	FCPIO_ECHO_CMPL,
61	FCPIO_LUNMAP_CHNG,
62	FCPIO_LUNMAP_REQ,
63	FCPIO_LUNMAP_REQ_CMPL,
64	FCPIO_FLOGI_FIP_REG,
65	FCPIO_FLOGI_FIP_REG_CMPL,
66};
67
68/*
69 * Header status codes from the firmware
70 */
71enum fcpio_status {
72	FCPIO_SUCCESS = 0,              /* request was successful */
73
74	/*
75	 * If a request to the firmware is rejected, the original request
76	 * header will be returned with the status set to one of the following:
77	 */
78	FCPIO_INVALID_HEADER,    /* header contains invalid data */
79	FCPIO_OUT_OF_RESOURCE,   /* out of resources to complete request */
80	FCPIO_INVALID_PARAM,     /* some parameter in request is invalid */
81	FCPIO_REQ_NOT_SUPPORTED, /* request type is not supported */
82	FCPIO_IO_NOT_FOUND,      /* requested I/O was not found */
83
84	/*
85	 * Once a request is processed, the firmware will usually return
86	 * a cmpl message type.  In cases where errors occurred,
87	 * the header status field would be filled in with one of the following:
88	 */
89	FCPIO_ABORTED = 0x41,     /* request was aborted */
90	FCPIO_TIMEOUT,            /* request was timed out */
91	FCPIO_SGL_INVALID,        /* request was aborted due to sgl error */
92	FCPIO_MSS_INVALID,        /* request was aborted due to mss error */
93	FCPIO_DATA_CNT_MISMATCH,  /* recv/sent more/less data than exp. */
94	FCPIO_FW_ERR,             /* request was terminated due to fw error */
95	FCPIO_ITMF_REJECTED,      /* itmf req was rejected by remote node */
96	FCPIO_ITMF_FAILED,        /* itmf req was failed by remote node */
97	FCPIO_ITMF_INCORRECT_LUN, /* itmf req targeted incorrect LUN */
98	FCPIO_CMND_REJECTED,      /* request was invalid and rejected */
99	FCPIO_NO_PATH_AVAIL,      /* no paths to the lun was available */
100	FCPIO_PATH_FAILED,        /* i/o sent to current path failed */
101	FCPIO_LUNMAP_CHNG_PEND,   /* i/o rejected due to lunmap change */
102};
103
104/*
105 * The header command tag.  All host requests will use the "tag" field
106 * to mark commands with a unique tag.  When the firmware responds to
107 * a host request, it will copy the tag field into the response.
108 *
109 * The only firmware requests that will use the rx_id/ox_id fields instead
110 * of the tag field will be the target command and target task management
111 * requests.  These two requests do not have corresponding host requests
112 * since they come directly from the FC initiator on the network.
113 */
114struct fcpio_tag {
115	union {
116		u32 req_id;
117		struct {
118			u16 rx_id;
119			u16 ox_id;
120		} ex_id;
121	} u;
122};
123
124static inline void
125fcpio_tag_id_enc(struct fcpio_tag *tag, u32 id)
126{
127	tag->u.req_id = id;
128}
129
130static inline void
131fcpio_tag_id_dec(struct fcpio_tag *tag, u32 *id)
132{
133	*id = tag->u.req_id;
134}
135
136static inline void
137fcpio_tag_exid_enc(struct fcpio_tag *tag, u16 ox_id, u16 rx_id)
138{
139	tag->u.ex_id.rx_id = rx_id;
140	tag->u.ex_id.ox_id = ox_id;
141}
142
143static inline void
144fcpio_tag_exid_dec(struct fcpio_tag *tag, u16 *ox_id, u16 *rx_id)
145{
146	*rx_id = tag->u.ex_id.rx_id;
147	*ox_id = tag->u.ex_id.ox_id;
148}
149
150/*
151 * The header for an fcpio request, whether from the firmware or from the
152 * host driver
153 */
154struct fcpio_header {
155	u8            type;           /* enum fcpio_type */
156	u8            status;         /* header status entry */
157	u16           _resvd;         /* reserved */
158	struct fcpio_tag    tag;      /* header tag */
159};
160
161static inline void
162fcpio_header_enc(struct fcpio_header *hdr,
163		 u8 type, u8 status,
164		 struct fcpio_tag tag)
165{
166	hdr->type = type;
167	hdr->status = status;
168	hdr->_resvd = 0;
169	hdr->tag = tag;
170}
171
172static inline void
173fcpio_header_dec(struct fcpio_header *hdr,
174		 u8 *type, u8 *status,
175		 struct fcpio_tag *tag)
176{
177	*type = hdr->type;
178	*status = hdr->status;
179	*tag = hdr->tag;
180}
181
182#define CDB_16      16
183#define CDB_32      32
184#define LUN_ADDRESS 8
185
186/*
187 * fcpio_icmnd_16: host -> firmware request
188 *
189 * used for sending out an initiator SCSI 16-byte command
190 */
191struct fcpio_icmnd_16 {
192	u32	  lunmap_id;		/* index into lunmap table */
193	u8	  special_req_flags;	/* special exchange request flags */
194	u8	  _resvd0[3];	        /* reserved */
195	u32	  sgl_cnt;		/* scatter-gather list count */
196	u32	  sense_len;		/* sense buffer length */
197	u64	  sgl_addr;		/* scatter-gather list addr */
198	u64	  sense_addr;		/* sense buffer address */
199	u8	  crn;			/* SCSI Command Reference No. */
200	u8	  pri_ta;		/* SCSI Priority and Task attribute */
201	u8	  _resvd1;		/* reserved: should be 0 */
202	u8	  flags;		/* command flags */
203	u8	  scsi_cdb[CDB_16];	/* SCSI Cmnd Descriptor Block */
204	u32	  data_len;		/* length of data expected */
205	u8	  lun[LUN_ADDRESS];	/* FC vNIC only: LUN address */
206	u8	  _resvd2;		/* reserved */
207	u8	  d_id[3];		/* FC vNIC only: Target D_ID */
208	u16	  mss;			/* FC vNIC only: max burst */
209	u16	  _resvd3;		/* reserved */
210	u32	  r_a_tov;		/* FC vNIC only: Res. Alloc Timeout */
211	u32	  e_d_tov;	        /* FC vNIC only: Err Detect Timeout */
212};
213
214/*
215 * Special request flags
216 */
217#define FCPIO_ICMND_SRFLAG_RETRY 0x01   /* Enable Retry handling on exchange */
218
219/*
220 * Priority/Task Attribute settings
221 */
222#define FCPIO_ICMND_PTA_SIMPLE      0   /* simple task attribute */
223#define FCPIO_ICMND_PTA_HEADQ       1   /* head of queue task attribute */
224#define FCPIO_ICMND_PTA_ORDERED     2   /* ordered task attribute */
225#define FCPIO_ICMND_PTA_ACA         4   /* auto contingent allegiance */
226#define FCPIO_ICMND_PRI_SHIFT       3   /* priority field starts in bit 3 */
227
228/*
229 * Command flags
230 */
231#define FCPIO_ICMND_RDDATA      0x02    /* read data */
232#define FCPIO_ICMND_WRDATA      0x01    /* write data */
233
234/*
235 * fcpio_icmnd_32: host -> firmware request
236 *
237 * used for sending out an initiator SCSI 32-byte command
238 */
239struct fcpio_icmnd_32 {
240	u32   lunmap_id;              /* index into lunmap table */
241	u8    special_req_flags;      /* special exchange request flags */
242	u8    _resvd0[3];             /* reserved */
243	u32   sgl_cnt;                /* scatter-gather list count */
244	u32   sense_len;              /* sense buffer length */
245	u64   sgl_addr;               /* scatter-gather list addr */
246	u64   sense_addr;             /* sense buffer address */
247	u8    crn;                    /* SCSI Command Reference No. */
248	u8    pri_ta;                 /* SCSI Priority and Task attribute */
249	u8    _resvd1;                /* reserved: should be 0 */
250	u8    flags;                  /* command flags */
251	u8    scsi_cdb[CDB_32];       /* SCSI Cmnd Descriptor Block */
252	u32   data_len;               /* length of data expected */
253	u8    lun[LUN_ADDRESS];       /* FC vNIC only: LUN address */
254	u8    _resvd2;                /* reserved */
255	u8    d_id[3];		      /* FC vNIC only: Target D_ID */
256	u16   mss;                    /* FC vNIC only: max burst */
257	u16   _resvd3;                /* reserved */
258	u32   r_a_tov;                /* FC vNIC only: Res. Alloc Timeout */
259	u32   e_d_tov;                /* FC vNIC only: Error Detect Timeout */
260};
261
262/*
263 * fcpio_itmf: host -> firmware request
264 *
265 * used for requesting the firmware to abort a request and/or send out
266 * a task management function
267 *
268 * The t_tag field is only needed when the request type is ABT_TASK.
269 */
270struct fcpio_itmf {
271	u32   lunmap_id;              /* index into lunmap table */
272	u32   tm_req;                 /* SCSI Task Management request */
273	u32   t_tag;                  /* header tag of fcpio to be aborted */
274	u32   _resvd;                 /* _reserved */
275	u8    lun[LUN_ADDRESS];       /* FC vNIC only: LUN address */
276	u8    _resvd1;                /* reserved */
277	u8    d_id[3];		      /* FC vNIC only: Target D_ID */
278	u32   r_a_tov;                /* FC vNIC only: R_A_TOV in msec */
279	u32   e_d_tov;                /* FC vNIC only: E_D_TOV in msec */
280};
281
282/*
283 * Task Management request
284 */
285enum fcpio_itmf_tm_req_type {
286	FCPIO_ITMF_ABT_TASK_TERM = 0x01,    /* abort task and terminate */
287	FCPIO_ITMF_ABT_TASK,                /* abort task and issue abts */
288	FCPIO_ITMF_ABT_TASK_SET,            /* abort task set */
289	FCPIO_ITMF_CLR_TASK_SET,            /* clear task set */
290	FCPIO_ITMF_LUN_RESET,               /* logical unit reset task mgmt */
291	FCPIO_ITMF_CLR_ACA,                 /* Clear ACA condition */
292};
293
294/*
295 * fcpio_tdata: host -> firmware request
296 *
297 * used for requesting the firmware to send out a read data transfer for a
298 * target command
299 */
300struct fcpio_tdata {
301	u16   rx_id;                  /* FC rx_id of target command */
302	u16   flags;                  /* command flags */
303	u32   rel_offset;             /* data sequence relative offset */
304	u32   sgl_cnt;                /* scatter-gather list count */
305	u32   data_len;               /* length of data expected to send */
306	u64   sgl_addr;               /* scatter-gather list address */
307};
308
309/*
310 * Command flags
311 */
312#define FCPIO_TDATA_SCSI_RSP    0x01    /* send a scsi resp. after last frame */
313
314/*
315 * fcpio_txrdy: host -> firmware request
316 *
317 * used for requesting the firmware to send out a write data transfer for a
318 * target command
319 */
320struct fcpio_txrdy {
321	u16   rx_id;                  /* FC rx_id of target command */
322	u16   _resvd0;                /* reserved */
323	u32   rel_offset;             /* data sequence relative offset */
324	u32   sgl_cnt;                /* scatter-gather list count */
325	u32   data_len;               /* length of data expected to send */
326	u64   sgl_addr;               /* scatter-gather list address */
327};
328
329/*
330 * fcpio_trsp: host -> firmware request
331 *
332 * used for requesting the firmware to send out a response for a target
333 * command
334 */
335struct fcpio_trsp {
336	u16   rx_id;                  /* FC rx_id of target command */
337	u16   _resvd0;                /* reserved */
338	u32   sense_len;              /* sense data buffer length */
339	u64   sense_addr;             /* sense data buffer address */
340	u16   _resvd1;                /* reserved */
341	u8    flags;                  /* response request flags */
342	u8    scsi_status;            /* SCSI status */
343	u32   residual;               /* SCSI data residual value of I/O */
344};
345
346/*
347 * resposnse request flags
348 */
349#define FCPIO_TRSP_RESID_UNDER  0x08   /* residual is valid and is underflow */
350#define FCPIO_TRSP_RESID_OVER   0x04   /* residual is valid and is overflow */
351
352/*
353 * fcpio_ttmf_ack: host -> firmware response
354 *
355 * used by the host to indicate to the firmware it has received and processed
356 * the target tmf request
357 */
358struct fcpio_ttmf_ack {
359	u16   rx_id;                  /* FC rx_id of target command */
360	u16   _resvd0;                /* reserved */
361	u32   tmf_status;             /* SCSI task management status */
362};
363
364/*
365 * fcpio_tabort: host -> firmware request
366 *
367 * used by the host to request the firmware to abort a target request that was
368 * received by the firmware
369 */
370struct fcpio_tabort {
371	u16   rx_id;                  /* rx_id of the target request */
372};
373
374/*
375 * fcpio_reset: host -> firmware request
376 *
377 * used by the host to signal a reset of the driver to the firmware
378 * and to request firmware to clean up all outstanding I/O
379 */
380struct fcpio_reset {
381	u32   _resvd;
382};
383
384enum fcpio_flogi_reg_format_type {
385	FCPIO_FLOGI_REG_DEF_DEST = 0,    /* Use the oui | s_id mac format */
386	FCPIO_FLOGI_REG_GW_DEST,         /* Use the fixed gateway mac */
387};
388
389/*
390 * fcpio_flogi_reg: host -> firmware request
391 *
392 * fc vnic only
393 * used by the host to notify the firmware of the lif's s_id
394 * and destination mac address format
395 */
396struct fcpio_flogi_reg {
397	u8 format;
398	u8 s_id[3];			/* FC vNIC only: Source S_ID */
399	u8 gateway_mac[ETH_ALEN];	/* Destination gateway mac */
400	u16 _resvd;
401	u32 r_a_tov;			/* R_A_TOV in msec */
402	u32 e_d_tov;			/* E_D_TOV in msec */
403};
404
405/*
406 * fcpio_echo: host -> firmware request
407 *
408 * sends a heartbeat echo request to the firmware
409 */
410struct fcpio_echo {
411	u32 _resvd;
412};
413
414/*
415 * fcpio_lunmap_req: host -> firmware request
416 *
417 * scsi vnic only
418 * sends a request to retrieve the lunmap table for scsi vnics
419 */
420struct fcpio_lunmap_req {
421	u64 addr;                     /* address of the buffer */
422	u32 len;                      /* len of the buffer */
423};
424
425/*
426 * fcpio_flogi_fip_reg: host -> firmware request
427 *
428 * fc vnic only
429 * used by the host to notify the firmware of the lif's s_id
430 * and destination mac address format
431 */
432struct fcpio_flogi_fip_reg {
433	u8    _resvd0;
434	u8     s_id[3];               /* FC vNIC only: Source S_ID */
435	u8     fcf_mac[ETH_ALEN];     /* FCF Target destination mac */
436	u16   _resvd1;
437	u32   r_a_tov;                /* R_A_TOV in msec */
438	u32   e_d_tov;                /* E_D_TOV in msec */
439	u8    ha_mac[ETH_ALEN];       /* Host adapter source mac */
440	u16   _resvd2;
441};
442
443/*
444 * Basic structure for all fcpio structures that are sent from the host to the
445 * firmware.  They are 128 bytes per structure.
446 */
447#define FCPIO_HOST_REQ_LEN      128     /* expected length of host requests */
448
449struct fcpio_host_req {
450	struct fcpio_header hdr;
451
452	union {
453		/*
454		 * Defines space needed for request
455		 */
456		u8 buf[FCPIO_HOST_REQ_LEN - sizeof(struct fcpio_header)];
457
458		/*
459		 * Initiator host requests
460		 */
461		struct fcpio_icmnd_16               icmnd_16;
462		struct fcpio_icmnd_32               icmnd_32;
463		struct fcpio_itmf                   itmf;
464
465		/*
466		 * Target host requests
467		 */
468		struct fcpio_tdata                  tdata;
469		struct fcpio_txrdy                  txrdy;
470		struct fcpio_trsp                   trsp;
471		struct fcpio_ttmf_ack               ttmf_ack;
472		struct fcpio_tabort                 tabort;
473
474		/*
475		 * Misc requests
476		 */
477		struct fcpio_reset                  reset;
478		struct fcpio_flogi_reg              flogi_reg;
479		struct fcpio_echo                   echo;
480		struct fcpio_lunmap_req             lunmap_req;
481		struct fcpio_flogi_fip_reg          flogi_fip_reg;
482	} u;
483};
484
485/*
486 * fcpio_icmnd_cmpl: firmware -> host response
487 *
488 * used for sending the host a response to an initiator command
489 */
490struct fcpio_icmnd_cmpl {
491	u8    _resvd0[6];             /* reserved */
492	u8    flags;                  /* response flags */
493	u8    scsi_status;            /* SCSI status */
494	u32   residual;               /* SCSI data residual length */
495	u32   sense_len;              /* SCSI sense length */
496};
497
498/*
499 * response flags
500 */
501#define FCPIO_ICMND_CMPL_RESID_UNDER    0x08    /* resid under and valid */
502#define FCPIO_ICMND_CMPL_RESID_OVER     0x04    /* resid over and valid */
503
504/*
505 * fcpio_itmf_cmpl: firmware -> host response
506 *
507 * used for sending the host a response for a itmf request
508 */
509struct fcpio_itmf_cmpl {
510	u32    _resvd;                /* reserved */
511};
512
513/*
514 * fcpio_tcmnd_16: firmware -> host request
515 *
516 * used by the firmware to notify the host of an incoming target SCSI 16-Byte
517 * request
518 */
519struct fcpio_tcmnd_16 {
520	u8    lun[LUN_ADDRESS];       /* FC vNIC only: LUN address */
521	u8    crn;                    /* SCSI Command Reference No. */
522	u8    pri_ta;                 /* SCSI Priority and Task attribute */
523	u8    _resvd2;                /* reserved: should be 0 */
524	u8    flags;                  /* command flags */
525	u8    scsi_cdb[CDB_16];       /* SCSI Cmnd Descriptor Block */
526	u32   data_len;               /* length of data expected */
527	u8    _resvd1;                /* reserved */
528	u8    s_id[3];		      /* FC vNIC only: Source S_ID */
529};
530
531/*
532 * Priority/Task Attribute settings
533 */
534#define FCPIO_TCMND_PTA_SIMPLE      0   /* simple task attribute */
535#define FCPIO_TCMND_PTA_HEADQ       1   /* head of queue task attribute */
536#define FCPIO_TCMND_PTA_ORDERED     2   /* ordered task attribute */
537#define FCPIO_TCMND_PTA_ACA         4   /* auto contingent allegiance */
538#define FCPIO_TCMND_PRI_SHIFT       3   /* priority field starts in bit 3 */
539
540/*
541 * Command flags
542 */
543#define FCPIO_TCMND_RDDATA      0x02    /* read data */
544#define FCPIO_TCMND_WRDATA      0x01    /* write data */
545
546/*
547 * fcpio_tcmnd_32: firmware -> host request
548 *
549 * used by the firmware to notify the host of an incoming target SCSI 32-Byte
550 * request
551 */
552struct fcpio_tcmnd_32 {
553	u8    lun[LUN_ADDRESS];       /* FC vNIC only: LUN address */
554	u8    crn;                    /* SCSI Command Reference No. */
555	u8    pri_ta;                 /* SCSI Priority and Task attribute */
556	u8    _resvd2;                /* reserved: should be 0 */
557	u8    flags;                  /* command flags */
558	u8    scsi_cdb[CDB_32];       /* SCSI Cmnd Descriptor Block */
559	u32   data_len;               /* length of data expected */
560	u8    _resvd0;                /* reserved */
561	u8    s_id[3];		      /* FC vNIC only: Source S_ID */
562};
563
564/*
565 * fcpio_tdrsp_cmpl: firmware -> host response
566 *
567 * used by the firmware to notify the host of a response to a host target
568 * command
569 */
570struct fcpio_tdrsp_cmpl {
571	u16   rx_id;                  /* rx_id of the target request */
572	u16   _resvd0;                /* reserved */
573};
574
575/*
576 * fcpio_ttmf: firmware -> host request
577 *
578 * used by the firmware to notify the host of an incoming task management
579 * function request
580 */
581struct fcpio_ttmf {
582	u8    _resvd0;                /* reserved */
583	u8    s_id[3];		      /* FC vNIC only: Source S_ID */
584	u8    lun[LUN_ADDRESS];       /* FC vNIC only: LUN address */
585	u8    crn;                    /* SCSI Command Reference No. */
586	u8    _resvd2[3];             /* reserved */
587	u32   tmf_type;               /* task management request type */
588};
589
590/*
591 * Task Management request
592 */
593#define FCPIO_TTMF_CLR_ACA      0x40    /* Clear ACA condition */
594#define FCPIO_TTMF_LUN_RESET    0x10    /* logical unit reset task mgmt */
595#define FCPIO_TTMF_CLR_TASK_SET 0x04    /* clear task set */
596#define FCPIO_TTMF_ABT_TASK_SET 0x02    /* abort task set */
597#define FCPIO_TTMF_ABT_TASK     0x01    /* abort task */
598
599/*
600 * fcpio_tabort_cmpl: firmware -> host response
601 *
602 * used by the firmware to respond to a host's tabort request
603 */
604struct fcpio_tabort_cmpl {
605	u16   rx_id;                  /* rx_id of the target request */
606	u16   _resvd0;                /* reserved */
607};
608
609/*
610 * fcpio_ack: firmware -> host response
611 *
612 * used by firmware to notify the host of the last work request received
613 */
614struct fcpio_ack {
615	u16  request_out;             /* last host entry received */
616	u16  _resvd;
617};
618
619/*
620 * fcpio_reset_cmpl: firmware -> host response
621 *
622 * use by firmware to respond to the host's reset request
623 */
624struct fcpio_reset_cmpl {
625	u16   vnic_id;
626};
627
628/*
629 * fcpio_flogi_reg_cmpl: firmware -> host response
630 *
631 * fc vnic only
632 * response to the fcpio_flogi_reg request
633 */
634struct fcpio_flogi_reg_cmpl {
635	u32 _resvd;
636};
637
638/*
639 * fcpio_echo_cmpl: firmware -> host response
640 *
641 * response to the fcpio_echo request
642 */
643struct fcpio_echo_cmpl {
644	u32 _resvd;
645};
646
647/*
648 * fcpio_lunmap_chng: firmware -> host notification
649 *
650 * scsi vnic only
651 * notifies the host that the lunmap tables have changed
652 */
653struct fcpio_lunmap_chng {
654	u32 _resvd;
655};
656
657/*
658 * fcpio_lunmap_req_cmpl: firmware -> host response
659 *
660 * scsi vnic only
661 * response for lunmap table request from the host
662 */
663struct fcpio_lunmap_req_cmpl {
664	u32 _resvd;
665};
666
667/*
668 * Basic structure for all fcpio structures that are sent from the firmware to
669 * the host.  They are 64 bytes per structure.
670 */
671#define FCPIO_FW_REQ_LEN        64      /* expected length of fw requests */
672struct fcpio_fw_req {
673	struct fcpio_header hdr;
674
675	union {
676		/*
677		 * Defines space needed for request
678		 */
679		u8 buf[FCPIO_FW_REQ_LEN - sizeof(struct fcpio_header)];
680
681		/*
682		 * Initiator firmware responses
683		 */
684		struct fcpio_icmnd_cmpl         icmnd_cmpl;
685		struct fcpio_itmf_cmpl          itmf_cmpl;
686
687		/*
688		 * Target firmware new requests
689		 */
690		struct fcpio_tcmnd_16           tcmnd_16;
691		struct fcpio_tcmnd_32           tcmnd_32;
692
693		/*
694		 * Target firmware responses
695		 */
696		struct fcpio_tdrsp_cmpl         tdrsp_cmpl;
697		struct fcpio_ttmf               ttmf;
698		struct fcpio_tabort_cmpl        tabort_cmpl;
699
700		/*
701		 * Firmware response to work received
702		 */
703		struct fcpio_ack                ack;
704
705		/*
706		 * Misc requests
707		 */
708		struct fcpio_reset_cmpl         reset_cmpl;
709		struct fcpio_flogi_reg_cmpl     flogi_reg_cmpl;
710		struct fcpio_echo_cmpl          echo_cmpl;
711		struct fcpio_lunmap_chng        lunmap_chng;
712		struct fcpio_lunmap_req_cmpl    lunmap_req_cmpl;
713	} u;
714};
715
716/*
717 * Access routines to encode and decode the color bit, which is the most
718 * significant bit of the MSB of the structure
719 */
720static inline void fcpio_color_enc(struct fcpio_fw_req *fw_req, u8 color)
721{
722	u8 *c = ((u8 *) fw_req) + sizeof(struct fcpio_fw_req) - 1;
723
724	if (color)
725		*c |= 0x80;
726	else
727		*c &= ~0x80;
728}
729
730static inline void fcpio_color_dec(struct fcpio_fw_req *fw_req, u8 *color)
731{
732	u8 *c = ((u8 *) fw_req) + sizeof(struct fcpio_fw_req) - 1;
733
734	*color = *c >> 7;
735
736	/*
737	 * Make sure color bit is read from desc *before* other fields
738	 * are read from desc.  Hardware guarantees color bit is last
739	 * bit (byte) written.  Adding the rmb() prevents the compiler
740	 * and/or CPU from reordering the reads which would potentially
741	 * result in reading stale values.
742	 */
743
744	rmb();
745
746}
747
748/*
749 * Lunmap table entry for scsi vnics
750 */
751#define FCPIO_LUNMAP_TABLE_SIZE     256
752#define FCPIO_FLAGS_LUNMAP_VALID    0x80
753#define FCPIO_FLAGS_BOOT            0x01
754struct fcpio_lunmap_entry {
755	u8    bus;
756	u8    target;
757	u8    lun;
758	u8    path_cnt;
759	u16   flags;
760	u16   update_cnt;
761};
762
763struct fcpio_lunmap_tbl {
764	u32                   update_cnt;
765	struct fcpio_lunmap_entry   lunmaps[FCPIO_LUNMAP_TABLE_SIZE];
766};
767
768#endif /* _FCPIO_H_ */
769