|  | @@ -0,0 +1,376 @@
 | 
		
	
		
			
			|  | 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 */
 |