d7f8b4ab20811081d1018b524d81b02a66e910d4
[people/pcmattman/gpxe.git] / src / include / gpxe / infiniband.h
1 #ifndef _GPXE_INFINIBAND_H
2 #define _GPXE_INFINIBAND_H
3
4 /** @file
5  *
6  * Infiniband protocol
7  *
8  */
9
10 #include <stdint.h>
11 #include <gpxe/netdevice.h>
12
13 /** An Infiniband Global Identifier */
14 struct ib_gid {
15         uint8_t bytes[16];
16 };
17
18 /** An Infiniband Global Route Header */
19 struct ib_global_route_header {
20         /** IP version, traffic class, and flow label
21          *
22          *  4 bits : Version of the GRH
23          *  8 bits : Traffic class
24          * 20 bits : Flow label
25          */
26         uint32_t ipver_tclass_flowlabel;
27         /** Payload length */
28         uint16_t paylen;
29         /** Next header */
30         uint8_t nxthdr;
31         /** Hop limit */
32         uint8_t hoplmt;
33         /** Source GID */
34         struct ib_gid sgid;
35         /** Destiniation GID */
36         struct ib_gid dgid;
37 } __attribute__ (( packed ));
38
39 /** Infiniband MAC address length */
40 #define IB_ALEN 20
41
42 /** An Infiniband MAC address */
43 struct ib_mac {
44         /** Queue pair number
45          *
46          * MSB must be zero; QPNs are only 24-bit.
47          */
48         uint32_t qpn;
49         /** Port GID */
50         struct ib_gid gid;
51 } __attribute__ (( packed ));
52
53 /** Infiniband link-layer header length */
54 #define IB_HLEN 4
55
56 /** An Infiniband link-layer header */
57 struct ibhdr {
58         /** Network-layer protocol */
59         uint16_t proto;
60         /** Reserved, must be zero */
61         uint16_t reserved;
62 } __attribute__ (( packed ));
63
64
65
66 struct ib_device;
67 struct ib_queue_pair;
68 struct ib_completion_queue;
69
70 /** An Infiniband Work Queue */
71 struct ib_work_queue {
72         /** Containing queue pair */
73         struct ib_queue_pair *qp;
74         /** "Is a send queue" flag */
75         int is_send;
76         /** Associated completion queue */
77         struct ib_completion_queue *cq;
78         /** List of work queues on this completion queue */
79         struct list_head list;
80         /** Number of work queue entries */
81         unsigned int num_wqes;
82         /** Next work queue entry index
83          *
84          * This is the index of the next entry to be filled (i.e. the
85          * first empty entry).  This value is not bounded by num_wqes;
86          * users must logical-AND with (num_wqes-1) to generate an
87          * array index.
88          */
89         unsigned long next_idx;
90         /** I/O buffers assigned to work queue */
91         struct io_buffer **iobufs;
92         /** Device private data */
93         void *dev_priv;
94 };
95
96 /** An Infiniband Queue Pair */
97 struct ib_queue_pair {
98         /** Queue Pair Number */
99         unsigned long qpn;
100         /** Send queue */
101         struct ib_work_queue send;
102         /** Receive queue */
103         struct ib_work_queue recv;
104         /** Device private data */
105         void *dev_priv;
106         /** Queue owner private data */
107         void *owner_priv;
108 };
109
110 /** An Infiniband Completion Queue */
111 struct ib_completion_queue {
112         /** Completion queue number */
113         unsigned long cqn;
114         /** Number of completion queue entries */
115         unsigned int num_cqes;
116         /** Next completion queue entry index
117          *
118          * This is the index of the next entry to be filled (i.e. the
119          * first empty entry).  This value is not bounded by num_wqes;
120          * users must logical-AND with (num_wqes-1) to generate an
121          * array index.
122          */
123         unsigned long next_idx;
124         /** List of work queues completing to this queue */
125         struct list_head work_queues;
126         /** Device private data */
127         void *dev_priv;
128 };
129
130 /** An Infiniband completion */
131 struct ib_completion {
132         /** Syndrome
133          *
134          * If non-zero, then the completion is in error.
135          */
136         unsigned int syndrome;
137         /** Length */
138         size_t len;
139 };
140
141 /** An Infiniband completion handler
142  *
143  * @v ibdev             Infiniband device
144  * @v qp                Queue pair
145  * @v completion        Completion
146  * @v iobuf             I/O buffer
147  */
148 typedef void ( * ib_completer_t ) ( struct ib_device *ibdev,
149                                     struct ib_queue_pair *qp,
150                                     struct ib_completion *completion,
151                                     struct io_buffer *iobuf );
152
153 /** An Infiniband Address Vector */
154 struct ib_address_vector {
155         /** Destination Queue Pair */
156         unsigned int dest_qp;
157         /** Queue key */
158         unsigned int qkey;
159         /** Destination Local ID */
160         unsigned int dlid;
161         /** Rate */
162         unsigned int rate;
163         /** Service level */
164         unsigned int sl;
165         /** GID is present */
166         unsigned int gid_present;
167         /** GID */
168         struct ib_gid gid;
169 };
170
171 /**
172  * Infiniband device operations
173  *
174  * These represent a subset of the Infiniband Verbs.
175  */
176 struct ib_device_operations {
177         /**
178          * Create completion queue
179          *
180          * @v ibdev             Infiniband device
181          * @v cq                Completion queue
182          * @ret rc              Return status code
183          */
184         int ( * create_cq ) ( struct ib_device *ibdev,
185                               struct ib_completion_queue *cq );
186         /**
187          * Destroy completion queue
188          *
189          * @v ibdev             Infiniband device
190          * @v cq                Completion queue
191          */
192         void ( * destroy_cq ) ( struct ib_device *ibdev,
193                                 struct ib_completion_queue *cq );
194         /** Post send work queue entry
195          *
196          * @v ibdev             Infiniband device
197          * @v qp                Queue pair
198          * @v av                Address vector
199          * @v iobuf             I/O buffer
200          * @ret rc              Return status code
201          *
202          * If this method returns success, the I/O buffer remains
203          * owned by the queue pair.  If this method returns failure,
204          * the I/O buffer is immediately released; the failure is
205          * interpreted as "failure to enqueue buffer".
206          */
207         int ( * post_send ) ( struct ib_device *ibdev,
208                               struct ib_queue_pair *qp,
209                               struct ib_address_vector *av,
210                               struct io_buffer *iobuf );
211         /**
212          * Post receive work queue entry
213          *
214          * @v ibdev             Infiniband device
215          * @v qp                Queue pair
216          * @v iobuf             I/O buffer
217          * @ret rc              Return status code
218          *
219          * If this method returns success, the I/O buffer remains
220          * owned by the queue pair.  If this method returns failure,
221          * the I/O buffer is immediately released; the failure is
222          * interpreted as "failure to enqueue buffer".
223          */
224         int ( * post_recv ) ( struct ib_device *ibdev,
225                               struct ib_queue_pair *qp,
226                               struct io_buffer *iobuf );
227         /** Poll completion queue
228          *
229          * @v ibdev             Infiniband device
230          * @v cq                Completion queue
231          * @v complete_send     Send completion handler
232          * @v complete_recv     Receive completion handler
233          *
234          * The completion handler takes ownership of the I/O buffer.
235          */
236         void ( * poll_cq ) ( struct ib_device *ibdev,
237                              struct ib_completion_queue *cq,
238                              ib_completer_t complete_send,
239                              ib_completer_t complete_recv );
240 };
241
242 /** An Infiniband device */
243 struct ib_device {      
244         /** Infiniband operations */
245         struct ib_device_operations *op;
246         /** Device private data */
247         void *dev_priv;
248 };
249
250
251 extern struct ib_work_queue * ib_find_wq ( struct ib_completion_queue *cq,
252                                            unsigned long qpn, int is_send );
253
254
255
256 extern struct ll_protocol infiniband_protocol;
257
258 extern const char * ib_ntoa ( const void *ll_addr );
259
260 /**
261  * Allocate Infiniband device
262  *
263  * @v priv_size         Size of driver private data
264  * @ret netdev          Network device, or NULL
265  */
266 static inline struct net_device * alloc_ibdev ( size_t priv_size ) {
267         struct net_device *netdev;
268
269         netdev = alloc_netdev ( priv_size );
270         if ( netdev ) {
271                 netdev->ll_protocol = &infiniband_protocol;
272         }
273         return netdev;
274 }
275
276 #endif /* _GPXE_INFINIBAND_H */