/*
 * Copyright (C) 2002-2021 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, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 * 02110-1301, USA
 */


/*****************************************************/
/* File: structure.c                                 */
/* Description: Functions to create and delete an    */
/*  ASN1 tree.                                       */
/*****************************************************/


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


extern char _asn1_identifierMissing[];


/******************************************************/
/* Function : _asn1_add_single_node                     */
/* Description: creates a new NODE_ASN element.       */
/* Parameters:                                        */
/*   type: type of the new element (see ASN1_ETYPE_         */
/*         and CONST_ constants).                     */
/* Return: pointer to the new element.                */
/******************************************************/
asn1_node
_asn1_add_single_node (unsigned int type)
{
  asn1_node punt;

  punt = calloc (1, sizeof (struct asn1_node_st));
  if (punt == NULL)
    return NULL;

  punt->type = type;

  return punt;
}


/******************************************************************/
/* Function : _asn1_find_left                                     */
/* Description: returns the NODE_ASN element with RIGHT field that*/
/*              points the element NODE.                          */
/* Parameters:                                                    */
/*   node: NODE_ASN element pointer.                              */
/* Return: NULL if not found.                                     */
/******************************************************************/
asn1_node
_asn1_find_left (asn1_node_const node)
{
  if ((node == NULL) || (node->left == NULL) || (node->left->down == node))
    return NULL;

  return node->left;
}


int
_asn1_create_static_structure (asn1_node_const pointer, char *output_file_name,
			       char *vector_name)
{
  FILE *file;
  asn1_node_const p;
  unsigned long t;

  file = fopen (output_file_name, "w");

  if (file == NULL)
    return ASN1_FILE_NOT_FOUND;

  fprintf (file, "#if HAVE_CONFIG_H\n");
  fprintf (file, "# include \"config.h\"\n");
  fprintf (file, "#endif\n\n");

  fprintf (file, "#include <libtasn1.h>\n\n");

  fprintf (file, "const asn1_static_node %s[] = {\n", vector_name);

  p = pointer;

  while (p)
    {
      fprintf (file, "  { ");

      if (p->name[0] != 0)
	fprintf (file, "\"%s\", ", p->name);
      else
	fprintf (file, "NULL, ");

      t = p->type;
      if (p->down)
	t |= CONST_DOWN;
      if (p->right)
	t |= CONST_RIGHT;

      fprintf (file, "%lu, ", t);

      if (p->value)
	fprintf (file, "\"%s\"},\n", p->value);
      else
	fprintf (file, "NULL },\n");

      if (p->down)
	{
	  p = p->down;
	}
      else if (p->right)
	{
	  p = p->right;
	}
      else
	{
	  while (1)
	    {
	      p = _asn1_find_up (p);
	      if (p == pointer)
		{
		  p = NULL;
		  break;
		}
	      if (p->right)
		{
		  p = p->right;
		  break;
		}
	    }
	}
    }

  fprintf (file, "  { NULL, 0, NULL }\n};\n");

  fclose (file);

  return ASN1_SUCCESS;
}


/**
 * asn1_array2tree:
 * @array: specify the array that contains ASN.1 declarations
 * @definitions: return the pointer to the structure created by
 *   *ARRAY ASN.1 declarations
 * @errorDescription: return the error description.
 *
 * Creates the structures needed to manage the ASN.1 definitions.
 * @array is a vector created by asn1_parser2array().
 *
 * Returns: %ASN1_SUCCESS if structure was created correctly,
 *   %ASN1_ELEMENT_NOT_EMPTY if *@definitions not NULL,
 *   %ASN1_IDENTIFIER_NOT_FOUND if in the file there is an identifier
 *   that is not defined (see @errorDescription for more information),
 *   %ASN1_ARRAY_ERROR if the array pointed by @array is wrong.
 **/
