These changes are the raw update to qemu-2.6.
[kvmfornfv.git] / qemu / roms / ipxe / src / include / ipxe / pccrr.h
1 #ifndef _IPXE_PCCRR_H
2 #define _IPXE_PCCRR_H
3
4 /** @file
5  *
6  * Peer Content Caching and Retrieval: Retrieval Protocol [MS-PCCRR]
7  *
8  * All fields are in network byte order.
9  *
10  */
11
12 FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
13
14 #include <stdint.h>
15 #include <ipxe/uaccess.h>
16
17 /** Magic retrieval URI path */
18 #define PEERDIST_MAGIC_PATH "/116B50EB-ECE2-41ac-8429-9F9E963361B7/"
19
20 /** Retrieval protocol version */
21 union peerdist_msg_version {
22         /** Raw version number */
23         uint32_t raw;
24         /** Major:minor version number */
25         struct {
26                 /** Minor version number */
27                 uint16_t minor;
28                 /** Major version number */
29                 uint16_t major;
30         } __attribute__ (( packed ));
31 } __attribute__ (( packed ));
32
33 /** Retrieval protocol version 1.0 */
34 #define PEERDIST_MSG_VERSION_1_0 0x00000001UL
35
36 /** Retrieval protocol version 2.0 */
37 #define PEERDIST_MSG_VERSION_2_0 0x00000002UL
38
39 /** Retrieval protocol supported versions */
40 struct peerdist_msg_versions {
41         /** Minimum supported protocol version */
42         union peerdist_msg_version min;
43         /** Maximum supported protocol version */
44         union peerdist_msg_version max;
45 } __attribute__ (( packed ));
46
47 /** Retrieval protocol block range */
48 struct peerdist_msg_range {
49         /** First block in range */
50         uint32_t first;
51         /** Number of blocks in range */
52         uint32_t count;
53 } __attribute__ (( packed ));
54
55 /** Retrieval protocol segment ID header */
56 struct peerdist_msg_segment {
57         /** Digest size (i.e. length of segment ID) */
58         uint32_t digestsize;
59         /* Followed by a single variable-length ID and padding:
60          *
61          * uint8_t id[digestsize];
62          * uint8_t pad[ (-digestsize) & 0x3 ];
63          */
64 } __attribute__ (( packed ));
65
66 /** Retrieval protocol segment ID
67  *
68  * @v digestsize        Digest size
69  */
70 #define peerdist_msg_segment_t( digestsize )                            \
71         struct {                                                        \
72                 struct peerdist_msg_segment segment;                    \
73                 uint8_t id[digestsize];                                 \
74                 uint8_t pad[ ( -(digestsize) ) & 0x3 ];                 \
75         } __attribute__ (( packed ))
76
77 /** Retrieval protocol block range list header */
78 struct peerdist_msg_ranges {
79         /** Number of ranges */
80         uint32_t count;
81         /* Followed by an array of block ranges:
82          *
83          * struct peerdist_msg_range range[count];
84          */
85 } __attribute__ (( packed ));
86
87 /** Retrieval protocol block range list
88  *
89  * @v count             Number of ranges
90  */
91 #define peerdist_msg_ranges_t( count )                                  \
92         struct {                                                        \
93                 struct peerdist_msg_ranges ranges;                      \
94                 struct peerdist_msg_range range[count];                 \
95         } __attribute__ (( packed ))
96
97 /** Retrieval protocol data block header */
98 struct peerdist_msg_block {
99         /** Length of data block */
100         uint32_t len;
101         /* Followed by the (encrypted) data block:
102          *
103          * uint8_t data[len];
104          */
105 } __attribute__ (( packed ));
106
107 /** Retrieval protocol data block */
108 #define peerdist_msg_block_t( len )                                     \
109         struct {                                                        \
110                 struct peerdist_msg_block block;                        \
111                 uint8_t data[len];                                      \
112         } __attribute__ (( packed ))
113
114 /** Retrieval protocol initialisation vector header */
115 struct peerdist_msg_iv {
116         /** Cipher block size */
117         uint32_t blksize;
118         /* Followed by the initialisation vector:
119          *
120          * uint8_t data[blksize];
121          */
122 } __attribute__ (( packed ));
123
124 /** Retrieval protocol initialisation vector */
125 #define peerdist_msg_iv_t( blksize )                                    \
126         struct {                                                        \
127                 struct peerdist_msg_iv iv;                              \
128                 uint8_t data[blksize];                                  \
129         } __attribute__ (( packed ))
130
131 /** Retrieval protocol useless VRF data header */
132 struct peerdist_msg_useless_vrf {
133         /** Length of useless VRF data */
134         uint32_t len;
135         /* Followed by a variable-length useless VRF data block and
136          * padding:
137          *
138          * uint8_t data[len];
139          * uint8_t pad[ (-len) & 0x3 ];
140          */
141 } __attribute__ (( packed ));
142
143 /** Retrieval protocol useless VRF data */
144 #define peerdist_msg_useless_vrf_t( vrf_len )                           \
145         struct {                                                        \
146                 struct peerdist_msg_useless_vrf vrf;                    \
147                 uint8_t data[vrf_len];                                  \
148                 uint8_t pad[ ( -(vrf_len) ) & 0x3 ];                    \
149         } __attribute__ (( packed ))
150
151 /** Retrieval protocol message header */
152 struct peerdist_msg_header {
153         /** Protocol version
154          *
155          * This is the protocol version in which the message type was
156          * first defined.
157          */
158         union peerdist_msg_version version;
159         /** Message type */
160         uint32_t type;
161         /** Message size (including this header) */
162         uint32_t len;
163         /** Cryptographic algorithm ID */
164         uint32_t algorithm;
165 } __attribute__ (( packed ));
166
167 /** Retrieval protocol cryptographic algorithm IDs */
168 enum peerdist_msg_algorithm {
169         /** No encryption */
170         PEERDIST_MSG_PLAINTEXT = 0x00000000UL,
171         /** AES-128 in CBC mode */
172         PEERDIST_MSG_AES_128_CBC = 0x00000001UL,
173         /** AES-192 in CBC mode */
174         PEERDIST_MSG_AES_192_CBC = 0x00000002UL,
175         /** AES-256 in CBC mode */
176         PEERDIST_MSG_AES_256_CBC = 0x00000003UL,
177 };
178
179 /** Retrieval protocol transport response header */
180 struct peerdist_msg_transport_header {
181         /** Length (excluding this header)
182          *
183          * This seems to be identical in both purpose and value to the
184          * length found within the message header, and therefore
185          * serves no useful purpose.
186          */
187         uint32_t len;
188 } __attribute__ (( packed ));
189
190 /** Retrieval protocol negotiation request */
191 struct peerdist_msg_nego_req {
192         /** Message header */
193         struct peerdist_msg_header hdr;
194         /** Supported versions */
195         struct peerdist_msg_versions versions;
196 } __attribute__ (( packed ));
197
198 /** Retrieval protocol negotiation request version */
199 #define PEERDIST_MSG_NEGO_REQ_VERSION PEERDIST_MSG_VERSION_1_0
200
201 /** Retrieval protocol negotiation request type */
202 #define PEERDIST_MSG_NEGO_REQ_TYPE 0x00000000UL
203
204 /** Retrieval protocol negotiation response */
205 struct peerdist_msg_nego_resp {
206         /** Message header */
207         struct peerdist_msg_header hdr;
208         /** Supported versions */
209         struct peerdist_msg_versions versions;
210 } __attribute__ (( packed ));
211
212 /** Retrieval protocol negotiation response version */
213 #define PEERDIST_MSG_NEGO_RESP_VERSION PEERDIST_MSG_VERSION_1_0
214
215 /** Retrieval protocol negotiation response type */
216 #define PEERDIST_MSG_NEGO_RESP_TYPE 0x00000001UL
217
218 /** Retrieval protocol block list request header */
219 struct peerdist_msg_getblklist {
220         /** Message header */
221         struct peerdist_msg_header hdr;
222         /* Followed by a segment ID and a block range list:
223          *
224          * peerdist_msg_segment_t(digestsize) segment;
225          * peerdist_msg_ranges_t(count) ranges;
226          */
227 } __attribute__ (( packed ));
228
229 /** Retrieval protocol block list request
230  *
231  * @v digestsize        Digest size
232  * @v count             Block range count
233  */
234 #define peerdist_msg_getblklist_t( digestsize, count )                  \
235         struct {                                                        \
236                 struct peerdist_msg_getblklist getblklist;              \
237                 peerdist_msg_segment_t ( digestsize ) segment;          \
238                 peerdist_msg_ranges_t ( count ) ranges;                 \
239         } __attribute__ (( packed ))
240
241 /** Retrieval protocol block list request version */
242 #define PEERDIST_MSG_GETBLKLIST_VERSION PEERDIST_MSG_VERSION_1_0
243
244 /** Retrieval protocol block list request type */
245 #define PEERDIST_MSG_GETBLKLIST_TYPE 0x00000002UL
246
247 /** Retrieval protocol block fetch request header */
248 struct peerdist_msg_getblks {
249         /** Message header */
250         struct peerdist_msg_header hdr;
251         /* Followed by a segment ID, a block range list, and a useless
252          * VRF block:
253          *
254          * peerdist_msg_segment_t(digestsize) segment;
255          * peerdist_msg_ranges_t(count) ranges;
256          * peerdist_msg_vrf_t(vrf_len) vrf;
257          */
258 } __attribute__ (( packed ));
259
260 /** Retrieval protocol block fetch request
261  *
262  * @v digestsize        Digest size
263  * @v count             Block range count
264  * @v vrf_len           Length of uselessness
265  */
266 #define peerdist_msg_getblks_t( digestsize, count, vrf_len )            \
267         struct {                                                        \
268                 struct peerdist_msg_getblks getblks;                    \
269                 peerdist_msg_segment_t ( digestsize ) segment;          \
270                 peerdist_msg_ranges_t ( count ) ranges;                 \
271                 peerdist_msg_useless_vrf_t ( vrf_len );                 \
272         } __attribute__ (( packed ))
273
274 /** Retrieval protocol block fetch request version */
275 #define PEERDIST_MSG_GETBLKS_VERSION PEERDIST_MSG_VERSION_1_0
276
277 /** Retrieval protocol block fetch request type */
278 #define PEERDIST_MSG_GETBLKS_TYPE 0x00000003UL
279
280 /** Retrieval protocol block list response header */
281 struct peerdist_msg_blklist {
282         /** Message header */
283         struct peerdist_msg_header hdr;
284         /* Followed by a segment ID, a block range list, and a next
285          * block index:
286          *
287          * peerdist_msg_segment_t(digestsize) segment;
288          * peerdist_msg_ranges_t(count) ranges;
289          * uint32_t next;
290          */
291 } __attribute__ (( packed ));
292
293 /** Retrieval protocol block list response
294  *
295  * @v digestsize        Digest size
296  * @v count             Block range count
297  */
298 #define peerdist_msg_blklist_t( digestsize, count )                     \
299         struct {                                                        \
300                 struct peerdist_msg_blklist blklist;                    \
301                 peerdist_msg_segment_t ( digestsize ) segment;          \
302                 peerdist_msg_ranges_t ( count ) ranges;                 \
303                 uint32_t next;                                          \
304         } __attribute__ (( packed ))
305
306 /** Retrieval protocol block list response version */
307 #define PEERDIST_MSG_BLKLIST_VERSION PEERDIST_MSG_VERSION_1_0
308
309 /** Retrieval protocol block list response type */
310 #define PEERDIST_MSG_BLKLIST_TYPE 0x00000004UL
311
312 /** Retrieval protocol block fetch response header */
313 struct peerdist_msg_blk {
314         /** Message header */
315         struct peerdist_msg_header hdr;
316         /* Followed by a segment ID, a block index, a next block
317          * index, a data block, a useless VRF block, and an
318          * initialisation vector:
319          *
320          * peerdist_msg_segment_t(digestsize) segment;
321          * uint32_t index;
322          * uint32_t next;
323          * peerdist_msg_block_t(len) data;
324          * peerdist_msg_useless_vrf_t(vrf_len) vrf;
325          * peerdist_msg_iv_t(blksize) iv;
326          */
327 } __attribute__ (( packed ));
328
329 /** Retrieval protocol block fetch response
330  *
331  * @v digestsize        Digest size
332  * @v len               Data block length
333  * @v vrf_len           Length of uselessness
334  * @v blksize           Cipher block size
335  */
336 #define peerdist_msg_blk_t( digestsize, len, vrf_len, blksize )         \
337         struct {                                                        \
338                 struct peerdist_msg_blk blk;                            \
339                 peerdist_msg_segment_t ( digestsize ) segment;          \
340                 uint32_t index;                                         \
341                 uint32_t next;                                          \
342                 peerdist_msg_block_t ( len ) block;                     \
343                 peerdist_msg_useless_vrf_t ( vrf_len ) vrf;             \
344                 peerdist_msg_iv_t ( blksize ) iv;                       \
345         } __attribute__ (( packed ))
346
347 /** Retrieval protocol block fetch response version */
348 #define PEERDIST_MSG_BLK_VERSION PEERDIST_MSG_VERSION_1_0
349
350 /** Retrieval protocol block fetch response type */
351 #define PEERDIST_MSG_BLK_TYPE 0x00000005UL
352
353 /**
354  * Parse retrieval protocol block fetch response
355  *
356  * @v raw               Raw data
357  * @v raw_len           Length of raw data
358  * @v digestsize        Digest size
359  * @v blksize           Cipher block size
360  * @v blk               Structure to fill in
361  * @ret rc              Return status code
362  */
363 #define peerdist_msg_blk( raw, raw_len, digestsize, blksize, blk ) ( {  \
364         assert ( sizeof ( (blk)->segment.id ) == (digestsize) );        \
365         assert ( sizeof ( (blk)->block.data ) == 0 );                   \
366         assert ( sizeof ( (blk)->vrf.data ) == 0 );                     \
367         assert ( sizeof ( (blk)->iv.data ) == blksize );                \
368         peerdist_msg_blk_untyped ( (raw), (raw_len), (digestsize),      \
369                                    (blksize), blk );                    \
370         } )
371
372 extern int peerdist_msg_blk_untyped ( userptr_t raw, size_t raw_len,
373                                       size_t digestsize, size_t blksize,
374                                       void *out );
375
376 #endif /* _IPXE_PCCRR_H */