1 #ifndef _IPXE_FCP_H
2 #define _IPXE_FCP_H
3 
4 /**
5  * @file
6  *
7  * Fibre Channel Protocol
8  *
9  */
10 
11 FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
12 
13 #include <stdint.h>
14 #include <ipxe/fc.h>
15 #include <ipxe/fcels.h>
16 #include <ipxe/scsi.h>
17 
18 /** An FCP command IU */
19 struct fcp_cmnd {
20 	/** SCSI LUN */
21 	struct scsi_lun lun;
22 	/** Command reference number */
23 	uint8_t ref;
24 	/** Priority and task attributes */
25 	uint8_t priority;
26 	/** Task management flags */
27 	uint8_t flags;
28 	/** Direction */
29 	uint8_t dirn;
30 	/** SCSI CDB */
31 	union scsi_cdb cdb;
32 	/** Data length */
33 	uint32_t len;
34 } __attribute__ (( packed ));
35 
36 /** Command includes data-out */
37 #define FCP_CMND_WRDATA 0x01
38 
39 /** Command includes data-in */
40 #define FCP_CMND_RDDATA 0x02
41 
42 /** FCP tag magic marker */
43 #define FCP_TAG_MAGIC 0x18ae0000
44 
45 /** An FCP transfer ready IU */
46 struct fcp_xfer_rdy {
47 	/** Relative offset of data */
48 	uint32_t offset;
49 	/** Burst length */
50 	uint32_t len;
51 	/** Reserved */
52 	uint32_t reserved;
53 } __attribute__ (( packed ));
54 
55 /** An FCP response IU */
56 struct fcp_rsp {
57 	/** Reserved */
58 	uint8_t reserved[8];
59 	/** Retry delay timer */
60 	uint16_t retry_delay;
61 	/** Flags */
62 	uint8_t flags;
63 	/** SCSI status code */
64 	uint8_t status;
65 	/** Residual data count */
66 	uint32_t residual;
67 	/** Sense data length */
68 	uint32_t sense_len;
69 	/** Response data length */
70 	uint32_t response_len;
71 } __attribute__ (( packed ));
72 
73 /** Response length field is valid */
74 #define FCP_RSP_RESPONSE_LEN_VALID 0x01
75 
76 /** Sense length field is valid */
77 #define FCP_RSP_SENSE_LEN_VALID 0x02
78 
79 /** Residual represents overrun */
80 #define FCP_RSP_RESIDUAL_OVERRUN 0x04
81 
82 /** Residual represents underrun */
83 #define FCP_RSP_RESIDUAL_UNDERRUN 0x08
84 
85 /**
86  * Get response data portion of FCP response
87  *
88  * @v rsp			FCP response
89  * @ret response_data		Response data, or NULL if not present
90  */
fcp_rsp_response_data(struct fcp_rsp * rsp)91 static inline void * fcp_rsp_response_data ( struct fcp_rsp *rsp ) {
92 	return ( ( rsp->flags & FCP_RSP_RESPONSE_LEN_VALID ) ?
93 		 ( ( ( void * ) rsp ) + sizeof ( *rsp ) ) : NULL );
94 }
95 
96 /**
97  * Get length of response data portion of FCP response
98  *
99  * @v rsp			FCP response
100  * @ret response_data_len	Response data length
101  */
fcp_rsp_response_data_len(struct fcp_rsp * rsp)102 static inline size_t fcp_rsp_response_data_len ( struct fcp_rsp *rsp ) {
103 	return ( ( rsp->flags & FCP_RSP_RESPONSE_LEN_VALID ) ?
104 		 ntohl ( rsp->response_len ) : 0 );
105 }
106 
107 /**
108  * Get sense data portion of FCP response
109  *
110  * @v rsp			FCP response
111  * @ret sense_data		Sense data, or NULL if not present
112  */
fcp_rsp_sense_data(struct fcp_rsp * rsp)113 static inline void * fcp_rsp_sense_data ( struct fcp_rsp *rsp ) {
114 	return ( ( rsp->flags & FCP_RSP_SENSE_LEN_VALID ) ?
115 		 ( ( ( void * ) rsp ) + sizeof ( *rsp ) +
116 		   fcp_rsp_response_data_len ( rsp ) ) : NULL );
117 }
118 
119 /**
120  * Get length of sense data portion of FCP response
121  *
122  * @v rsp			FCP response
123  * @ret sense_data_len		Sense data length
124  */
fcp_rsp_sense_data_len(struct fcp_rsp * rsp)125 static inline size_t fcp_rsp_sense_data_len ( struct fcp_rsp *rsp ) {
126 	return ( ( rsp->flags & FCP_RSP_SENSE_LEN_VALID ) ?
127 		 ntohl ( rsp->sense_len ) : 0 );
128 }
129 
130 /** An FCP PRLI service parameter page */
131 struct fcp_prli_service_parameters {
132 	/** Flags */
133 	uint32_t flags;
134 } __attribute__ (( packed ));
135 
136 /** Write FCP_XFER_RDY disabled */
137 #define FCP_PRLI_NO_WRITE_RDY 0x0001
138 
139 /** Read FCP_XFER_RDY disabled */
140 #define FCP_PRLI_NO_READ_RDY 0x0002
141 
142 /** Has target functionality */
143 #define FCP_PRLI_TARGET 0x0010
144 
145 /** Has initiator functionality */
146 #define FCP_PRLI_INITIATOR 0x0020
147 
148 /** Data overlay allowed */
149 #define FCP_PRLI_OVERLAY 0x0040
150 
151 /** Confirm completion allowed */
152 #define FCP_PRLI_CONF 0x0080
153 
154 /** Retransmission supported */
155 #define FCP_PRLI_RETRY 0x0100
156 
157 /** Task retry identification */
158 #define FCP_PRLI_TASK_RETRY 0x0200
159 
160 /** REC ELS supported */
161 #define FCP_PRLI_REC 0x0400
162 
163 /** Enhanced discovery supported */
164 #define FCP_PRLI_ENH_DISC 0x0800
165 
166 /** An FCP device description */
167 struct fcp_description {
168 	/** Fibre Channel WWN */
169 	struct fc_name wwn;
170 	/** SCSI LUN */
171 	struct scsi_lun lun;
172 };
173 
174 #endif /* _IPXE_FCP_H */
175