2 * Copyright 1995-2016 The OpenSSL Project Authors. All Rights Reserved.
4 * Licensed under the Apache License 2.0 (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
12 #include "internal/cryptlib.h"
13 #include <openssl/asn1.h>
14 #include "asn1_local.h"
16 static int asn1_get_length(const unsigned char **pp
, int *inf
, long *rl
,
18 static void asn1_put_length(unsigned char **pp
, int length
);
20 static int _asn1_check_infinite_end(const unsigned char **p
, long len
)
23 * If there is 0 or 1 byte left, the length check should pick things up
28 if ((len
>= 2) && ((*p
)[0] == 0) && ((*p
)[1] == 0)) {
36 int ASN1_check_infinite_end(unsigned char **p
, long len
)
38 return _asn1_check_infinite_end((const unsigned char **)p
, len
);
41 int ASN1_const_check_infinite_end(const unsigned char **p
, long len
)
43 return _asn1_check_infinite_end(p
, len
);
46 int ASN1_get_object(const unsigned char **pp
, long *plength
, int *ptag
,
47 int *pclass
, long omax
)
51 const unsigned char *p
= *pp
;
57 ret
= (*p
& V_ASN1_CONSTRUCTED
);
58 xclass
= (*p
& V_ASN1_PRIVATE
);
59 i
= *p
& V_ASN1_PRIMITIVE_TAG
;
60 if (i
== V_ASN1_PRIMITIVE_TAG
) { /* high-tag */
70 if (len
> (INT_MAX
>> 7L))
86 if (!asn1_get_length(&p
, &inf
, plength
, max
))
89 if (inf
&& !(ret
& V_ASN1_CONSTRUCTED
))
92 if (*plength
> (omax
- (p
- *pp
))) {
93 ASN1err(ASN1_F_ASN1_GET_OBJECT
, ASN1_R_TOO_LONG
);
95 * Set this so that even if things are not long enough the values are
103 ASN1err(ASN1_F_ASN1_GET_OBJECT
, ASN1_R_HEADER_TOO_LONG
);
108 * Decode a length field.
109 * The short form is a single byte defining a length 0 - 127.
110 * The long form is a byte 0 - 127 with the top bit set and this indicates
111 * the number of following octets that contain the length. These octets
112 * are stored most significant digit first.
114 static int asn1_get_length(const unsigned char **pp
, int *inf
, long *rl
,
117 const unsigned char *p
= *pp
;
118 unsigned long ret
= 0;
132 /* Skip leading zeroes */
133 while (i
> 0 && *p
== 0) {
137 if (i
> (int)sizeof(long))
156 * class 0 is constructed constructed == 2 for indefinite length constructed
158 void ASN1_put_object(unsigned char **pp
, int constructed
, int length
, int tag
,
161 unsigned char *p
= *pp
;
164 i
= (constructed
) ? V_ASN1_CONSTRUCTED
: 0;
165 i
|= (xclass
& V_ASN1_PRIVATE
);
167 *(p
++) = i
| (tag
& V_ASN1_PRIMITIVE_TAG
);
169 *(p
++) = i
| V_ASN1_PRIMITIVE_TAG
;
170 for (i
= 0, ttag
= tag
; ttag
> 0; i
++)
181 if (constructed
== 2)
184 asn1_put_length(&p
, length
);
188 int ASN1_put_eoc(unsigned char **pp
)
190 unsigned char *p
= *pp
;
198 static void asn1_put_length(unsigned char **pp
, int length
)
200 unsigned char *p
= *pp
;
204 *(p
++) = (unsigned char)length
;
207 for (i
= 0; len
> 0; i
++)
212 p
[i
] = length
& 0xff;
220 int ASN1_object_size(int constructed
, int length
, int tag
)
232 if (constructed
== 2) {
244 if (ret
>= INT_MAX
- length
)
249 int ASN1_STRING_copy(ASN1_STRING
*dst
, const ASN1_STRING
*str
)
253 dst
->type
= str
->type
;
254 if (!ASN1_STRING_set(dst
, str
->data
, str
->length
))
256 /* Copy flags but preserve embed value */
257 dst
->flags
&= ASN1_STRING_FLAG_EMBED
;
258 dst
->flags
|= str
->flags
& ~ASN1_STRING_FLAG_EMBED
;
262 ASN1_STRING
*ASN1_STRING_dup(const ASN1_STRING
*str
)
268 ret
= ASN1_STRING_new();
271 if (!ASN1_STRING_copy(ret
, str
)) {
272 ASN1_STRING_free(ret
);
278 int ASN1_STRING_set(ASN1_STRING
*str
, const void *_data
, int len
)
281 const char *data
= _data
;
289 if ((str
->length
<= len
) || (str
->data
== NULL
)) {
291 str
->data
= OPENSSL_realloc(c
, len
+ 1);
292 if (str
->data
== NULL
) {
293 ASN1err(ASN1_F_ASN1_STRING_SET
, ERR_R_MALLOC_FAILURE
);
300 memcpy(str
->data
, data
, len
);
301 /* an allowance for strings :-) */
302 str
->data
[len
] = '\0';
307 void ASN1_STRING_set0(ASN1_STRING
*str
, void *data
, int len
)
309 OPENSSL_free(str
->data
);
314 ASN1_STRING
*ASN1_STRING_new(void)
316 return ASN1_STRING_type_new(V_ASN1_OCTET_STRING
);
319 ASN1_STRING
*ASN1_STRING_type_new(int type
)
323 ret
= OPENSSL_zalloc(sizeof(*ret
));
325 ASN1err(ASN1_F_ASN1_STRING_TYPE_NEW
, ERR_R_MALLOC_FAILURE
);
332 void asn1_string_embed_free(ASN1_STRING
*a
, int embed
)
336 if (!(a
->flags
& ASN1_STRING_FLAG_NDEF
))
337 OPENSSL_free(a
->data
);
342 void ASN1_STRING_free(ASN1_STRING
*a
)
346 asn1_string_embed_free(a
, a
->flags
& ASN1_STRING_FLAG_EMBED
);
349 void ASN1_STRING_clear_free(ASN1_STRING
*a
)
353 if (a
->data
&& !(a
->flags
& ASN1_STRING_FLAG_NDEF
))
354 OPENSSL_cleanse(a
->data
, a
->length
);
358 int ASN1_STRING_cmp(const ASN1_STRING
*a
, const ASN1_STRING
*b
)
362 i
= (a
->length
- b
->length
);
364 i
= memcmp(a
->data
, b
->data
, a
->length
);
366 return a
->type
- b
->type
;
374 int ASN1_STRING_length(const ASN1_STRING
*x
)
379 void ASN1_STRING_length_set(ASN1_STRING
*x
, int len
)
384 int ASN1_STRING_type(const ASN1_STRING
*x
)
389 const unsigned char *ASN1_STRING_get0_data(const ASN1_STRING
*x
)
394 #ifndef OPENSSL_NO_DEPRECATED_1_1_0
395 unsigned char *ASN1_STRING_data(ASN1_STRING
*x
)
401 char *sk_ASN1_UTF8STRING2text(STACK_OF(ASN1_UTF8STRING
) *text
, const char *sep
,
402 size_t max_len
/* excluding NUL terminator */)
405 ASN1_UTF8STRING
*current
;
406 size_t length
= 0, sep_len
;
410 if (!ossl_assert(sep
!= NULL
))
412 sep_len
= strlen(sep
);
414 for (i
= 0; i
< sk_ASN1_UTF8STRING_num(text
); ++i
) {
415 current
= sk_ASN1_UTF8STRING_value(text
, i
);
418 length
+= ASN1_STRING_length(current
);
419 if (length
> max_len
)
422 if ((result
= OPENSSL_malloc(length
+ 1)) == NULL
)
425 for (i
= 0, p
= result
; i
< sk_ASN1_UTF8STRING_num(text
); ++i
) {
426 current
= sk_ASN1_UTF8STRING_value(text
, i
);
427 length
= ASN1_STRING_length(current
);
428 if (i
> 0 && sep_len
> 0) {
429 strncpy(p
, sep
, sep_len
+ 1);
432 strncpy(p
, (const char *)ASN1_STRING_get0_data(current
), length
);