/*
 * Copyright (C) 2002-2025 Free Software Foundation, Inc.
 *
 * This file is part of LIBTASN1.
 *
 * The LIBTASN1 library is free software; you can redistribute it
 * and/or modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, see
 * <https://www.gnu.org/licenses/>.
 */


/*****************************************************/
/* File: coding.c                                    */
/* Description: Functions to create a DER coding of  */
/*   an ASN1 type.                                   */
/*****************************************************/

#include <int.h>
#include "parser_aux.h"
#include <gstr.h>
#include "element.h"
#include "minmax.h"
#include <structure.h>

#define MAX_TAG_LEN 16

/******************************************************/
/* Function : _asn1_error_description_value_not_found */
/* Description: creates the ErrorDescription string   */
/* for the ASN1_VALUE_NOT_FOUND error.                */
/* Parameters:                                        */
/*   node: node of the tree where the value is NULL.  */
/*   ErrorDescription: string returned.               */
/* Return:                                            */
/******************************************************/
static void
_asn1_error_description_value_not_found (asn1_node node,
					 char *ErrorDescription)
{

  if (ErrorDescription == NULL)
    return;

  Estrcpy (ErrorDescription, ":: value of element '");
  _asn1_hierarchical_name (node, ErrorDescription + strlen (ErrorDescription),
			   ASN1_MAX_ERROR_DESCRIPTION_SIZE - 40);
  Estrcat (ErrorDescription, "' not found");

}

/**
 * asn1_length_der:
 * @len: value to convert.
 * @der: buffer to hold the returned encoding (may be %NULL).
 * @der_len: number of meaningful bytes of ANS (der[0]..der[der_len-1]).
 *
 * Creates the DER encoding of the provided length value.
 * The @der buffer must have enough room for the output. The maximum
 * length this function will encode is %ASN1_MAX_LENGTH_SIZE.
 *
 * To know the size of the DER encoding use a %NULL value for @der.
 **/
void
asn1_length_der (unsigned long int len, unsigned char *der, int *der_len)
{
  int k;
  unsigned char temp[ASN1_MAX_LENGTH_SIZE];
#if SIZEOF_UNSIGNED_LONG_INT > 8
  len &= 0xFFFFFFFFFFFFFFFF;
#endif

  if (len < 128)
    {
      /* short form */
      if (der != NULL)
	der[0] = (unsigned char) len;
      *der_len = 1;
    }
  else
    {
      /* Long form */
      k = 0;
      while (len)
	{
	  temp[k++] = len & 0xFF;
	  len = len >> 8;
	}
      *der_len = k + 1;
      if (der != NULL)
	{
	  der[0] = ((unsigned char) k & 0x7F) + 128;
	  while (k--)
	    der[*der_len - 1 - k] = temp[k];
	}
    }
}

/******************************************************/
/* Function : _asn1_tag_der                           */
/* Description: creates the DER coding for the CLASS  */
/* and TAG parameters.                                */
/* It is limited by the ASN1_MAX_TAG_SIZE variable    */
/* Parameters:                                        */
/*   class: value to convert.                         */
/*   tag_value: value to convert.                     */
/*   ans: string returned.                            */
/*   ans_len: number of meaningful bytes of ANS       */
/*            (ans[0]..ans[ans_len-1]).               */
/* Return:                                            */
/******************************************************/
static void
_asn1_tag_der (unsigned char class, unsigned int tag_value,
	       unsigned char ans[ASN1_MAX_TAG_SIZE], int *ans_len)
{
  int k;
  unsigned char temp[ASN1_MAX_TAG_SIZE];

  if (tag_value < 31)
    {
      /* short form */
      ans[0] = (class & 0xE0) + ((unsigned char) (tag_value & 0x1F));
      *ans_len = 1;
    }
  else
    {
      /* Long form */
      ans[0] = (class & 0xE0) + 31;
      k = 0;
      while (tag_value != 0)
	{
	  temp[k++] = tag_value & 0x7F;
	  tag_value >>= 7;

	  if (k > ASN1_MAX_TAG_SIZE - 1)
	    break;		/* will not encode larger tags */
	}
      *ans_len = k + 1;
      while (k--)
	ans[*ans_len - 1 - k] = temp[k] + 128;
      ans[*ans_len - 1] -= 128;
    }
}

/**
 * asn1_octet_der:
 * @str: the input data.
 * @str_len: STR length (str[0]..str[*str_len-1]).
 * @der: encoded string returned.
 * @der_len: number of meaningful bytes of DER (der[0]..der[der_len-1]).
 *
 * Creates a length-value DER encoding for the input data.
 * The DER encoding of the input data will be placed in the @der variable.
 *
 * Note that the OCTET STRING tag is not included in the output.
 *
 * This function does not return any value because it is expected
 * that @der_len will contain enough bytes to store the string
 * plus the DER encoding. The DER encoding size can be obtained using
 * asn1_length_der().
 **/
void
asn1_octet_der (const unsigned char *str, int str_len,
		unsigned char *der, int *der_len)
{
  int len_len;

  if (der == NULL || str_len < 0)
    return;

  asn1_length_der (str_len, der, &len_len);
  memcpy (der + len_len, str, str_len);
  *der_len = str_len + len_len;
}