int
asn1_array2tree (const asn1_static_node * array, asn1_node * definitions,
		 char *errorDescription)
{
  asn1_node p, p_last = NULL;
  unsigned long k;
  int move;
  int result;
  unsigned int type;
  list_type *e_list = NULL;

  if (errorDescription)
    errorDescription[0] = 0;

  if (*definitions != NULL)
    return ASN1_ELEMENT_NOT_EMPTY;

  move = UP;

  for (k = 0; array[k].value || array[k].type || array[k].name; k++)
    {
      type = convert_old_type (array[k].type);

      p = _asn1_add_static_node (&e_list, type & (~CONST_DOWN));
      if (array[k].name)
	_asn1_set_name (p, array[k].name);
      if (array[k].value)
	_asn1_set_value (p, array[k].value, strlen (array[k].value) + 1);

      if (*definitions == NULL)
	*definitions = p;

      if (move == DOWN)
	{
	  if (p_last && p_last->down)
	      _asn1_delete_structure (e_list, &p_last->down, 0);
	  _asn1_set_down (p_last, p);
	}
      else if (move == RIGHT)
        {
	  if (p_last && p_last->right)
	      _asn1_delete_structure (e_list, &p_last->right, 0);
	  _asn1_set_right (p_last, p);
        }

      p_last = p;

      if (type & CONST_DOWN)
	move = DOWN;
      else if (type & CONST_RIGHT)
	move = RIGHT;
      else
	{
	  while (p_last != *definitions)
	    {
	      p_last = _asn1_find_up (p_last);

	      if (p_last == NULL)
		break;

	      if (p_last->type & CONST_RIGHT)
		{
		  p_last->type &= ~CONST_RIGHT;
		  move = RIGHT;
		  break;
		}
	    }			/* while */
	}
    }				/* while */

  if (p_last == *definitions)
    {
      result = _asn1_check_identifier (*definitions);
      if (result == ASN1_SUCCESS)
	{
	  _asn1_change_integer_value (*definitions);
	  result = _asn1_expand_object_id (&e_list, *definitions);
	}
    }
  else
    {
      result = ASN1_ARRAY_ERROR;
    }

  if (errorDescription != NULL)
    {
      if (result == ASN1_IDENTIFIER_NOT_FOUND)
	{
	  Estrcpy (errorDescription, ":: identifier '");
	  Estrcat (errorDescription, _asn1_identifierMissing);
	  Estrcat (errorDescription, "' not found");
	}
      else
	errorDescription[0] = 0;
    }

  if (result != ASN1_SUCCESS)
    {
      _asn1_delete_list_and_nodes (e_list);
      *definitions = NULL;
    }
  else
    _asn1_delete_list (e_list);

  return result;
}

/**
 * asn1_delete_structure:
 * @structure: pointer to the structure that you want to delete.
 *
 * Deletes the structure *@structure.  At the end, *@structure is set
 * to NULL.
 *
 * Returns: %ASN1_SUCCESS if successful, %ASN1_ELEMENT_NOT_FOUND if
 *   *@structure was NULL.
 **/
int
asn1_delete_structure (asn1_node * structure)
{
  return _asn1_delete_structure (NULL, structure, 0);
}

/**
 * asn1_delete_structure2:
 * @structure: pointer to the structure that you want to delete.
 * @flags: additional flags (see %ASN1_DELETE_FLAG_ZEROIZE)
 *
 * Deletes the structure *@structure.  At the end, *@structure is set
 * to NULL.
 *
 * Returns: %ASN1_SUCCESS if successful, %ASN1_ELEMENT_NOT_FOUND if
 *   *@structure was NULL.
 **/
int
asn1_delete_structure2 (asn1_node * structure, unsigned int flags)
{
  return _asn1_delete_structure (NULL, structure, flags);
}

