]> git.ipfire.org Git - thirdparty/openssl.git/blame - ssl/packet_locl.h
Convert X509_REVOKED* functions to use const getters
[thirdparty/openssl.git] / ssl / packet_locl.h
CommitLineData
7e729bb5 1/*
846e33c7 2 * Copyright 2015-2016 The OpenSSL Project Authors. All Rights Reserved.
7e729bb5 3 *
846e33c7
RS
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
7e729bb5
MC
8 */
9
10#ifndef HEADER_PACKET_LOCL_H
11# define HEADER_PACKET_LOCL_H
12
13# include <string.h>
14# include <openssl/bn.h>
15# include <openssl/buffer.h>
31011544 16# include <openssl/crypto.h>
80e0ecbf 17# include <openssl/e_os2.h>
7e729bb5 18
1de1d768
RL
19# include "internal/numbers.h"
20
7e729bb5
MC
21# ifdef __cplusplus
22extern "C" {
23# endif
24
25typedef struct {
7e729bb5 26 /* Pointer to where we are currently reading from */
b6981744 27 const unsigned char *curr;
6a12a574
EK
28 /* Number of bytes remaining */
29 size_t remaining;
7e729bb5
MC
30} PACKET;
31
6a12a574 32/* Internal unchecked shorthand; don't use outside this file. */
80e0ecbf 33static ossl_inline void packet_forward(PACKET *pkt, size_t len)
6a12a574
EK
34{
35 pkt->curr += len;
36 pkt->remaining -= len;
37}
38
7e729bb5 39/*
bc6616a4 40 * Returns the number of bytes remaining to be read in the PACKET
7e729bb5 41 */
80e0ecbf 42static ossl_inline size_t PACKET_remaining(const PACKET *pkt)
7e729bb5 43{
6a12a574 44 return pkt->remaining;
7e729bb5
MC
45}
46
06217867
EK
47/*
48 * Returns a pointer to the first byte after the packet data.
49 * Useful for integrating with non-PACKET parsing code.
50 * Specifically, we use PACKET_end() to verify that a d2i_... call
51 * has consumed the entire packet contents.
52 */
53static ossl_inline const unsigned char *PACKET_end(const PACKET *pkt)
54{
55 return pkt->curr + pkt->remaining;
56}
ec30e856
EK
57/*
58 * Returns a pointer to the PACKET's current position.
59 * For use in non-PACKETized APIs.
ec30e856 60 */
b6981744 61static ossl_inline const unsigned char *PACKET_data(const PACKET *pkt)
ec30e856
EK
62{
63 return pkt->curr;
64}
65
7e729bb5
MC
66/*
67 * Initialise a PACKET with |len| bytes held in |buf|. This does not make a
68 * copy of the data so |buf| must be present for the whole time that the PACKET
69 * is being used.
70 */
b6981744
EK
71__owur static ossl_inline int PACKET_buf_init(PACKET *pkt,
72 const unsigned char *buf,
80e0ecbf 73 size_t len)
7e729bb5 74{
6a12a574 75 /* Sanity check for negative values. */
3fde6c92 76 if (len > (size_t)(SIZE_MAX / 2))
7e729bb5 77 return 0;
7e729bb5 78
6a12a574
EK
79 pkt->curr = buf;
80 pkt->remaining = len;
7e729bb5
MC
81 return 1;
82}
83
b3e2272c 84/* Initialize a PACKET to hold zero bytes. */
80e0ecbf 85static ossl_inline void PACKET_null_init(PACKET *pkt)
b3e2272c
EK
86{
87 pkt->curr = NULL;
88 pkt->remaining = 0;
89}
90
31011544
EK
91/*
92 * Returns 1 if the packet has length |num| and its contents equal the |num|
93 * bytes read from |ptr|. Returns 0 otherwise (lengths or contents not equal).
94 * If lengths are equal, performs the comparison in constant time.
95 */
80e0ecbf
DSH
96__owur static ossl_inline int PACKET_equal(const PACKET *pkt, const void *ptr,
97 size_t num)
98{
31011544
EK
99 if (PACKET_remaining(pkt) != num)
100 return 0;
101 return CRYPTO_memcmp(pkt->curr, ptr, num) == 0;
102}
103
7e729bb5
MC
104/*
105 * Peek ahead and initialize |subpkt| with the next |len| bytes read from |pkt|.
106 * Data is not copied: the |subpkt| packet will share its underlying buffer with
107 * the original |pkt|, so data wrapped by |pkt| must outlive the |subpkt|.
108 */
80e0ecbf
DSH
109__owur static ossl_inline int PACKET_peek_sub_packet(const PACKET *pkt,
110 PACKET *subpkt,
111 size_t len)
7e729bb5
MC
112{
113 if (PACKET_remaining(pkt) < len)
114 return 0;
115
f4f78ff7 116 return PACKET_buf_init(subpkt, pkt->curr, len);
7e729bb5
MC
117}
118
119/*
120 * Initialize |subpkt| with the next |len| bytes read from |pkt|. Data is not
121 * copied: the |subpkt| packet will share its underlying buffer with the
122 * original |pkt|, so data wrapped by |pkt| must outlive the |subpkt|.
123 */
80e0ecbf
DSH
124__owur static ossl_inline int PACKET_get_sub_packet(PACKET *pkt,
125 PACKET *subpkt,
126 size_t len)
7e729bb5
MC
127{
128 if (!PACKET_peek_sub_packet(pkt, subpkt, len))
129 return 0;
130
6a12a574 131 packet_forward(pkt, len);
7e729bb5
MC
132
133 return 1;
134}
135
80e0ecbf
DSH
136/*
137 * Peek ahead at 2 bytes in network order from |pkt| and store the value in
7e729bb5
MC
138 * |*data|
139 */
80e0ecbf
DSH
140__owur static ossl_inline int PACKET_peek_net_2(const PACKET *pkt,
141 unsigned int *data)
7e729bb5
MC
142{
143 if (PACKET_remaining(pkt) < 2)
144 return 0;
145
80e0ecbf 146 *data = ((unsigned int)(*pkt->curr)) << 8;
7e729bb5
MC
147 *data |= *(pkt->curr + 1);
148
149 return 1;
150}
151
152/* Equivalent of n2s */
153/* Get 2 bytes in network order from |pkt| and store the value in |*data| */
80e0ecbf
DSH
154__owur static ossl_inline int PACKET_get_net_2(PACKET *pkt,
155 unsigned int *data)
7e729bb5
MC
156{
157 if (!PACKET_peek_net_2(pkt, data))
158 return 0;
159
6a12a574 160 packet_forward(pkt, 2);
7e729bb5
MC
161
162 return 1;
163}
164
80e0ecbf
DSH
165/*
166 * Peek ahead at 3 bytes in network order from |pkt| and store the value in
7e729bb5
MC
167 * |*data|
168 */
80e0ecbf
DSH
169__owur static ossl_inline int PACKET_peek_net_3(const PACKET *pkt,
170 unsigned long *data)
7e729bb5
MC
171{
172 if (PACKET_remaining(pkt) < 3)
173 return 0;
174
80e0ecbf
DSH
175 *data = ((unsigned long)(*pkt->curr)) << 16;
176 *data |= ((unsigned long)(*(pkt->curr + 1))) << 8;
44128847 177 *data |= *(pkt->curr + 2);
7e729bb5
MC
178
179 return 1;
180}
181
182/* Equivalent of n2l3 */
183/* Get 3 bytes in network order from |pkt| and store the value in |*data| */
80e0ecbf
DSH
184__owur static ossl_inline int PACKET_get_net_3(PACKET *pkt,
185 unsigned long *data)
7e729bb5
MC
186{
187 if (!PACKET_peek_net_3(pkt, data))
188 return 0;
189
6a12a574 190 packet_forward(pkt, 3);
7e729bb5
MC
191
192 return 1;
193}
194
80e0ecbf
DSH
195/*
196 * Peek ahead at 4 bytes in network order from |pkt| and store the value in
7e729bb5
MC
197 * |*data|
198 */
80e0ecbf
DSH
199__owur static ossl_inline int PACKET_peek_net_4(const PACKET *pkt,
200 unsigned long *data)
7e729bb5
MC
201{
202 if (PACKET_remaining(pkt) < 4)
203 return 0;
204
80e0ecbf 205 *data = ((unsigned long)(*pkt->curr)) << 24;
44128847 206 *data |= ((unsigned long)(*(pkt->curr + 1))) << 16;
80e0ecbf
DSH
207 *data |= ((unsigned long)(*(pkt->curr + 2))) << 8;
208 *data |= *(pkt->curr + 3);
7e729bb5
MC
209
210 return 1;
211}
212
213/* Equivalent of n2l */
214/* Get 4 bytes in network order from |pkt| and store the value in |*data| */
80e0ecbf
DSH
215__owur static ossl_inline int PACKET_get_net_4(PACKET *pkt,
216 unsigned long *data)
7e729bb5
MC
217{
218 if (!PACKET_peek_net_4(pkt, data))
219 return 0;
220
6a12a574 221 packet_forward(pkt, 4);
7e729bb5
MC
222
223 return 1;
224}
225
226/* Peek ahead at 1 byte from |pkt| and store the value in |*data| */
80e0ecbf
DSH
227__owur static ossl_inline int PACKET_peek_1(const PACKET *pkt,
228 unsigned int *data)
7e729bb5
MC
229{
230 if (!PACKET_remaining(pkt))
231 return 0;
232
233 *data = *pkt->curr;
234
235 return 1;
236}
237
238/* Get 1 byte from |pkt| and store the value in |*data| */
80e0ecbf 239__owur static ossl_inline int PACKET_get_1(PACKET *pkt, unsigned int *data)
7e729bb5
MC
240{
241 if (!PACKET_peek_1(pkt, data))
242 return 0;
243
6a12a574 244 packet_forward(pkt, 1);
7e729bb5
MC
245
246 return 1;
247}
248
249/*
250 * Peek ahead at 4 bytes in reverse network order from |pkt| and store the value
251 * in |*data|
252 */
80e0ecbf
DSH
253__owur static ossl_inline int PACKET_peek_4(const PACKET *pkt,
254 unsigned long *data)
7e729bb5
MC
255{
256 if (PACKET_remaining(pkt) < 4)
257 return 0;
258
80e0ecbf
DSH
259 *data = *pkt->curr;
260 *data |= ((unsigned long)(*(pkt->curr + 1))) << 8;
44128847
MC
261 *data |= ((unsigned long)(*(pkt->curr + 2))) << 16;
262 *data |= ((unsigned long)(*(pkt->curr + 3))) << 24;
7e729bb5
MC
263
264 return 1;
265}
266
267/* Equivalent of c2l */
268/*
269 * Get 4 bytes in reverse network order from |pkt| and store the value in
270 * |*data|
271 */
80e0ecbf 272__owur static ossl_inline int PACKET_get_4(PACKET *pkt, unsigned long *data)
7e729bb5
MC
273{
274 if (!PACKET_peek_4(pkt, data))
275 return 0;
276
6a12a574 277 packet_forward(pkt, 4);
7e729bb5
MC
278
279 return 1;
280}
281
282/*
283 * Peek ahead at |len| bytes from the |pkt| and store a pointer to them in
284 * |*data|. This just points at the underlying buffer that |pkt| is using. The
285 * caller should not free this data directly (it will be freed when the
286 * underlying buffer gets freed
287 */
80e0ecbf 288__owur static ossl_inline int PACKET_peek_bytes(const PACKET *pkt,
b6981744 289 const unsigned char **data,
80e0ecbf 290 size_t len)
7e729bb5
MC
291{
292 if (PACKET_remaining(pkt) < len)
293 return 0;
294
295 *data = pkt->curr;
296
297 return 1;
298}
299
300/*
301 * Read |len| bytes from the |pkt| and store a pointer to them in |*data|. This
302 * just points at the underlying buffer that |pkt| is using. The caller should
303 * not free this data directly (it will be freed when the underlying buffer gets
304 * freed
305 */
80e0ecbf 306__owur static ossl_inline int PACKET_get_bytes(PACKET *pkt,
b6981744 307 const unsigned char **data,
80e0ecbf 308 size_t len)
7e729bb5
MC
309{
310 if (!PACKET_peek_bytes(pkt, data, len))
311 return 0;
312
6a12a574 313 packet_forward(pkt, len);
7e729bb5
MC
314
315 return 1;
316}
317
318/* Peek ahead at |len| bytes from |pkt| and copy them to |data| */
80e0ecbf
DSH
319__owur static ossl_inline int PACKET_peek_copy_bytes(const PACKET *pkt,
320 unsigned char *data,
321 size_t len)
7e729bb5
MC
322{
323 if (PACKET_remaining(pkt) < len)
324 return 0;
325
326 memcpy(data, pkt->curr, len);
327
328 return 1;
329}
330
6d41fc80
EK
331/*
332 * Read |len| bytes from |pkt| and copy them to |data|.
333 * The caller is responsible for ensuring that |data| can hold |len| bytes.
334 */
80e0ecbf
DSH
335__owur static ossl_inline int PACKET_copy_bytes(PACKET *pkt,
336 unsigned char *data,
337 size_t len)
7e729bb5
MC
338{
339 if (!PACKET_peek_copy_bytes(pkt, data, len))
340 return 0;
341
6a12a574 342 packet_forward(pkt, len);
7e729bb5
MC
343
344 return 1;
345}
346
67202973
EK
347/*
348 * Copy packet data to |dest|, and set |len| to the number of copied bytes.
349 * If the packet has more than |dest_len| bytes, nothing is copied.
350 * Returns 1 if the packet data fits in |dest_len| bytes, 0 otherwise.
351 * Does not forward PACKET position (because it is typically the last thing
352 * done with a given PACKET).
353 */
80e0ecbf
DSH
354__owur static ossl_inline int PACKET_copy_all(const PACKET *pkt,
355 unsigned char *dest,
356 size_t dest_len, size_t *len)
357{
67202973
EK
358 if (PACKET_remaining(pkt) > dest_len) {
359 *len = 0;
360 return 0;
361 }
362 *len = pkt->remaining;
363 memcpy(dest, pkt->curr, pkt->remaining);
364 return 1;
365}
366
6d41fc80
EK
367/*
368 * Copy |pkt| bytes to a newly allocated buffer and store a pointer to the
369 * result in |*data|, and the length in |len|.
370 * If |*data| is not NULL, the old data is OPENSSL_free'd.
371 * If the packet is empty, or malloc fails, |*data| will be set to NULL.
372 * Returns 1 if the malloc succeeds and 0 otherwise.
373 * Does not forward PACKET position (because it is typically the last thing
374 * done with a given PACKET).
375 */
80e0ecbf
DSH
376__owur static ossl_inline int PACKET_memdup(const PACKET *pkt,
377 unsigned char **data, size_t *len)
6d41fc80
EK
378{
379 size_t length;
380
381 OPENSSL_free(*data);
382 *data = NULL;
383 *len = 0;
384
385 length = PACKET_remaining(pkt);
386
387 if (length == 0)
388 return 1;
389
7644a9ae 390 *data = OPENSSL_memdup(pkt->curr, length);
6d41fc80
EK
391 if (*data == NULL)
392 return 0;
393
394 *len = length;
395 return 1;
396}
397
398/*
399 * Read a C string from |pkt| and copy to a newly allocated, NUL-terminated
400 * buffer. Store a pointer to the result in |*data|.
401 * If |*data| is not NULL, the old data is OPENSSL_free'd.
402 * If the data in |pkt| does not contain a NUL-byte, the entire data is
403 * copied and NUL-terminated.
404 * Returns 1 if the malloc succeeds and 0 otherwise.
405 * Does not forward PACKET position (because it is typically the last thing done
406 * with a given PACKET).
407 */
80e0ecbf 408__owur static ossl_inline int PACKET_strndup(const PACKET *pkt, char **data)
6d41fc80
EK
409{
410 OPENSSL_free(*data);
32942870
EK
411
412 /* This will succeed on an empty packet, unless pkt->curr == NULL. */
80e0ecbf 413 *data = OPENSSL_strndup((const char *)pkt->curr, PACKET_remaining(pkt));
6d41fc80
EK
414 return (*data != NULL);
415}
416
06217867
EK
417/* Returns 1 if |pkt| contains at least one 0-byte, 0 otherwise. */
418static ossl_inline int PACKET_contains_zero_byte(const PACKET *pkt)
419{
420 return memchr(pkt->curr, 0, pkt->remaining) != NULL;
421}
422
7e729bb5 423/* Move the current reading position forward |len| bytes */
80e0ecbf 424__owur static ossl_inline int PACKET_forward(PACKET *pkt, size_t len)
7e729bb5
MC
425{
426 if (PACKET_remaining(pkt) < len)
427 return 0;
428
6a12a574 429 packet_forward(pkt, len);
7e729bb5
MC
430
431 return 1;
432}
433
ec30e856
EK
434/*
435 * Reads a variable-length vector prefixed with a one-byte length, and stores
436 * the contents in |subpkt|. |pkt| can equal |subpkt|.
437 * Data is not copied: the |subpkt| packet will share its underlying buffer with
438 * the original |pkt|, so data wrapped by |pkt| must outlive the |subpkt|.
439 * Upon failure, the original |pkt| and |subpkt| are not modified.
440 */
80e0ecbf
DSH
441__owur static ossl_inline int PACKET_get_length_prefixed_1(PACKET *pkt,
442 PACKET *subpkt)
ec30e856 443{
80e0ecbf 444 unsigned int length;
b6981744 445 const unsigned char *data;
80e0ecbf
DSH
446 PACKET tmp = *pkt;
447 if (!PACKET_get_1(&tmp, &length) ||
448 !PACKET_get_bytes(&tmp, &data, (size_t)length)) {
449 return 0;
450 }
451
452 *pkt = tmp;
453 subpkt->curr = data;
454 subpkt->remaining = length;
455
456 return 1;
ec30e856
EK
457}
458
06217867
EK
459/*
460 * Like PACKET_get_length_prefixed_1, but additionally, fails when there are
461 * leftover bytes in |pkt|.
462 */
463__owur static ossl_inline int PACKET_as_length_prefixed_1(PACKET *pkt, PACKET *subpkt)
464{
465 unsigned int length;
466 const unsigned char *data;
467 PACKET tmp = *pkt;
468 if (!PACKET_get_1(&tmp, &length) ||
469 !PACKET_get_bytes(&tmp, &data, (size_t)length) ||
470 PACKET_remaining(&tmp) != 0) {
471 return 0;
472 }
473
474 *pkt = tmp;
475 subpkt->curr = data;
476 subpkt->remaining = length;
477
478 return 1;
479}
480
ec30e856
EK
481/*
482 * Reads a variable-length vector prefixed with a two-byte length, and stores
483 * the contents in |subpkt|. |pkt| can equal |subpkt|.
484 * Data is not copied: the |subpkt| packet will share its underlying buffer with
485 * the original |pkt|, so data wrapped by |pkt| must outlive the |subpkt|.
486 * Upon failure, the original |pkt| and |subpkt| are not modified.
487 */
80e0ecbf
DSH
488__owur static ossl_inline int PACKET_get_length_prefixed_2(PACKET *pkt,
489 PACKET *subpkt)
ec30e856 490{
80e0ecbf 491 unsigned int length;
b6981744 492 const unsigned char *data;
80e0ecbf 493 PACKET tmp = *pkt;
06217867 494
80e0ecbf
DSH
495 if (!PACKET_get_net_2(&tmp, &length) ||
496 !PACKET_get_bytes(&tmp, &data, (size_t)length)) {
497 return 0;
498 }
499
500 *pkt = tmp;
501 subpkt->curr = data;
502 subpkt->remaining = length;
503
504 return 1;
ec30e856
EK
505}
506
06217867
EK
507/*
508 * Like PACKET_get_length_prefixed_2, but additionally, fails when there are
509 * leftover bytes in |pkt|.
510 */
511__owur static ossl_inline int PACKET_as_length_prefixed_2(PACKET *pkt,
512 PACKET *subpkt)
513{
514 unsigned int length;
515 const unsigned char *data;
516 PACKET tmp = *pkt;
517
518 if (!PACKET_get_net_2(&tmp, &length) ||
519 !PACKET_get_bytes(&tmp, &data, (size_t)length) ||
520 PACKET_remaining(&tmp) != 0) {
521 return 0;
522 }
523
524 *pkt = tmp;
525 subpkt->curr = data;
526 subpkt->remaining = length;
527
528 return 1;
529}
530
ec30e856
EK
531/*
532 * Reads a variable-length vector prefixed with a three-byte length, and stores
533 * the contents in |subpkt|. |pkt| can equal |subpkt|.
534 * Data is not copied: the |subpkt| packet will share its underlying buffer with
535 * the original |pkt|, so data wrapped by |pkt| must outlive the |subpkt|.
536 * Upon failure, the original |pkt| and |subpkt| are not modified.
537 */
80e0ecbf
DSH
538__owur static ossl_inline int PACKET_get_length_prefixed_3(PACKET *pkt,
539 PACKET *subpkt)
ec30e856 540{
80e0ecbf 541 unsigned long length;
b6981744 542 const unsigned char *data;
80e0ecbf
DSH
543 PACKET tmp = *pkt;
544 if (!PACKET_get_net_3(&tmp, &length) ||
545 !PACKET_get_bytes(&tmp, &data, (size_t)length)) {
546 return 0;
547 }
548
549 *pkt = tmp;
550 subpkt->curr = data;
551 subpkt->remaining = length;
552
553 return 1;
ec30e856 554}
7e729bb5
MC
555# ifdef __cplusplus
556}
557# endif
558
80e0ecbf 559#endif /* HEADER_PACKET_LOCL_H */