/**
 * asn1_encode_simple_der:
 * @etype: The type of the string to be encoded (ASN1_ETYPE_)
 * @str: the string data.
 * @str_len: the string length
 * @tl: the encoded tag and length
 * @tl_len: the bytes of the @tl field
 *
 * Creates the DER encoding for various simple ASN.1 types like strings etc.
 * It stores the tag and length in @tl, which should have space for at least
 * %ASN1_MAX_TL_SIZE bytes. Initially @tl_len should contain the size of @tl.
 *
 * The complete DER encoding should consist of the value in @tl appended
 * with the provided @str.
 *
 * Returns: %ASN1_SUCCESS if successful or an error value.
 **/
int
asn1_encode_simple_der (unsigned int etype, const unsigned char *str,
			unsigned int str_len, unsigned char *tl,
			unsigned int *tl_len)
{
  int tag_len, len_len;
  unsigned tlen;
  unsigned char der_tag[ASN1_MAX_TAG_SIZE];
  unsigned char der_length[ASN1_MAX_LENGTH_SIZE];
  unsigned char *p;

  if (str == NULL)
    return ASN1_VALUE_NOT_VALID;

  if (ETYPE_OK (etype) == 0)
    return ASN1_VALUE_NOT_VALID;

  /* doesn't handle constructed classes */
  if (ETYPE_CLASS (etype) != ASN1_CLASS_UNIVERSAL)
    return ASN1_VALUE_NOT_VALID;

  _asn1_tag_der (ETYPE_CLASS (etype), ETYPE_TAG (etype), der_tag, &tag_len);

  asn1_length_der (str_len, der_length, &len_len);

  if (tag_len <= 0 || len_len <= 0)
    return ASN1_VALUE_NOT_VALID;

  tlen = tag_len + len_len;

  if (*tl_len < tlen)
    return ASN1_MEM_ERROR;

  p = tl;
  memcpy (p, der_tag, tag_len);
  p += tag_len;
  memcpy (p, der_length, len_len);

  *tl_len = tlen;

  return ASN1_SUCCESS;
}

/******************************************************/
/* Function : _asn1_time_der                          */
/* Description: creates the DER coding for a TIME     */
/* type (length included).                            */
/* Parameters:                                        */
/*   str: TIME null-terminated string.                */
/*   der: string returned.                            */
/*   der_len: number of meaningful bytes of DER       */
/*            (der[0]..der[ans_len-1]). Initially it  */
/*            if must store the length of DER.        */
/* Return:                                            */
/*   ASN1_MEM_ERROR when DER isn't big enough         */
/*   ASN1_SUCCESS otherwise                           */
/******************************************************/
static int
_asn1_time_der (unsigned char *str, int str_len, unsigned char *der,
		int *der_len)
{
  int len_len;
  int max_len;

  max_len = *der_len;

  asn1_length_der (str_len, (max_len > 0) ? der : NULL, &len_len);

  if ((len_len + str_len) <= max_len)
    memcpy (der + len_len, str, str_len);
  *der_len = len_len + str_len;

  if ((*der_len) > max_len)
    return ASN1_MEM_ERROR;

  return ASN1_SUCCESS;
}


/*
void
_asn1_get_utctime_der(unsigned char *der,int *der_len,unsigned char *str)
{
  int len_len,str_len;
  char temp[20];

  if(str==NULL) return;
  str_len=asn1_get_length_der(der,*der_len,&len_len);
  if (str_len<0) return;
  memcpy(temp,der+len_len,str_len);
  *der_len=str_len+len_len;
  switch(str_len)
  {
  case 11:
    temp[10]=0;
    strcat(temp,"00+0000");
    break;
  case 13:
    temp[12]=0;
    strcat(temp,"+0000");
    break;
  case 15:
    temp[15]=0;
    memmove(temp+12,temp+10,6);
    temp[10]=temp[11]='0';
    break;
  case 17:
    temp[17]=0;
    break;
  default:
    return;
  }
  strcpy(str,temp);
}
*/

static void
encode_val (uint64_t val, unsigned char *der, int max_len, int *der_len)
{
  int first, k;
  unsigned char bit7;

  first = 0;
  for (k = sizeof (val); k >= 0; k--)
    {
      bit7 = (val >> (k * 7)) & 0x7F;
      if (bit7 || first || !k)
	{
	  if (k)
	    bit7 |= 0x80;
	  if (max_len > (*der_len))
	    der[*der_len] = bit7;
	  (*der_len)++;
	  first = 1;
	}
    }
}

/******************************************************/
/* Function : _asn1_object_id_der                     */
/* Description: creates the DER coding for an         */
/* OBJECT IDENTIFIER  type (length included).         */
/* Parameters:                                        */
/*   str: OBJECT IDENTIFIER null-terminated string.   */
/*   der: string returned.                            */
/*   der_len: number of meaningful bytes of DER       */
/*            (der[0]..der[ans_len-1]). Initially it  */
/*            must store the length of DER.           */
/* Return:                                            */
/*   ASN1_MEM_ERROR when DER isn't big enough         */
/*   ASN1_SUCCESS if successful                       */
/*   or an error value.                               */
/******************************************************/
static int
_asn1_object_id_der (const char *str, unsigned char *der, int *der_len)
{
  int len_len, counter, max_len;
  char *temp, *n_end, *n_start;
  uint64_t val, val1 = 0;
  int str_len = _asn1_strlen (str);

  max_len = *der_len;
  *der_len = 0;

  if (der == NULL && max_len > 0)
    return ASN1_VALUE_NOT_VALID;

  temp = malloc (str_len + 2);
  if (temp == NULL)
    return ASN1_MEM_ALLOC_ERROR;

  memcpy (temp, str, str_len);
  temp[str_len] = '.';
  temp[str_len + 1] = 0;

  counter = 0;
  n_start = temp;
  while ((n_end = strchr (n_start, '.')))
    {
      *n_end = 0;
      val = _asn1_strtou64 (n_start, NULL, 10);
      counter++;

      if (counter == 1)
	{
	  val1 = val;
	}
      else if (counter == 2)
	{
	  uint64_t val0;

	  if (val1 > 2)
	    {
	      free (temp);
	      return ASN1_VALUE_NOT_VALID;
	    }
	  else if ((val1 == 0 || val1 == 1) && val > 39)
	    {
	      free (temp);
	      return ASN1_VALUE_NOT_VALID;
	    }

	  val0 = 40 * val1 + val;
	  encode_val (val0, der, max_len, der_len);
	}
      else
	{
	  encode_val (val, der, max_len, der_len);
	}
      n_start = n_end + 1;
    }

  asn1_length_der (*der_len, NULL, &len_len);
  if (max_len >= (*der_len + len_len))
    {
      memmove (der + len_len, der, *der_len);
      asn1_length_der (*der_len, der, &len_len);
    }
  *der_len += len_len;

  free (temp);

  if (max_len < (*der_len))
    return ASN1_MEM_ERROR;

  return ASN1_SUCCESS;
}

