From 53958290ab731c8486531a3bdef54a933533579d Mon Sep 17 00:00:00 2001 From: Nikos Mavrogiannopoulos Date: Thu, 22 May 2014 23:33:08 +0200 Subject: Allow a NULL value in asn1_read_value() for all types. --- lib/decoding.c | 6 +++--- lib/element.c | 46 ++++++++++++++++++++++++++++------------------ 2 files changed, 31 insertions(+), 21 deletions(-) (limited to 'lib') diff --git a/lib/decoding.c b/lib/decoding.c index 93bc962..90a37ff 100644 --- a/lib/decoding.c +++ b/lib/decoding.c @@ -254,7 +254,6 @@ asn1_get_octet_der (const unsigned char *der, int der_len, if (der_len <= 0) return ASN1_GENERIC_ERROR; - /* if(str==NULL) return ASN1_SUCCESS; */ *str_len = asn1_get_length_der (der, der_len, &len_len); if (*str_len < 0) @@ -263,7 +262,7 @@ asn1_get_octet_der (const unsigned char *der, int der_len, *ret_len = *str_len + len_len; if (str_size >= *str_len) { - if (*str_len > 0) + if (*str_len > 0 && str != NULL) memcpy (str, der + len_len, *str_len); } else @@ -380,6 +379,7 @@ asn1_get_bit_der (const unsigned char *der, int der_len, if (der_len <= 0) return ASN1_GENERIC_ERROR; + len_byte = asn1_get_length_der (der, der_len, &len_len) - 1; if (len_byte < 0) return ASN1_DER_ERROR; @@ -392,7 +392,7 @@ asn1_get_bit_der (const unsigned char *der, int der_len, if (str_size >= len_byte) { - if (len_byte > 0) + if (len_byte > 0 && str) memcpy (str, der + len_len + 1, len_byte); } else diff --git a/lib/element.c b/lib/element.c index 359b3ab..ac30e46 100644 --- a/lib/element.c +++ b/lib/element.c @@ -112,8 +112,11 @@ _asn1_convert_integer (const unsigned char *value, unsigned char *value_out, /* VALUE_OUT is too short to contain the value conversion */ return ASN1_MEM_ERROR; - for (k2 = k; k2 < SIZEOF_UNSIGNED_LONG_INT; k2++) - value_out[k2 - k] = val[k2]; + if (value_out != NULL) + { + for (k2 = k; k2 < SIZEOF_UNSIGNED_LONG_INT; k2++) + value_out[k2 - k] = val[k2]; + } #if 0 printf ("_asn1_convert_integer: valueIn=%s, lenOut=%d", value, *len); @@ -650,31 +653,34 @@ asn1_write_value (asn1_node node_root, const char *name, } #define ADD_STR_VALUE( ptr, ptr_size, data) \ - *len = (int) _asn1_strlen (data) + 1; \ - if (ptr_size < (int) _asn1_strlen (ptr) + (*len)) { \ - return ASN1_MEM_ERROR; \ - } else { \ - /* this strcat is checked */ \ - if (ptr) _asn1_strcat (ptr, data); \ - } + *len += _asn1_strlen(data); \ + if (ptr_size < (int) *len) { \ + (*len)++; \ + return ASN1_MEM_ERROR; \ + } else { \ + /* this strcat is checked */ \ + if (ptr) _asn1_strcat (ptr, data); \ + } /** * asn1_read_value: * @root: pointer to a structure. * @name: the name of the element inside a structure that you want to read. * @ivalue: vector that will contain the element's content, must be a - * pointer to memory cells already allocated. + * pointer to memory cells already allocated (may be %NULL). * @len: number of bytes of *value: value[0]..value[len-1]. Initialy * holds the sizeof value. * - * Returns the value of one element inside a structure. - * - * If an element is OPTIONAL and the function "read_value" returns + * Returns the value of one element inside a structure. + * If an element is OPTIONAL and this returns * %ASN1_ELEMENT_NOT_FOUND, it means that this element wasn't present * in the der encoding that created the structure. The first element * of a SEQUENCE_OF or SET_OF is named "?1". The second one "?2" and * so on. * + * Note that there can be valid values with length zero. In these case + * this function will succeed and @len will be zero. + * * INTEGER: VALUE will contain a two's complement form integer. * * integer=-1 -> value[0]=0xFF , len=1. @@ -730,19 +736,22 @@ asn1_read_value (asn1_node root, const char *name, void *ivalue, int *len) * @root: pointer to a structure. * @name: the name of the element inside a structure that you want to read. * @ivalue: vector that will contain the element's content, must be a - * pointer to memory cells already allocated. + * pointer to memory cells already allocated (may be %NULL). * @len: number of bytes of *value: value[0]..value[len-1]. Initialy * holds the sizeof value. * @etype: The type of the value read (ASN1_ETYPE) * - * Returns the value of one element inside a structure. - * - * If an element is OPTIONAL and the function "read_value" returns + * Returns the value of one element inside a structure. + * If an element is OPTIONAL and this returns * %ASN1_ELEMENT_NOT_FOUND, it means that this element wasn't present * in the der encoding that created the structure. The first element * of a SEQUENCE_OF or SET_OF is named "?1". The second one "?2" and * so on. * + * Note that there can be valid values with length zero. In these case + * this function will succeed and @len will be zero. + * + * * INTEGER: VALUE will contain a two's complement form integer. * * integer=-1 -> value[0]=0xFF , len=1. @@ -889,6 +898,7 @@ asn1_read_value_type (asn1_node root, const char *name, void *ivalue, case ASN1_ETYPE_OBJECT_ID: if (node->type & CONST_ASSIGN) { + *len = 0; if (value) value[0] = 0; p = node->down; @@ -904,7 +914,7 @@ asn1_read_value_type (asn1_node root, const char *name, void *ivalue, } p = p->right; } - *len = _asn1_strlen (value) + 1; + (*len)++; } else if ((node->type & CONST_DEFAULT) && (node->value == NULL)) { -- cgit v1.2.3