int
_asn1_delete_structure (list_type *e_list, asn1_node * structure, unsigned int flags)
{
  asn1_node p, p2, p3;

  if (*structure == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  p = *structure;
  while (p)
    {
      if (p->down)
	{
	  p = p->down;
	}
      else
	{			/* no down */
	  p2 = p->right;
	  if (p != *structure)
	    {
	      p3 = _asn1_find_up (p);
	      _asn1_set_down (p3, p2);
	      if (e_list)
		_asn1_delete_node_from_list (e_list, p);
	      _asn1_remove_node (p, flags);
	      p = p3;
	    }
	  else
	    {			/* p==root */
	      p3 = _asn1_find_left (p);
	      if (!p3)
		{
		  p3 = _asn1_find_up (p);
		  if (p3)
		    _asn1_set_down (p3, p2);
		  else
		    {
		      if (p->right)
			p->right->left = NULL;
		    }
		}
	      else
		_asn1_set_right (p3, p2);
	      if (e_list)
		_asn1_delete_node_from_list (e_list, p);
	      _asn1_remove_node (p, flags);
	      p = NULL;
	    }
	}
    }

  *structure = NULL;
  return ASN1_SUCCESS;
}


/**
 * asn1_delete_element:
 * @structure: pointer to the structure that contains the element you
 *   want to delete.
 * @element_name: element's name you want to delete.
 *
 * Deletes the element named *@element_name inside *@structure.
 *
 * Returns: %ASN1_SUCCESS if successful, %ASN1_ELEMENT_NOT_FOUND if
 *   the @element_name was not found.
 **/
int
asn1_delete_element (asn1_node structure, const char *element_name)
{
  asn1_node p2, p3, source_node;

  source_node = asn1_find_node (structure, element_name);

  if (source_node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  p2 = source_node->right;
  p3 = _asn1_find_left (source_node);
  if (!p3)
    {
      p3 = _asn1_find_up (source_node);
      if (p3)
	_asn1_set_down (p3, p2);
      else if (source_node->right)
	source_node->right->left = NULL;
    }
  else
    _asn1_set_right (p3, p2);

  return asn1_delete_structure (&source_node);
}

#ifndef __clang_analyzer__
asn1_node
_asn1_copy_structure3 (asn1_node_const source_node)
{
  asn1_node_const p_s;
  asn1_node dest_node, p_d, p_d_prev;
  int move;

  if (source_node == NULL)
    return NULL;

  dest_node = _asn1_add_single_node (source_node->type);
  if (dest_node == NULL)
    return dest_node;

  p_s = source_node;
  p_d = dest_node;

  move = DOWN;

  do
    {
      if (move != UP)
	{
	  if (p_s->name[0] != 0)
	    _asn1_cpy_name (p_d, p_s);
	  if (p_s->value)
	    _asn1_set_value (p_d, p_s->value, p_s->value_len);
	  if (p_s->down)
	    {
	      p_s = p_s->down;
	      p_d_prev = p_d;
	      p_d = _asn1_add_single_node (p_s->type);
	      _asn1_set_down (p_d_prev, p_d);
	      continue;
	    }
	  p_d->start = p_s->start;
	  p_d->end = p_s->end;
	}

      if (p_s == source_node)
	break;

      if (p_s->right)
	{
	  move = RIGHT;
	  p_s = p_s->right;
	  p_d_prev = p_d;
	  p_d = _asn1_add_single_node (p_s->type);
	  _asn1_set_right (p_d_prev, p_d);
	}
      else
	{
	  move = UP;
	  p_s = _asn1_find_up (p_s);
	  p_d = _asn1_find_up (p_d);
	}
    }
  while (p_s != source_node);
  return dest_node;
}
#else

/* Non-production code */
asn1_node
_asn1_copy_structure3 (asn1_node_const source_node)
{
  return NULL;
}
#endif /* __clang_analyzer__ */


static asn1_node
_asn1_copy_structure2 (asn1_node_const root, const char *source_name)
{
  asn1_node source_node;

  source_node = asn1_find_node (root, source_name);

  return _asn1_copy_structure3 (source_node);

}


static int
_asn1_type_choice_config (asn1_node node)
{
  asn1_node p, p2, p3, p4;
  int move, tlen;

  if (node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  p = node;
  move = DOWN;

  while (!((p == node) && (move == UP)))
    {
      if (move != UP)
	{
	  if ((type_field (p->type) == ASN1_ETYPE_CHOICE)
	      && (p->type & CONST_TAG))
	    {
	      p2 = p->down;
	      while (p2)
		{
		  if (type_field (p2->type) != ASN1_ETYPE_TAG)
		    {
		      p2->type |= CONST_TAG;
		      p3 = _asn1_find_left (p2);
		      while (p3)
			{
			  if (type_field (p3->type) == ASN1_ETYPE_TAG)
			    {
			      p4 = _asn1_add_single_node (p3->type);
			      tlen = _asn1_strlen (p3->value);
			      if (tlen > 0)
				_asn1_set_value (p4, p3->value, tlen + 1);
			      _asn1_set_right (p4, p2->down);
			      _asn1_set_down (p2, p4);
			    }
			  p3 = _asn1_find_left (p3);
			}
		    }
		  p2 = p2->right;
		}
	      p->type &= ~(CONST_TAG);
	      p2 = p->down;
	      while (p2)
		{
		  p3 = p2->right;
		  if (type_field (p2->type) == ASN1_ETYPE_TAG)
		    asn1_delete_structure (&p2);
		  p2 = p3;
		}
	    }
	  move = DOWN;
	}
      else
	move = RIGHT;

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

      if (p == node)
	{
	  move = UP;
	  continue;
	}

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

  return ASN1_SUCCESS;
}


static int
_asn1_expand_identifier (asn1_node * node, asn1_node_const root)
{
  asn1_node p, p2, p3;
  char name2[ASN1_MAX_NAME_SIZE + 2];
  int move;

  if (node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  p = *node;
  move = DOWN;

  while (!((p == *node) && (move == UP)))
    {
      if (move != UP)
	{
	  if (type_field (p->type) == ASN1_ETYPE_IDENTIFIER)
	    {
	      snprintf (name2, sizeof (name2), "%s.%s", root->name, p->value);
	      p2 = _asn1_copy_structure2 (root, name2);
	      if (p2 == NULL)
		{
		  return ASN1_IDENTIFIER_NOT_FOUND;
		}
	      _asn1_cpy_name (p2, p);
	      p2->right = p->right;
	      p2->left = p->left;
	      if (p->right)
		p->right->left = p2;
	      p3 = p->down;
	      if (p3)
		{
		  while (p3->right)
		    p3 = p3->right;
		  _asn1_set_right (p3, p2->down);
		  _asn1_set_down (p2, p->down);
		}

	      p3 = _asn1_find_left (p);
	      if (p3)
		_asn1_set_right (p3, p2);
	      else
		{
		  p3 = _asn1_find_up (p);
		  if (p3)
		    _asn1_set_down (p3, p2);
		  else
		    {
		      p2->left = NULL;
		    }
		}

	      if (p->type & CONST_SIZE)
		p2->type |= CONST_SIZE;
	      if (p->type & CONST_TAG)
		p2->type |= CONST_TAG;
	      if (p->type & CONST_OPTION)
		p2->type |= CONST_OPTION;
	      if (p->type & CONST_DEFAULT)
		p2->type |= CONST_DEFAULT;
	      if (p->type & CONST_SET)
		p2->type |= CONST_SET;
	      if (p->type & CONST_NOT_USED)
		p2->type |= CONST_NOT_USED;

	      if (p == *node)
		*node = p2;
	      _asn1_remove_node (p, 0);
	      p = p2;
	      move = DOWN;
	      continue;
	    }
	  move = DOWN;
	}
      else
	move = RIGHT;

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

      if (p == *node)
	{
	  move = UP;
	  continue;
	}

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

  return ASN1_SUCCESS;
}


/**
 * asn1_create_element:
 * @definitions: pointer to the structure returned by "parser_asn1" function
 * @source_name: the name of the type of the new structure (must be
 *   inside p_structure).
 * @element: pointer to the structure created.
 *
 * Creates a structure of type @source_name.  Example using
 *  "pkix.asn":
 *
 * rc = asn1_create_element(cert_def, "PKIX1.Certificate", certptr);
 *
 * Returns: %ASN1_SUCCESS if creation OK, %ASN1_ELEMENT_NOT_FOUND if
 *   @source_name is not known.
 **/
int
asn1_create_element (asn1_node_const definitions, const char *source_name,
		     asn1_node * element)
{
  asn1_node dest_node;
  int res;

  dest_node = _asn1_copy_structure2 (definitions, source_name);

  if (dest_node == NULL)
    return ASN1_ELEMENT_NOT_FOUND;

  _asn1_set_name (dest_node, "");

  res = _asn1_expand_identifier (&dest_node, definitions);
  _asn1_type_choice_config (dest_node);

  *element = dest_node;

  return res;
}


/**
 * asn1_print_structure:
 * @out: pointer to the output file (e.g. stdout).
 * @structure: pointer to the structure that you want to visit.
 * @name: an element of the structure
 * @mode: specify how much of the structure to print, can be
 *   %ASN1_PRINT_NAME, %ASN1_PRINT_NAME_TYPE,
 *   %ASN1_PRINT_NAME_TYPE_VALUE, or %ASN1_PRINT_ALL.
 *
 * Prints on the @out file descriptor the structure's tree starting
 * from the @name element inside the structure @structure.
 **/
void
asn1_print_structure (FILE * out, asn1_node_const structure, const char *name,
		      int mode)
{
  asn1_node_const p, root;
  int k, indent = 0, len, len2, len3;

  if (out == NULL)
    return;

  root = asn1_find_node (structure, name);

  if (root == NULL)
    return;

  p = root;
  while (p)
    {
      if (mode == ASN1_PRINT_ALL)
	{
	  for (k = 0; k < indent; k++)
	    fprintf (out, " ");
	  fprintf (out, "name:");
	  if (p->name[0] != 0)
	    fprintf (out, "%s  ", p->name);
	  else
	    fprintf (out, "NULL  ");
	}
      else
	{
	  switch (type_field (p->type))
	    {
	    case ASN1_ETYPE_CONSTANT:
	    case ASN1_ETYPE_TAG:
	    case ASN1_ETYPE_SIZE:
	      break;
	    default:
	      for (k = 0; k < indent; k++)
		fprintf (out, " ");
	      fprintf (out, "name:");
	      if (p->name[0] != 0)
		fprintf (out, "%s  ", p->name);
	      else
		fprintf (out, "NULL  ");
	    }
	}

      if (mode != ASN1_PRINT_NAME)
	{
	  unsigned type = type_field (p->type);
	  switch (type)
	    {
	    case ASN1_ETYPE_CONSTANT:
	      if (mode == ASN1_PRINT_ALL)
		fprintf (out, "type:CONST");
	      break;
	    case ASN1_ETYPE_TAG:
	      if (mode == ASN1_PRINT_ALL)
		fprintf (out, "type:TAG");
	      break;
	    case ASN1_ETYPE_SIZE:
	      if (mode == ASN1_PRINT_ALL)
		fprintf (out, "type:SIZE");
	      break;
	    case ASN1_ETYPE_DEFAULT:
	      fprintf (out, "type:DEFAULT");
	      break;
	    case ASN1_ETYPE_IDENTIFIER:
	      fprintf (out, "type:IDENTIFIER");
	      break;
	    case ASN1_ETYPE_ANY:
	      fprintf (out, "type:ANY");
	      break;
	    case ASN1_ETYPE_CHOICE:
	      fprintf (out, "type:CHOICE");
	      break;
	    case ASN1_ETYPE_DEFINITIONS:
	      fprintf (out, "type:DEFINITIONS");
	      break;
	    CASE_HANDLED_ETYPES:
	      fprintf (out, "%s", _asn1_tags[type].desc);
	      break;
	    default:
	      break;
	    }
	}

      if ((mode == ASN1_PRINT_NAME_TYPE_VALUE) || (mode == ASN1_PRINT_ALL))
	{
	  switch (type_field (p->type))
	    {
	    case ASN1_ETYPE_CONSTANT:
	      if (mode == ASN1_PRINT_ALL)
		if (p->value)
		  fprintf (out, "  value:%s", p->value);
	      break;
	    case ASN1_ETYPE_TAG:
	      if (mode == ASN1_PRINT_ALL)
		if (p->value)
		  fprintf (out, "  value:%s", p->value);
	      break;
	    case ASN1_ETYPE_SIZE:
	      if (mode == ASN1_PRINT_ALL)
		if (p->value)
		  fprintf (out, "  value:%s", p->value);
	      break;
	    case ASN1_ETYPE_DEFAULT:
	      if (p->value)
		fprintf (out, "  value:%s", p->value);
	      else if (p->type & CONST_TRUE)
		fprintf (out, "  value:TRUE");
	      else if (p->type & CONST_FALSE)
		fprintf (out, "  value:FALSE");
	      break;
	    case ASN1_ETYPE_IDENTIFIER:
	      if (p->value)
		fprintf (out, "  value:%s", p->value);
	      break;
	    case ASN1_ETYPE_INTEGER:
	      if (p->value)
		{
		  len2 = -1;
		  len = asn1_get_length_der (p->value, p->value_len, &len2);
		  fprintf (out, "  value:0x");
		  if (len > 0)
		    for (k = 0; k < len; k++)
		      fprintf (out, "%02x", (unsigned) (p->value)[k + len2]);
		}
	      break;
	    case ASN1_ETYPE_ENUMERATED:
	      if (p->value)
		{
		  len2 = -1;
		  len = asn1_get_length_der (p->value, p->value_len, &len2);
		  fprintf (out, "  value:0x");
		  if (len > 0)
		    for (k = 0; k < len; k++)
		      fprintf (out, "%02x", (unsigned) (p->value)[k + len2]);
		}
	      break;
	    case ASN1_ETYPE_BOOLEAN:
	      if (p->value)
		{
		  if (p->value[0] == 'T')
		    fprintf (out, "  value:TRUE");
		  else if (p->value[0] == 'F')
		    fprintf (out, "  value:FALSE");
		}
	      break;
	    case ASN1_ETYPE_BIT_STRING:
	      if (p->value)
		{
		  len2 = -1;
		  len = asn1_get_length_der (p->value, p->value_len, &len2);
		  if (len > 0)
		    {
		      fprintf (out, "  value(%i):",
			       (len - 1) * 8 - (p->value[len2]));
		      for (k = 1; k < len; k++)
			fprintf (out, "%02x", (unsigned) (p->value)[k + len2]);
		    }
		}
	      break;
	    case ASN1_ETYPE_GENERALIZED_TIME:
	    case ASN1_ETYPE_UTC_TIME:
	      if (p->value)
		{
		  fprintf (out, "  value:");
		  for (k = 0; k < p->value_len; k++)
		    fprintf (out, "%c", (p->value)[k]);
		}
	      break;
	    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_UTF8_STRING:
	    case ASN1_ETYPE_VISIBLE_STRING:
	      if (p->value)
		{
		  len2 = -1;
		  len = asn1_get_length_der (p->value, p->value_len, &len2);
		  fprintf (out, "  value:");
		  if (len > 0)
		    for (k = 0; k < len; k++)
		      fprintf (out, "%c", (p->value)[k + len2]);
		}
	      break;
	    case ASN1_ETYPE_BMP_STRING:
	    case ASN1_ETYPE_OCTET_STRING:
	      if (p->value)
		{
		  len2 = -1;
		  len = asn1_get_length_der (p->value, p->value_len, &len2);
		  fprintf (out, "  value:");
		  if (len > 0)
		    for (k = 0; k < len; k++)
		      fprintf (out, "%02x", (unsigned) (p->value)[k + len2]);
		}
	      break;
	    case ASN1_ETYPE_OBJECT_ID:
	      if (p->value)
		fprintf (out, "  value:%s", p->value);
	      break;
	    case ASN1_ETYPE_ANY:
	      if (p->value)
		{
		  len3 = -1;
		  len2 = asn1_get_length_der (p->value, p->value_len, &len3);
		  fprintf (out, "  value:");
		  if (len2 > 0)
		    for (k = 0; k < len2; k++)
		      fprintf (out, "%02x", (unsigned) (p->value)[k + len3]);
		}
	      break;
	    case ASN1_ETYPE_SET:
	    case ASN1_ETYPE_SET_OF:
	    case ASN1_ETYPE_CHOICE:
	    case ASN1_ETYPE_DEFINITIONS:
	    case ASN1_ETYPE_SEQUENCE_OF:
	    case ASN1_ETYPE_SEQUENCE:
	    case ASN1_ETYPE_NULL:
	      break;
	    default:
	      break;
	    }
	}

      if (mode == ASN1_PRINT_ALL)
	{
	  if (p->type & 0x1FFFFF00)
	    {
	      fprintf (out, "  attr:");
	      if (p->type & CONST_UNIVERSAL)
		fprintf (out, "UNIVERSAL,");
	      if (p->type & CONST_PRIVATE)
		fprintf (out, "PRIVATE,");
	      if (p->type & CONST_APPLICATION)
		fprintf (out, "APPLICATION,");
	      if (p->type & CONST_EXPLICIT)
		fprintf (out, "EXPLICIT,");
	      if (p->type & CONST_IMPLICIT)
		fprintf (out, "IMPLICIT,");
	      if (p->type & CONST_TAG)
		fprintf (out, "TAG,");
	      if (p->type & CONST_DEFAULT)
		fprintf (out, "DEFAULT,");
	      if (p->type & CONST_TRUE)
		fprintf (out, "TRUE,");
	      if (p->type & CONST_FALSE)
		fprintf (out, "FALSE,");
	      if (p->type & CONST_LIST)
		fprintf (out, "LIST,");
	      if (p->type & CONST_MIN_MAX)
		fprintf (out, "MIN_MAX,");
	      if (p->type & CONST_OPTION)
		fprintf (out, "OPTION,");
	      if (p->type & CONST_1_PARAM)
		fprintf (out, "1_PARAM,");
	      if (p->type & CONST_SIZE)
		fprintf (out, "SIZE,");
	      if (p->type & CONST_DEFINED_BY)
		fprintf (out, "DEF_BY,");
	      if (p->type & CONST_GENERALIZED)
		fprintf (out, "GENERALIZED,");
	      if (p->type & CONST_UTC)
		fprintf (out, "UTC,");
	      if (p->type & CONST_SET)
		fprintf (out, "SET,");
	      if (p->type & CONST_NOT_USED)
		fprintf (out, "NOT_USED,");
	      if (p->type & CONST_ASSIGN)
		fprintf (out, "ASSIGNMENT,");
	    }
	}

      if (mode == ASN1_PRINT_ALL)
	{
	  fprintf (out, "\n");
	}
      else
	{
	  switch (type_field (p->type))
	    {
	    case ASN1_ETYPE_CONSTANT:
	    case ASN1_ETYPE_TAG:
	    case ASN1_ETYPE_SIZE:
	      break;
	    default:
	      fprintf (out, "\n");
	    }
	}

      if (p->down)
	{
	  p = p->down;
	  indent += 2;
	}
      else if (p == root)
	{
	  p = NULL;
	  break;
	}
      else if (p->right)
	p = p->right;
      else
	{
	  while (1)
	    {
	      p = _asn1_find_up (p);
	      if (p == root)
		{
		  p = NULL;
		  break;
		}
	      indent -= 2;
	      if (p->right)
		{
		  p = p->right;
		  break;
		}
	    }
	}
    }
}



/**
 * asn1_number_of_elements:
 * @element: pointer to the root of an ASN1 structure.
 * @name: the name of a sub-structure of ROOT.
 * @num: pointer to an integer where the result will be stored
 *
 * Counts the number of elements of a sub-structure called NAME with
 * names equal to "?1","?2", ...
 *
 * Returns: %ASN1_SUCCESS if successful, %ASN1_ELEMENT_NOT_FOUND if
 *   @name is not known, %ASN1_GENERIC_ERROR if pointer @num is %NULL.
 **/
int
asn1_number_of_elements (asn1_node_const element, const char *name, int *num)
{
  asn1_node_const node, p;

  if (num == NULL)
    return ASN1_GENERIC_ERROR;

  *num = 0;

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

  p = node->down;

  while (p)
    {
      if (p->name[0] == '?')
	(*num)++;
      p = p->right;
    }

  return ASN1_SUCCESS;
}


/**
 * asn1_find_structure_from_oid:
 * @definitions: ASN1 definitions
 * @oidValue: value of the OID to search (e.g. "1.2.3.4").
 *
 * Search the structure that is defined just after an OID definition.
 *
 * Returns: %NULL when @oidValue not found, otherwise the pointer to a
 *   constant string that contains the element name defined just after
 *   the OID.
 **/
const char *
asn1_find_structure_from_oid (asn1_node_const definitions, const char *oidValue)
{
  char name[2 * ASN1_MAX_NAME_SIZE + 2];
  char value[ASN1_MAX_NAME_SIZE];
  asn1_node p;
  int len;
  int result;
  const char *definitionsName;

  if ((definitions == NULL) || (oidValue == NULL))
    return NULL;		/* ASN1_ELEMENT_NOT_FOUND; */

  definitionsName = definitions->name;

  /* search the OBJECT_ID into definitions */
  p = definitions->down;
  while (p)
    {
      if ((type_field (p->type) == ASN1_ETYPE_OBJECT_ID) &&
	  (p->type & CONST_ASSIGN))
	{
          snprintf(name, sizeof(name), "%s.%s", definitionsName, p->name);

	  len = ASN1_MAX_NAME_SIZE;
	  result = asn1_read_value (definitions, name, value, &len);

	  if ((result == ASN1_SUCCESS) && (!strcmp (oidValue, value)))
	    {
	      p = p->right;
	      if (p == NULL)	/* reach the end of ASN1 definitions */
		return NULL;	/* ASN1_ELEMENT_NOT_FOUND; */

	      return p->name;
	    }
	}
      p = p->right;
    }

  return NULL;			/* ASN1_ELEMENT_NOT_FOUND; */
}

/**
 * asn1_copy_node:
 * @dst: Destination asn1 node.
 * @dst_name: Field name in destination node.
 * @src: Source asn1 node.
 * @src_name: Field name in source node.
 *
 * Create a deep copy of a asn1_node variable. That
 * function requires @dst to be expanded using asn1_create_element().
 *
 * Returns: Return %ASN1_SUCCESS on success.
 **/
int
asn1_copy_node (asn1_node dst, const char *dst_name,
		asn1_node_const src, const char *src_name)
{
  int result;
  asn1_node dst_node;
  void *data = NULL;
  int size = 0;

  result = asn1_der_coding (src, src_name, NULL, &size, NULL);
  if (result != ASN1_MEM_ERROR)
    return result;

  data = malloc (size);
  if (data == NULL)
    return ASN1_MEM_ERROR;

  result = asn1_der_coding (src, src_name, data, &size, NULL);
  if (result != ASN1_SUCCESS)
    {
      free (data);
      return result;
    }

  dst_node = asn1_find_node (dst, dst_name);
  if (dst_node == NULL)
    {
      free (data);
      return ASN1_ELEMENT_NOT_FOUND;
    }

  result = asn1_der_decoding (&dst_node, data, size, NULL);

  free (data);

  return result;
}

/**
 * asn1_dup_node:
 * @src: Source asn1 node.
 * @src_name: Field name in source node.
 *
 * Create a deep copy of a asn1_node variable. This function
 * will return an exact copy of the provided structure.
 *
 * Returns: Return %NULL on failure.
 **/
asn1_node
asn1_dup_node (asn1_node_const src, const char *src_name)
{
  return _asn1_copy_structure2(src, src_name);
}