/**
 * asn1_object_id_der:
 * @str: An object identifier in numeric, dot format.
 * @der: buffer to hold the returned encoding (may be %NULL).
 * @der_len: initially the size of @der; will hold the final size.
 * @flags: must be zero
 *
 * Creates the DER encoding of the provided object identifier.
 *
 * Returns: %ASN1_SUCCESS if DER encoding was OK, %ASN1_VALUE_NOT_VALID
 *   if @str is not a valid OID, %ASN1_MEM_ERROR if the @der
 *   vector isn't big enough and in this case @der_len will contain the
 *   length needed.
 **/
int
asn1_object_id_der (const char *str, unsigned char *der, int *der_len,
		    unsigned flags)
{
  unsigned char tag_der[MAX_TAG_LEN];
  int tag_len = 0, r;
  int max_len = *der_len;

  *der_len = 0;

  _asn1_tag_der (ETYPE_CLASS (ASN1_ETYPE_OBJECT_ID),
		 ETYPE_TAG (ASN1_ETYPE_OBJECT_ID), tag_der, &tag_len);

  if (max_len > tag_len)
    {
      memcpy (der, tag_der, tag_len);
    }
  max_len -= tag_len;
  der += tag_len;

  r = _asn1_object_id_der (str, der, &max_len);
  if (r == ASN1_MEM_ERROR || r == ASN1_SUCCESS)
    {
      *der_len = max_len + tag_len;
    }

  return r;
}

static const unsigned char bit_mask[] =
  { 0xFF, 0xFE, 0xFC, 0xF8, 0xF0, 0xE0, 0xC0, 0x80 };

/**
 * asn1_bit_der:
 * @str: BIT string.
 * @bit_len: number of meaningful bits in STR.
 * @der: string returned.
 * @der_len: number of meaningful bytes of DER
 *   (der[0]..der[ans_len-1]).
 *
 * Creates a length-value DER encoding for the input data
 * as it would have been for a BIT STRING.
 * The DER encoded data will be copied in @der.
 *
 * Note that the BIT STRING tag is not included in the output.
 *
 * This function does not return any value because it is expected
 * that @der_len will contain enough bytes to store the string
 * plus the DER encoding. The DER encoding size can be obtained using
 * asn1_length_der().
 **/
void
asn1_bit_der (const unsigned char *str, int bit_len,
	      unsigned char *der, int *der_len)
{
  int len_len, len_byte, len_pad;

  if (der == NULL)
    return;

  len_byte = bit_len >> 3;
  len_pad = 8 - (bit_len & 7);
  if (len_pad == 8)
    len_pad = 0;
  else
    len_byte++;
  asn1_length_der (len_byte + 1, der, &len_len);
  der[len_len] = len_pad;

  if (str)
    memcpy (der + len_len + 1, str, len_byte);
  der[len_len + len_byte] &= bit_mask[len_pad];
  *der_len = len_byte + len_len + 1;
}


/******************************************************/
/* Function : _asn1_complete_explicit_tag             */
/* Description: add the length coding to the EXPLICIT */
/* tags.                                              */
/* Parameters:                                        */
/*   node: pointer to the tree element.               */
/*   der: string with the DER coding of the whole tree*/
/*   counter: number of meaningful bytes of DER       */
/*            (der[0]..der[*counter-1]).              */
/*   max_len: size of der vector                      */
/* Return:                                            */
/*   ASN1_MEM_ERROR if der vector isn't big enough,   */
/*   otherwise ASN1_SUCCESS.                          */
/******************************************************/
static int
_asn1_complete_explicit_tag (asn1_node node, unsigned char *der,
			     int *counter, int *max_len)
{
  asn1_node p;
  int is_tag_implicit, len2, len3;
  unsigned char temp[SIZEOF_UNSIGNED_INT];

  if (der == NULL && *max_len > 0)
    return ASN1_VALUE_NOT_VALID;

  is_tag_implicit = 0;

  if (node->type & CONST_TAG)
    {
      p = node->down;
      if (p == NULL)
	return ASN1_DER_ERROR;
      /* When there are nested tags we must complete them reverse to
         the order they were created. This is because completing a tag
         modifies all data within it, including the incomplete tags
         which store buffer positions -- simon@josefsson.org 2002-09-06
       */
      while (p->right)
	p = p->right;
      while (p && p != node->down->left)
	{
	  if (type_field (p->type) == ASN1_ETYPE_TAG)
	    {
	      if (p->type & CONST_EXPLICIT)
		{
		  len2 = strtol (p->name, NULL, 10);
		  _asn1_set_name (p, NULL);

		  asn1_length_der (*counter - len2, temp, &len3);
		  if (len3 <= (*max_len))
		    {
		      memmove (der + len2 + len3, der + len2,
			       *counter - len2);
		      memcpy (der + len2, temp, len3);
		    }
		  *max_len -= len3;
		  *counter += len3;
		  is_tag_implicit = 0;
		}
	      else
		{		/* CONST_IMPLICIT */
		  if (!is_tag_implicit)
		    {
		      is_tag_implicit = 1;
		    }
		}
	    }
	  p = p->left;
	}
    }

  if (*max_len < 0)
    return ASN1_MEM_ERROR;

  return ASN1_SUCCESS;
}

const tag_and_class_st _asn1_tags[] = {
  [ASN1_ETYPE_GENERALSTRING] =
    {ASN1_TAG_GENERALSTRING, ASN1_CLASS_UNIVERSAL, "type:GENERALSTRING"},
  [ASN1_ETYPE_NUMERIC_STRING] =
    {ASN1_TAG_NUMERIC_STRING, ASN1_CLASS_UNIVERSAL, "type:NUMERIC_STR"},
  [ASN1_ETYPE_IA5_STRING] =
    {ASN1_TAG_IA5_STRING, ASN1_CLASS_UNIVERSAL, "type:IA5_STR"},
  [ASN1_ETYPE_TELETEX_STRING] =
    {ASN1_TAG_TELETEX_STRING, ASN1_CLASS_UNIVERSAL, "type:TELETEX_STR"},
  [ASN1_ETYPE_PRINTABLE_STRING] =
    {ASN1_TAG_PRINTABLE_STRING, ASN1_CLASS_UNIVERSAL, "type:PRINTABLE_STR"},
  [ASN1_ETYPE_UNIVERSAL_STRING] =
    {ASN1_TAG_UNIVERSAL_STRING, ASN1_CLASS_UNIVERSAL, "type:UNIVERSAL_STR"},
  [ASN1_ETYPE_BMP_STRING] =
    {ASN1_TAG_BMP_STRING, ASN1_CLASS_UNIVERSAL, "type:BMP_STR"},
  [ASN1_ETYPE_UTF8_STRING] =
    {ASN1_TAG_UTF8_STRING, ASN1_CLASS_UNIVERSAL, "type:UTF8_STR"},
  [ASN1_ETYPE_VISIBLE_STRING] =
    {ASN1_TAG_VISIBLE_STRING, ASN1_CLASS_UNIVERSAL, "type:VISIBLE_STR"},
  [ASN1_ETYPE_OCTET_STRING] =
    {ASN1_TAG_OCTET_STRING, ASN1_CLASS_UNIVERSAL, "type:OCT_STR"},
  [ASN1_ETYPE_BIT_STRING] =
    {ASN1_TAG_BIT_STRING, ASN1_CLASS_UNIVERSAL, "type:BIT_STR"},
  [ASN1_ETYPE_OBJECT_ID] =
    {ASN1_TAG_OBJECT_ID, ASN1_CLASS_UNIVERSAL, "type:OBJ_ID"},
  [ASN1_ETYPE_NULL] = {ASN1_TAG_NULL, ASN1_CLASS_UNIVERSAL, "type:NULL"},
  [ASN1_ETYPE_BOOLEAN] =
    {ASN1_TAG_BOOLEAN, ASN1_CLASS_UNIVERSAL, "type:BOOLEAN"},
  [ASN1_ETYPE_INTEGER] =
    {ASN1_TAG_INTEGER, ASN1_CLASS_UNIVERSAL, "type:INTEGER"},
  [ASN1_ETYPE_ENUMERATED] =
    {ASN1_TAG_ENUMERATED, ASN1_CLASS_UNIVERSAL, "type:ENUMERATED"},
  [ASN1_ETYPE_SEQUENCE] =
    {ASN1_TAG_SEQUENCE, ASN1_CLASS_UNIVERSAL | ASN1_CLASS_STRUCTURED,
     "type:SEQUENCE"},
  [ASN1_ETYPE_SEQUENCE_OF] =
    {ASN1_TAG_SEQUENCE, ASN1_CLASS_UNIVERSAL | ASN1_CLASS_STRUCTURED,
     "type:SEQ_OF"},
  [ASN1_ETYPE_SET] =
    {ASN1_TAG_SET, ASN1_CLASS_UNIVERSAL | ASN1_CLASS_STRUCTURED, "type:SET"},
  [ASN1_ETYPE_SET_OF] =
    {ASN1_TAG_SET, ASN1_CLASS_UNIVERSAL | ASN1_CLASS_STRUCTURED,
     "type:SET_OF"},
  [ASN1_ETYPE_GENERALIZED_TIME] =
    {ASN1_TAG_GENERALIZEDTime, ASN1_CLASS_UNIVERSAL, "type:GENERALIZED_TIME"},
  [ASN1_ETYPE_UTC_TIME] =
    {ASN1_TAG_UTCTime, ASN1_CLASS_UNIVERSAL, "type:UTC_TIME"},
};

unsigned int _asn1_tags_size = sizeof (_asn1_tags) / sizeof (_asn1_tags[0]);

/******************************************************/
/* Function : _asn1_insert_tag_der                    */
/* Description: creates the DER coding of tags of one */
/* NODE.                                              */
/* Parameters:                                        */
/*   node: pointer to the tree element.               */
/*   der: string returned                             */
/*   counter: number of meaningful bytes of DER       */
/*            (counter[0]..der[*counter-1]).          */
/*   max_len: size of der vector                      */
/* Return:                                            */
/*   ASN1_GENERIC_ERROR if the type is unknown,       */
/*   ASN1_MEM_ERROR if der vector isn't big enough,   */
/*   otherwise ASN1_SUCCESS.                          */
/******************************************************/
static int
_asn1_insert_tag_der (asn1_node node, unsigned char *der, int *counter,
		      int *max_len)
{
  asn1_node p;
  int tag_len, is_tag_implicit;
  unsigned char class, class_implicit =
    0, temp[MAX (SIZEOF_UNSIGNED_INT * 3 + 1, LTOSTR_MAX_SIZE)];
  unsigned long tag_implicit = 0;
  unsigned char tag_der[MAX_TAG_LEN];

  is_tag_implicit = 0;

  if (node->type & CONST_TAG)
    {
      p = node->down;
      while (p)
	{
	  if (type_field (p->type) == ASN1_ETYPE_TAG)
	    {
	      if (p->type & CONST_APPLICATION)
		class = ASN1_CLASS_APPLICATION;
	      else if (p->type & CONST_UNIVERSAL)
		class = ASN1_CLASS_UNIVERSAL;
	      else if (p->type & CONST_PRIVATE)
		class = ASN1_CLASS_PRIVATE;
	      else
		class = ASN1_CLASS_CONTEXT_SPECIFIC;

	      if (p->type & CONST_EXPLICIT)
		{
		  if (is_tag_implicit)
		    _asn1_tag_der (class_implicit, tag_implicit, tag_der,
				   &tag_len);
		  else
		    _asn1_tag_der (class | ASN1_CLASS_STRUCTURED,
				   _asn1_strtoul (p->value, NULL, 10),
				   tag_der, &tag_len);

		  *max_len -= tag_len;
		  if (der && *max_len >= 0)
		    memcpy (der + *counter, tag_der, tag_len);
		  *counter += tag_len;

		  _asn1_ltostr (*counter, (char *) temp);
		  _asn1_set_name (p, (const char *) temp);

		  is_tag_implicit = 0;
		}
	      else
		{		/* CONST_IMPLICIT */
		  if (!is_tag_implicit)
		    {
		      if ((type_field (node->type) == ASN1_ETYPE_SEQUENCE) ||
			  (type_field (node->type) == ASN1_ETYPE_SEQUENCE_OF)
			  || (type_field (node->type) == ASN1_ETYPE_SET)
			  || (type_field (node->type) == ASN1_ETYPE_SET_OF))
			class |= ASN1_CLASS_STRUCTURED;
		      class_implicit = class;
		      tag_implicit = _asn1_strtoul (p->value, NULL, 10);
		      is_tag_implicit = 1;
		    }
		}
	    }
	  p = p->right;
	}
    }

  if (is_tag_implicit)
    {
      _asn1_tag_der (class_implicit, tag_implicit, tag_der, &tag_len);
    }
  else
    {
      unsigned type = type_field (node->type);
      switch (type)
	{
	CASE_HANDLED_ETYPES:
	  _asn1_tag_der (_asn1_tags[type].class, _asn1_tags[type].tag,
			 tag_der, &tag_len);
	  break;
	case ASN1_ETYPE_TAG:
	case ASN1_ETYPE_CHOICE:
	case ASN1_ETYPE_ANY:
	  tag_len = 0;
	  break;
	default:
	  return ASN1_GENERIC_ERROR;
	}
    }

  *max_len -= tag_len;
  if (der && *max_len >= 0)
    memcpy (der + *counter, tag_der, tag_len);
  *counter += tag_len;

  if (*max_len < 0)
    return ASN1_MEM_ERROR;

  return ASN1_SUCCESS;
}

/******************************************************/
/* Function : _asn1_ordering_set                      */
/* Description: puts the elements of a SET type in    */
/* the correct order according to DER rules.          */
/* Parameters:                                        */
/*   der: string with the DER coding.                 */
/*   node: pointer to the SET element.                */
/* Return:                                            */
/*    ASN1_SUCCESS if successful                      */
/*    or an error value.                              */
/******************************************************/
static int
_asn1_ordering_set (unsigned char *der, int der_len, asn1_node node)
{
  struct vet
  {
    int end;
    unsigned long value;
    struct vet *next, *prev;
  };

  int counter, len, len2;
  struct vet *first, *last, *p_vet, *p2_vet;
  asn1_node p;
  unsigned char class, *temp;
  unsigned long tag, t;
  int err;

  counter = 0;

  if (type_field (node->type) != ASN1_ETYPE_SET)
    return ASN1_VALUE_NOT_VALID;

  p = node->down;
  while (p && ((type_field (p->type) == ASN1_ETYPE_TAG) ||
	       (type_field (p->type) == ASN1_ETYPE_SIZE)))
    p = p->right;

  if ((p == NULL) || (p->right == NULL))
    return ASN1_SUCCESS;

  first = last = NULL;
  while (p)
    {
      p_vet = malloc (sizeof (struct vet));
      if (p_vet == NULL)
	{
	  err = ASN1_MEM_ALLOC_ERROR;
	  goto error;
	}

      p_vet->next = NULL;
      p_vet->prev = last;
      if (first == NULL)
	first = p_vet;
      else
	last->next = p_vet;
      last = p_vet;

      /* tag value calculation */
      err = asn1_get_tag_der (der + counter, der_len - counter, &class, &len2,
			      &tag);
      if (err != ASN1_SUCCESS)
	goto error;

      t = ((unsigned int) class) << 24;
      p_vet->value = t | tag;
      counter += len2;

      /* extraction and length */
      len2 = asn1_get_length_der (der + counter, der_len - counter, &len);
      if (len2 < 0)
	{
	  err = ASN1_DER_ERROR;
	  goto error;
	}
      counter += len + len2;

      p_vet->end = counter;
      p = p->right;
    }

  p_vet = first;

  while (p_vet)
    {
      p2_vet = p_vet->next;
      counter = 0;
      while (p2_vet)
	{
	  if (p_vet->value > p2_vet->value)
	    {
	      /* change position */
	      temp = malloc (p_vet->end - counter);
	      if (temp == NULL)
		{
		  err = ASN1_MEM_ALLOC_ERROR;
		  goto error;
		}

	      memcpy (temp, der + counter, p_vet->end - counter);
	      memcpy (der + counter, der + p_vet->end,
		      p2_vet->end - p_vet->end);
	      memcpy (der + counter + p2_vet->end - p_vet->end, temp,
		      p_vet->end - counter);
	      free (temp);

	      tag = p_vet->value;
	      p_vet->value = p2_vet->value;
	      p2_vet->value = tag;

	      p_vet->end = counter + (p2_vet->end - p_vet->end);
	    }
	  counter = p_vet->end;

	  p2_vet = p2_vet->next;
	  p_vet = p_vet->next;
	}

      if (p_vet != first)
	p_vet->prev->next = NULL;
      else
	first = NULL;
      free (p_vet);
      p_vet = first;
    }
  return ASN1_SUCCESS;

error:
  while (first != NULL)
    {
      p_vet = first;
      first = first->next;
      free (p_vet);
    }
  return err;
}

struct vet
{
  unsigned char *ptr;
  int size;
};

static int
setof_compar (const void *_e1, const void *_e2)
{
  unsigned length;
  const struct vet *e1 = _e1, *e2 = _e2;
  int rval;

  /* The encodings of the component values of a set-of value shall
   * appear in ascending order, the encodings being compared
   * as octet strings with the shorter components being
   * padded at their trailing end with 0-octets.
   * The padding octets are for comparison purposes and
   * do not appear in the encodings.
   */
  length = MIN (e1->size, e2->size);

  rval = memcmp (e1->ptr, e2->ptr, length);
  if (rval == 0 && e1->size != e2->size)
    {
      if (e1->size > e2->size)
	rval = 1;
      else if (e2->size > e1->size)
	rval = -1;
    }

  return rval;
}

/******************************************************/
/* Function : _asn1_ordering_set_of                   */
/* Description: puts the elements of a SET OF type in */
/* the correct order according to DER rules.          */
/* Parameters:                                        */
/*   der: string with the DER coding.                 */
/*   node: pointer to the SET OF element.             */
/* Return:                                            */
/*    ASN1_SUCCESS if successful                      */
/*    or an error value.                              */
/******************************************************/
static int
_asn1_ordering_set_of (unsigned char *der, int der_len, asn1_node node)
{
  int counter, len, len2;
  struct vet *list = NULL, *tlist;
  unsigned list_size = 0;
  struct vet *p_vet;
  asn1_node p;
  unsigned char class;
  unsigned i;
  unsigned char *out = NULL;
  int err;

  counter = 0;

  if (type_field (node->type) != ASN1_ETYPE_SET_OF)
    return ASN1_VALUE_NOT_VALID;

  p = node->down;
  while (p && ((type_field (p->type) == ASN1_ETYPE_TAG) ||
	       (type_field (p->type) == ASN1_ETYPE_SIZE)))
    p = p->right;
  if (p == NULL)
    return ASN1_VALUE_NOT_VALID;
  p = p->right;

  if ((p == NULL) || (p->right == NULL))
    return ASN1_SUCCESS;

  while (p)
    {
      list_size++;
      tlist = realloc (list, list_size * sizeof (struct vet));
      if (tlist == NULL)
	{
	  err = ASN1_MEM_ALLOC_ERROR;
	  goto error;
	}
      list = tlist;
      p_vet = &list[list_size - 1];

      p_vet->ptr = der + counter;
      p_vet->size = 0;

      /* extraction of tag and length */
      if (der_len - counter > 0)
	{
	  err = asn1_get_tag_der (der + counter, der_len - counter, &class,
				  &len, NULL);
	  if (err != ASN1_SUCCESS)
	    goto error;
	  counter += len;
	  p_vet->size += len;

	  len2 = asn1_get_length_der (der + counter, der_len - counter, &len);
	  if (len2 < 0)
	    {
	      err = ASN1_DER_ERROR;
	      goto error;
	    }
	  counter += len + len2;
	  p_vet->size += len + len2;

	}
      else
	{
	  err = ASN1_DER_ERROR;
	  goto error;
	}
      p = p->right;
    }

  if (counter > der_len)
    {
      err = ASN1_DER_ERROR;
      goto error;
    }

  qsort (list, list_size, sizeof (struct vet), setof_compar);

  out = malloc (der_len);
  if (out == NULL)
    {
      err = ASN1_MEM_ERROR;
      goto error;
    }

  /* the sum of p_vet->size == der_len */
  counter = 0;
  for (i = 0; i < list_size; i++)
    {
      p_vet = &list[i];
      memcpy (out + counter, p_vet->ptr, p_vet->size);
      counter += p_vet->size;
    }
  memcpy (der, out, der_len);
  free (out);

  err = ASN1_SUCCESS;

error:
  free (list);
  return err;
}

/**
 * asn1_der_coding:
 * @element: pointer to an ASN1 element
 * @name: the name of the structure you want to encode (it must be
 *   inside *POINTER).
 * @ider: vector that will contain the DER encoding. DER must be a
 *   pointer to memory cells already allocated.
 * @len: number of bytes of *@ider: @ider[0]..@ider[len-1], Initially
 *   holds the sizeof of der vector.
 * @ErrorDescription: return the error description or an empty
 *   string if success.
 *
 * Creates the DER encoding for the NAME structure (inside *POINTER
 * structure).
 *
 * Returns: %ASN1_SUCCESS if DER encoding OK, %ASN1_ELEMENT_NOT_FOUND
 *   if @name is not a valid element, %ASN1_VALUE_NOT_FOUND if there
 *   is an element without a value, %ASN1_MEM_ERROR if the @ider
 *   vector isn't big enough and in this case @len will contain the
 *   length needed.
 **/
int
asn1_der_coding (asn1_node_const element, const char *name, void *ider,
		 int *len, char *ErrorDescription)
{
  asn1_node node, p, p2;
  unsigned char temp[MAX (LTOSTR_MAX_SIZE, SIZEOF_UNSIGNED_LONG_INT * 3 + 1)];
  int counter, counter_old, len2, len3, move, max_len, max_len_old;
  int err;
  unsigned char *der = ider;
  unsigned char dummy;

  if (ErrorDescription)
    ErrorDescription[0] = 0;

  node = asn1_find_node (element, name);
  if (node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  /* Node is now a locally allocated variable.
   * That is because in some point we modify the
   * structure, and I don't know why! --nmav
   */
  node = _asn1_copy_structure3 (node);
  if (node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  max_len = *len;

  if (der == NULL && max_len > 0)
    {
      err = ASN1_VALUE_NOT_VALID;
      goto error;
    }

  counter = 0;
  move = DOWN;
  p = node;

  while (1)
    {

      counter_old = counter;
      max_len_old = max_len;
      if (move != UP)
	{
	  p->start = counter;
	  err = _asn1_insert_tag_der (p, der, &counter, &max_len);
	  if (err != ASN1_SUCCESS && err != ASN1_MEM_ERROR)
	    goto error;
	}
      switch (type_field (p->type))
	{
	case ASN1_ETYPE_NULL:
	  max_len--;
	  if (der != NULL && max_len >= 0)
	    der[counter] = 0;
	  counter++;
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_BOOLEAN:
	  if ((p->type & CONST_DEFAULT) && (p->value == NULL))
	    {
	      counter = counter_old;
	      max_len = max_len_old;
	    }
	  else
	    {
	      if (p->value == NULL)
		{
		  _asn1_error_description_value_not_found (p,
							   ErrorDescription);
		  err = ASN1_VALUE_NOT_FOUND;
		  goto error;
		}
	      max_len -= 2;
	      if (der != NULL && max_len >= 0)
		{
		  der[counter++] = 1;
		  if (p->value[0] == 'F')
		    der[counter++] = 0;
		  else
		    der[counter++] = 0xFF;
		}
	      else
		counter += 2;
	    }
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_INTEGER:
	case ASN1_ETYPE_ENUMERATED:
	  if ((p->type & CONST_DEFAULT) && (p->value == NULL))
	    {
	      counter = counter_old;
	      max_len = max_len_old;
	    }
	  else
	    {
	      if (p->value == NULL)
		{
		  _asn1_error_description_value_not_found (p,
							   ErrorDescription);
		  err = ASN1_VALUE_NOT_FOUND;
		  goto error;
		}
	      len2 = asn1_get_length_der (p->value, p->value_len, &len3);
	      if (len2 < 0)
		{
		  err = ASN1_DER_ERROR;
		  goto error;
		}
	      max_len -= len2 + len3;
	      if (der != NULL && max_len >= 0)
		memcpy (der + counter, p->value, len3 + len2);
	      counter += len3 + len2;
	    }
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_OBJECT_ID:
	  if ((p->type & CONST_DEFAULT) && (p->value == NULL))
	    {
	      counter = counter_old;
	      max_len = max_len_old;
	    }
	  else
	    {
	      if (p->value == NULL)
		{
		  _asn1_error_description_value_not_found (p,
							   ErrorDescription);
		  err = ASN1_VALUE_NOT_FOUND;
		  goto error;
		}
	      len2 = max_len;
	      err =
		_asn1_object_id_der ((char *) p->value,
				     der ? der + counter : &dummy, &len2);
	      if (err != ASN1_SUCCESS && err != ASN1_MEM_ERROR)
		goto error;

	      max_len -= len2;
	      counter += len2;
	    }
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_GENERALIZED_TIME:
	case ASN1_ETYPE_UTC_TIME:
	  if (p->value == NULL)
	    {
	      _asn1_error_description_value_not_found (p, ErrorDescription);
	      err = ASN1_VALUE_NOT_FOUND;
	      goto error;
	    }
	  len2 = max_len;
	  err =
	    _asn1_time_der (p->value, p->value_len,
			    der ? der + counter : &dummy, &len2);
	  if (err != ASN1_SUCCESS && err != ASN1_MEM_ERROR)
	    goto error;

	  max_len -= len2;
	  counter += len2;
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_OCTET_STRING:
	case ASN1_ETYPE_GENERALSTRING:
	case ASN1_ETYPE_NUMERIC_STRING:
	case ASN1_ETYPE_IA5_STRING:
	case ASN1_ETYPE_TELETEX_STRING:
	case ASN1_ETYPE_PRINTABLE_STRING:
	case ASN1_ETYPE_UNIVERSAL_STRING:
	case ASN1_ETYPE_BMP_STRING:
	case ASN1_ETYPE_UTF8_STRING:
	case ASN1_ETYPE_VISIBLE_STRING:
	case ASN1_ETYPE_BIT_STRING:
	  if (p->value == NULL)
	    {
	      _asn1_error_description_value_not_found (p, ErrorDescription);
	      err = ASN1_VALUE_NOT_FOUND;
	      goto error;
	    }
	  len2 = asn1_get_length_der (p->value, p->value_len, &len3);
	  if (len2 < 0)
	    {
	      err = ASN1_DER_ERROR;
	      goto error;
	    }
	  max_len -= len2 + len3;
	  if (der != NULL && max_len >= 0)
	    memcpy (der + counter, p->value, len3 + len2);
	  counter += len3 + len2;
	  move = RIGHT;
	  break;
	case ASN1_ETYPE_SEQUENCE:
	case ASN1_ETYPE_SET:
	  if (move != UP)
	    {
	      p->tmp_ival = counter;
	      if (p->down == NULL)
		{
		  move = UP;
		  continue;
		}
	      else
		{
		  p2 = p->down;
		  while (p2 && (type_field (p2->type) == ASN1_ETYPE_TAG))
		    p2 = p2->right;
		  if (p2)
		    {
		      p = p2;
		      move = RIGHT;
		      continue;
		    }
		  move = UP;
		  continue;
		}
	    }
	  else
	    {			/* move==UP */
	      len2 = p->tmp_ival;
	      p->tmp_ival = 0;
	      if ((type_field (p->type) == ASN1_ETYPE_SET) && (max_len >= 0))
		{
		  err =
		    _asn1_ordering_set (der ? der + len2 : &dummy,
					counter - len2, p);
		  if (err != ASN1_SUCCESS)
		    goto error;
		}
	      asn1_length_der (counter - len2, temp, &len3);
	      max_len -= len3;
	      if (der != NULL && max_len >= 0)
		{
		  memmove (der + len2 + len3, der + len2, counter - len2);
		  memcpy (der + len2, temp, len3);
		}
	      counter += len3;
	      move = RIGHT;
	    }
	  break;
	case ASN1_ETYPE_SEQUENCE_OF:
	case ASN1_ETYPE_SET_OF:
	  if (move != UP)
	    {
	      p->tmp_ival = counter;
	      p = p->down;
	      while ((type_field (p->type) == ASN1_ETYPE_TAG)
		     || (type_field (p->type) == ASN1_ETYPE_SIZE))
		p = p->right;
	      if (p->right)
		{
		  p = p->right;
		  move = RIGHT;
		  continue;
		}
	      else
		p = _asn1_find_up (p);
	      move = UP;
	    }
	  if (move == UP)
	    {
	      len2 = p->tmp_ival;
	      p->tmp_ival = 0;
	      if ((type_field (p->type) == ASN1_ETYPE_SET_OF)
		  && (counter - len2 > 0) && (max_len >= 0))
		{
		  err =
		    _asn1_ordering_set_of (der ? der + len2 : &dummy,
					   counter - len2, p);
		  if (err != ASN1_SUCCESS)
		    goto error;
		}
	      asn1_length_der (counter - len2, temp, &len3);
	      max_len -= len3;
	      if (der != NULL && max_len >= 0)
		{
		  memmove (der + len2 + len3, der + len2, counter - len2);
		  memcpy (der + len2, temp, len3);
		}
	      counter += len3;
	      move = RIGHT;
	    }
	  break;
	case ASN1_ETYPE_ANY:
	  if (p->value == NULL)
	    {
	      _asn1_error_description_value_not_found (p, ErrorDescription);
	      err = ASN1_VALUE_NOT_FOUND;
	      goto error;
	    }
	  len2 = asn1_get_length_der (p->value, p->value_len, &len3);
	  if (len2 < 0)
	    {
	      err = ASN1_DER_ERROR;
	      goto error;
	    }
	  max_len -= len2;
	  if (der != NULL && max_len >= 0)
	    memcpy (der + counter, p->value + len3, len2);
	  counter += len2;
	  move = RIGHT;
	  break;
	default:
	  move = (move == UP) ? RIGHT : DOWN;
	  break;
	}

      if ((move != DOWN) && (counter != counter_old))
	{
	  p->end = counter - 1;
	  err = _asn1_complete_explicit_tag (p, der, &counter, &max_len);
	  if (err != ASN1_SUCCESS && err != ASN1_MEM_ERROR)
	    goto error;
	}

      if (p == node && move != DOWN)
	break;

      if (move == DOWN)
	{
	  if (p->down)
	    p = p->down;
	  else
	    move = RIGHT;
	}
      if (move == RIGHT)
	{
	  if (p->right)
	    p = p->right;
	  else
	    move = UP;
	}
      if (move == UP)
	p = _asn1_find_up (p);
    }

  *len = counter;

  if (max_len < 0)
    {
      err = ASN1_MEM_ERROR;
      goto error;
    }

  err = ASN1_SUCCESS;

error:
  asn1_delete_structure (&node);
  return err;
}
