/* Support for printing Ada values for GDB, the GNU debugger.

   Copyright (C) 1986, 1988, 1989, 1991, 1992, 1993, 1994, 1997, 2001, 2002,
   2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
   Free Software Foundation, Inc.

   This file is part of GDB.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program 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 General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

#include "defs.h"
#include <ctype.h>
#include "gdb_string.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "demangle.h"
#include "valprint.h"
#include "language.h"
#include "annotate.h"
#include "ada-lang.h"
#include "c-lang.h"
#include "infcall.h"
#include "exceptions.h"
#include "objfiles.h"

static void print_record (struct type *, const gdb_byte *, struct ui_file *,
			  int,
			  const struct value *,
			  const struct value_print_options *);

static int print_field_values (struct type *, const gdb_byte *,
			       struct ui_file *, int,
			       const struct value *,
			       const struct value_print_options *,
			       int, struct type *,
			       const gdb_byte *);

static void adjust_type_signedness (struct type *);

static int ada_val_print_1 (struct type *, const gdb_byte *, int, CORE_ADDR,
			    struct ui_file *, int,
			    const struct value *,
			    const struct value_print_options *);


/* Make TYPE unsigned if its range of values includes no negatives.  */
static void
adjust_type_signedness (struct type *type)
{
  if (type != NULL && TYPE_CODE (type) == TYPE_CODE_RANGE
      && TYPE_LOW_BOUND (type) >= 0)
    TYPE_UNSIGNED (type) = 1;
}

/* Assuming TYPE is a simple array type, prints its lower bound on STREAM,
   if non-standard (i.e., other than 1 for numbers, other than lower bound
   of index type for enumerated type).  Returns 1 if something printed,
   otherwise 0.  */

static int
print_optional_low_bound (struct ui_file *stream, struct type *type,
			  const struct value_print_options *options)
{
  struct type *index_type;
  LONGEST low_bound;
  LONGEST high_bound;

  if (options->print_array_indexes)
    return 0;

  if (!get_array_bounds (type, &low_bound, &high_bound))
    return 0;

  /* If this is an empty array, then don't print the lower bound.
     That would be confusing, because we would print the lower bound,
     followed by... nothing!  */
  if (low_bound > high_bound)
    return 0;

  index_type = TYPE_INDEX_TYPE (type);

  if (TYPE_CODE (index_type) == TYPE_CODE_RANGE)
    {
      /* We need to know what the base type is, in order to do the
         appropriate check below.  Otherwise, if this is a subrange
         of an enumerated type, where the underlying value of the
         first element is typically 0, we might test the low bound
         against the wrong value.  */
      index_type = TYPE_TARGET_TYPE (index_type);
    }

  switch (TYPE_CODE (index_type))
    {
    case TYPE_CODE_BOOL:
      if (low_bound == 0)
	return 0;
      break;
    case TYPE_CODE_ENUM:
      if (low_bound == TYPE_FIELD_BITPOS (index_type, 0))
	return 0;
      break;
    case TYPE_CODE_UNDEF:
      index_type = NULL;
      /* FALL THROUGH */
    default:
      if (low_bound == 1)
	return 0;
      break;
    }

  ada_print_scalar (index_type, low_bound, stream);
  fprintf_filtered (stream, " => ");
  return 1;
}

/*  Version of val_print_array_elements for GNAT-style packed arrays.
    Prints elements of packed array of type TYPE at bit offset
    BITOFFSET from VALADDR on STREAM.  Formats according to OPTIONS and
    separates with commas.  RECURSE is the recursion (nesting) level.
    TYPE must have been decoded (as by ada_coerce_to_simple_array).  */

static void
val_print_packed_array_elements (struct type *type, const gdb_byte *valaddr,
				 int bitoffset, struct ui_file *stream,
				 int recurse,
				 const struct value *val,
				 const struct value_print_options *options)
{
  unsigned int i;
  unsigned int things_printed = 0;
  unsigned len;
  struct type *elttype, *index_type;
  unsigned eltlen;
  unsigned long bitsize = TYPE_FIELD_BITSIZE (type, 0);
  struct value *mark = value_mark ();
  LONGEST low = 0;

  elttype = TYPE_TARGET_TYPE (type);
  eltlen = TYPE_LENGTH (check_typedef (elttype));
  index_type = TYPE_INDEX_TYPE (type);

  {
    LONGEST high;

    if (get_discrete_bounds (index_type, &low, &high) < 0)
      len = 1;
    else
      len = high - low + 1;
  }

  i = 0;
  annotate_array_section_begin (i, elttype);

  while (i < len && things_printed < options->print_max)
    {
      struct value *v0, *v1;
      int i0;

      if (i != 0)
	{
	  if (options->prettyprint_arrays)
	    {
	      fprintf_filtered (stream, ",\n");
	      print_spaces_filtered (2 + 2 * recurse, stream);
	    }
	  else
	    {
	      fprintf_filtered (stream, ", ");
	    }
	}
      wrap_here (n_spaces (2 + 2 * recurse));
      maybe_print_array_index (index_type, i + low, stream, options);

      i0 = i;
      v0 = ada_value_primitive_packed_val (NULL, valaddr,
					   (i0 * bitsize) / HOST_CHAR_BIT,
					   (i0 * bitsize) % HOST_CHAR_BIT,
					   bitsize, elttype);
      while (1)
	{
	  i += 1;
	  if (i >= len)
	    break;
	  v1 = ada_value_primitive_packed_val (NULL, valaddr,
					       (i * bitsize) / HOST_CHAR_BIT,
					       (i * bitsize) % HOST_CHAR_BIT,
					       bitsize, elttype);
	  if (memcmp (value_contents (v0), value_contents (v1), eltlen) != 0)
	    break;
	}

      if (i - i0 > options->repeat_count_threshold)
	{
	  struct value_print_options opts = *options;

	  opts.deref_ref = 0;
	  val_print (elttype, value_contents (v0), 0, 0, stream,
		     recurse + 1, val, &opts, current_language);
	  annotate_elt_rep (i - i0);
	  fprintf_filtered (stream, _(" <repeats %u times>"), i - i0);
	  annotate_elt_rep_end ();

	}
      else
	{
	  int j;
	  struct value_print_options opts = *options;

	  opts.deref_ref = 0;
	  for (j = i0; j < i; j += 1)
	    {
	      if (j > i0)
		{
		  if (options->prettyprint_arrays)
		    {
		      fprintf_filtered (stream, ",\n");
		      print_spaces_filtered (2 + 2 * recurse, stream);
		    }
		  else
		    {
		      fprintf_filtered (stream, ", ");
		    }
		  wrap_here (n_spaces (2 + 2 * recurse));
		  maybe_print_array_index (index_type, j + low,
					   stream, options);
		}
	      val_print (elttype, value_contents (v0), 0, 0, stream,
			 recurse + 1, val, &opts, current_language);
	      annotate_elt ();
	    }
	}
      things_printed += i - i0;
    }
  annotate_array_section_end ();
  if (i < len)
    {
      fprintf_filtered (stream, "...");
    }

  value_free_to_mark (mark);
}

static struct type *
printable_val_type (struct type *type, const gdb_byte *valaddr)
{
  return ada_to_fixed_type (ada_aligned_type (type), valaddr, 0, NULL, 1);
}

/* Print the character C on STREAM as part of the contents of a literal
   string whose delimiter is QUOTER.  TYPE_LEN is the length in bytes
   (1 or 2) of the character.  */

void
ada_emit_char (int c, struct type *type, struct ui_file *stream,
	       int quoter, int type_len)
{
  if (type_len != 2)
    type_len = 1;

  c &= (1 << (type_len * TARGET_CHAR_BIT)) - 1;

  if (isascii (c) && isprint (c))
    {
      if (c == quoter && c == '"')
	fprintf_filtered (stream, "\"\"");
      else
	fprintf_filtered (stream, "%c", c);
    }
  else
    fprintf_filtered (stream, "[\"%0*x\"]", type_len * 2, c);
}

/* Character #I of STRING, given that TYPE_LEN is the size in bytes (1
   or 2) of a character.  */

static int
char_at (const gdb_byte *string, int i, int type_len,
	 enum bfd_endian byte_order)
{
  if (type_len == 1)
    return string[i];
  else
    return (int) extract_unsigned_integer (string + 2 * i, 2, byte_order);
}

/* Wrapper around memcpy to make it legal argument to ui_file_put */
static void
ui_memcpy (void *dest, const char *buffer, long len)
{
  memcpy (dest, buffer, (size_t) len);
  ((char *) dest)[len] = '\0';
}

/* Print a floating-point value of type TYPE, pointed to in GDB by
   VALADDR, on STREAM.  Use Ada formatting conventions: there must be
   a decimal point, and at least one digit before and after the
   point.  We use GNAT format for NaNs and infinities.  */
static void
ada_print_floating (const gdb_byte *valaddr, struct type *type,
		    struct ui_file *stream)
{
  char buffer[64];
  char *s, *result;
  int len;
  struct ui_file *tmp_stream = mem_fileopen ();
  struct cleanup *cleanups = make_cleanup_ui_file_delete (tmp_stream);

  print_floating (valaddr, type, tmp_stream);
  ui_file_put (tmp_stream, ui_memcpy, buffer);
  do_cleanups (cleanups);

  result = buffer;
  len = strlen (result);

  /* Modify for Ada rules.  */

  s = strstr (result, "inf");
  if (s == NULL)
    s = strstr (result, "Inf");
  if (s == NULL)
    s = strstr (result, "INF");
  if (s != NULL)
    strcpy (s, "Inf");

  if (s == NULL)
    {
      s = strstr (result, "nan");
      if (s == NULL)
	s = strstr (result, "NaN");
      if (s == NULL)
	s = strstr (result, "Nan");
      if (s != NULL)
	{
	  s[0] = s[2] = 'N';
	  if (result[0] == '-')
	    result += 1;
	}
    }

  if (s == NULL && strchr (result, '.') == NULL)
    {
      s = strchr (result, 'e');
      if (s == NULL)
	fprintf_filtered (stream, "%s.0", result);
      else
	fprintf_filtered (stream, "%.*s.0%s", (int) (s-result), result, s);
      return;
    }
  fprintf_filtered (stream, "%s", result);
}

void
ada_printchar (int c, struct type *type, struct ui_file *stream)
{
  fputs_filtered ("'", stream);
  ada_emit_char (c, type, stream, '\'', 1);
  fputs_filtered ("'", stream);
}

/* [From print_type_scalar in typeprint.c].   Print VAL on STREAM in a
   form appropriate for TYPE, if non-NULL.  If TYPE is NULL, print VAL
   like a default signed integer.  */

void
ada_print_scalar (struct type *type, LONGEST val, struct ui_file *stream)
{
  unsigned int i;
  unsigned len;

  if (!type)
    {
      print_longest (stream, 'd', 0, val);
      return;
    }

  type = ada_check_typedef (type);

  switch (TYPE_CODE (type))
    {

    case TYPE_CODE_ENUM:
      len = TYPE_NFIELDS (type);
      for (i = 0; i < len; i++)
	{
	  if (TYPE_FIELD_BITPOS (type, i) == val)
	    {
	      break;
	    }
	}
      if (i < len)
	{
	  fputs_filtered (ada_enum_name (TYPE_FIELD_NAME (type, i)), stream);
	}
      else
	{
	  print_longest (stream, 'd', 0, val);
	}
      break;

    case TYPE_CODE_INT:
      print_longest (stream, TYPE_UNSIGNED (type) ? 'u' : 'd', 0, val);
      break;

    case TYPE_CODE_CHAR:
      LA_PRINT_CHAR ((unsigned char) val, type, stream);
      break;

    case TYPE_CODE_BOOL:
      fprintf_filtered (stream, val ? "true" : "false");
      break;

    case TYPE_CODE_RANGE:
      ada_print_scalar (TYPE_TARGET_TYPE (type), val, stream);
      return;

    case TYPE_CODE_UNDEF:
    case TYPE_CODE_PTR:
    case TYPE_CODE_ARRAY:
    case TYPE_CODE_STRUCT:
    case TYPE_CODE_UNION:
    case TYPE_CODE_FUNC:
    case TYPE_CODE_FLT:
    case TYPE_CODE_VOID:
    case TYPE_CODE_SET:
    case TYPE_CODE_STRING:
    case TYPE_CODE_ERROR:
    case TYPE_CODE_MEMBERPTR:
    case TYPE_CODE_METHODPTR:
    case TYPE_CODE_METHOD:
    case TYPE_CODE_REF:
      warning (_("internal error: unhandled type in ada_print_scalar"));
      break;

    default:
      error (_("Invalid type code in symbol table."));
    }
  gdb_flush (stream);
}

/* Print the character string STRING, printing at most LENGTH characters.
   Printing stops early if the number hits print_max; repeat counts
   are printed as appropriate.  Print ellipses at the end if we
   had to stop before printing LENGTH characters, or if
   FORCE_ELLIPSES.   TYPE_LEN is the length (1 or 2) of the character type.
 */

static void
printstr (struct ui_file *stream, struct type *elttype, const gdb_byte *string,
	  unsigned int length, int force_ellipses, int type_len,
	  const struct value_print_options *options)
{
  enum bfd_endian byte_order = gdbarch_byte_order (get_type_arch (elttype));
  unsigned int i;
  unsigned int things_printed = 0;
  int in_quotes = 0;
  int need_comma = 0;

  if (length == 0)
    {
      fputs_filtered ("\"\"", stream);
      return;
    }

  for (i = 0; i < length && things_printed < options->print_max; i += 1)
    {
      /* Position of the character we are examining
         to see whether it is repeated.  */
      unsigned int rep1;
      /* Number of repetitions we have detected so far.  */
      unsigned int reps;

      QUIT;

      if (need_comma)
	{
	  fputs_filtered (", ", stream);
	  need_comma = 0;
	}

      rep1 = i + 1;
      reps = 1;
      while (rep1 < length
	     && char_at (string, rep1, type_len, byte_order)
		== char_at (string, i, type_len, byte_order))
	{
	  rep1 += 1;
	  reps += 1;
	}

      if (reps > options->repeat_count_threshold)
	{
	  if (in_quotes)
	    {
	      if (options->inspect_it)
		fputs_filtered ("\\\", ", stream);
	      else
		fputs_filtered ("\", ", stream);
	      in_quotes = 0;
	    }
	  fputs_filtered ("'", stream);
	  ada_emit_char (char_at (string, i, type_len, byte_order),
			 elttype, stream, '\'', type_len);
	  fputs_filtered ("'", stream);
	  fprintf_filtered (stream, _(" <repeats %u times>"), reps);
	  i = rep1 - 1;
	  things_printed += options->repeat_count_threshold;
	  need_comma = 1;
	}
      else
	{
	  if (!in_quotes)
	    {
	      if (options->inspect_it)
		fputs_filtered ("\\\"", stream);
	      else
		fputs_filtered ("\"", stream);
	      in_quotes = 1;
	    }
	  ada_emit_char (char_at (string, i, type_len, byte_order),
			 elttype, stream, '"', type_len);
	  things_printed += 1;
	}
    }

  /* Terminate the quotes if necessary.  */
  if (in_quotes)
    {
      if (options->inspect_it)
	fputs_filtered ("\\\"", stream);
      else
	fputs_filtered ("\"", stream);
    }

  if (force_ellipses || i < length)
    fputs_filtered ("...", stream);
}

void
ada_printstr (struct ui_file *stream, struct type *type, const gdb_byte *string,
	      unsigned int length, const char *encoding, int force_ellipses,
	      const struct value_print_options *options)
{
  printstr (stream, type, string, length, force_ellipses, TYPE_LENGTH (type),
	    options);
}


/* Print data of type TYPE located at VALADDR (within GDB), which came from
   the inferior at address ADDRESS, onto stdio stream STREAM according to
   OPTIONS.  The data at VALADDR is in target byte order.

   If the data is printed as a string, returns the number of string characters
   printed.

   RECURSE indicates the amount of indentation to supply before
   continuation lines; this amount is roughly twice the value of RECURSE.  */

int
ada_val_print (struct type *type, const gdb_byte *valaddr0,
	       int embedded_offset, CORE_ADDR address,
	       struct ui_file *stream, int recurse,
	       const struct value *val,
	       const struct value_print_options *options)
{
  volatile struct gdb_exception except;
  int result = 0;

  TRY_CATCH (except, RETURN_MASK_ALL)
    {
      result = ada_val_print_1 (type, valaddr0, embedded_offset, address,
				stream, recurse, val, options);
    }

  if (except.reason < 0)
    result = 0;

  return result;
}

/* Assuming TYPE is a simple array, print the value of this array located
   at VALADDR.  See ada_val_print for a description of the various
   parameters of this function; they are identical.  The semantics
   of the return value is also identical to ada_val_print.  */

static int
ada_val_print_array (struct type *type, const gdb_byte *valaddr,
		     CORE_ADDR address, struct ui_file *stream, int recurse,
		     const struct value *val,
		     const struct value_print_options *options)
{
  enum bfd_endian byte_order = gdbarch_byte_order (get_type_arch (type));
  struct type *elttype = TYPE_TARGET_TYPE (type);
  unsigned int eltlen;
  unsigned int len;
  int result = 0;

  if (elttype == NULL)
    eltlen = 0;
  else
    eltlen = TYPE_LENGTH (elttype);
  if (eltlen == 0)
    len = 0;
  else
    len = TYPE_LENGTH (type) / eltlen;

  /* For an array of chars, print with string syntax.  */
  if (ada_is_string_type (type)
      && (options->format == 0 || options->format == 's'))
    {
      if (options->prettyprint_arrays)
        print_spaces_filtered (2 + 2 * recurse, stream);

      /* If requested, look for the first null char and only print
         elements up to it.  */
      if (options->stop_print_at_null)
        {
          int temp_len;

          /* Look for a NULL char.  */
          for (temp_len = 0;
               (temp_len < len
                && temp_len < options->print_max
                && char_at (valaddr, temp_len, eltlen, byte_order) != 0);
               temp_len += 1);
          len = temp_len;
        }

      printstr (stream, elttype, valaddr, len, 0, eltlen, options);
      result = len;
    }
  else
    {
      fprintf_filtered (stream, "(");
      print_optional_low_bound (stream, type, options);
      if (TYPE_FIELD_BITSIZE (type, 0) > 0)
        val_print_packed_array_elements (type, valaddr, 0, stream,
                                         recurse, val, options);
      else
        val_print_array_elements (type, valaddr, address, stream,
                                  recurse, val, options, 0);
      fprintf_filtered (stream, ")");
    }

  return result;
}

/* See the comment on ada_val_print.  This function differs in that it
   does not catch evaluation errors (leaving that to ada_val_print).  */

static int
ada_val_print_1 (struct type *type, const gdb_byte *valaddr0,
		 int embedded_offset, CORE_ADDR address,
		 struct ui_file *stream, int recurse,
		 const struct value *original_value,
		 const struct value_print_options *options)
{
  unsigned int len;
  int i;
  struct type *elttype;
  LONGEST val;
  const gdb_byte *valaddr = valaddr0 + embedded_offset;

  type = ada_check_typedef (type);

  if (ada_is_array_descriptor_type (type)
      || ada_is_constrained_packed_array_type (type))
    {
      int retn;
      struct value *mark = value_mark ();
      struct value *val;

      val = value_from_contents_and_address (type, valaddr, address);
      val = ada_coerce_to_simple_array_ptr (val);
      if (val == NULL)
	{
	  fprintf_filtered (stream, "(null)");
	  retn = 0;
	}
      else
	retn = ada_val_print_1 (value_type (val), value_contents (val), 0,
				value_address (val), stream, recurse,
				NULL, options);
      value_free_to_mark (mark);
      return retn;
    }

  valaddr = ada_aligned_value_addr (type, valaddr);
  embedded_offset -= valaddr - valaddr0 - embedded_offset;
  type = printable_val_type (type, valaddr);

  switch (TYPE_CODE (type))
    {
    default:
      return c_val_print (type, valaddr0, embedded_offset, address, stream,
			  recurse, original_value, options);

    case TYPE_CODE_PTR:
      {
	int ret = c_val_print (type, valaddr0, embedded_offset, address, 
			       stream, recurse, original_value, options);

	if (ada_is_tag_type (type))
	  {
	    struct value *val = 
	      value_from_contents_and_address (type, valaddr, address);
	    const char *name = ada_tag_name (val);

	    if (name != NULL) 
	      fprintf_filtered (stream, " (%s)", name);
	    return 0;
	}
	return ret;
      }

    case TYPE_CODE_INT:
    case TYPE_CODE_RANGE:
      if (ada_is_fixed_point_type (type))
	{
	  LONGEST v = unpack_long (type, valaddr);
	  int len = TYPE_LENGTH (type);

	  fprintf_filtered (stream, len < 4 ? "%.11g" : "%.17g",
			    (double) ada_fixed_to_float (type, v));
	  return 0;
	}
      else if (TYPE_CODE (type) == TYPE_CODE_RANGE)
	{
	  struct type *target_type = TYPE_TARGET_TYPE (type);

	  if (TYPE_LENGTH (type) != TYPE_LENGTH (target_type))
	    {
	      /* Obscure case of range type that has different length from
	         its base type.  Perform a conversion, or we will get a
	         nonsense value.  Actually, we could use the same
	         code regardless of lengths; I'm just avoiding a cast.  */
	      struct value *v = value_cast (target_type,
					    value_from_contents_and_address
					    (type, valaddr, 0));

	      return ada_val_print_1 (target_type, value_contents (v), 0, 0,
				      stream, recurse + 1, NULL, options);
	    }
	  else
	    return ada_val_print_1 (TYPE_TARGET_TYPE (type),
				    valaddr0, embedded_offset,
				    address, stream, recurse, original_value, options);
	}
      else
	{
	  int format = (options->format ? options->format
			: options->output_format);

	  if (format)
	    {
	      struct value_print_options opts = *options;

	      opts.format = format;
	      print_scalar_formatted (valaddr, type, &opts, 0, stream);
	    }
          else if (ada_is_system_address_type (type))
            {
              /* FIXME: We want to print System.Address variables using
                 the same format as for any access type.  But for some
                 reason GNAT encodes the System.Address type as an int,
                 so we have to work-around this deficiency by handling
                 System.Address values as a special case.  */

	      struct gdbarch *gdbarch = get_type_arch (type);
	      struct type *ptr_type = builtin_type (gdbarch)->builtin_data_ptr;
	      CORE_ADDR addr = extract_typed_address (valaddr, ptr_type);

              fprintf_filtered (stream, "(");
              type_print (type, "", stream, -1);
              fprintf_filtered (stream, ") ");
	      fputs_filtered (paddress (gdbarch, addr), stream);
            }
	  else
	    {
	      val_print_type_code_int (type, valaddr, stream);
	      if (ada_is_character_type (type))
		{
		  fputs_filtered (" ", stream);
		  ada_printchar ((unsigned char) unpack_long (type, valaddr),
				 type, stream);
		}
	    }
	  return 0;
	}

    case TYPE_CODE_ENUM:
      if (options->format)
	{
	  print_scalar_formatted (valaddr, type, options, 0, stream);
	  break;
	}
      len = TYPE_NFIELDS (type);
      val = unpack_long (type, valaddr);
      for (i = 0; i < len; i++)
	{
	  QUIT;
	  if (val == TYPE_FIELD_BITPOS (type, i))
	    {
	      break;
	    }
	}
      if (i < len)
	{
	  const char *name = ada_enum_name (TYPE_FIELD_NAME (type, i));

	  if (name[0] == '\'')
	    fprintf_filtered (stream, "%ld %s", (long) val, name);
	  else
	    fputs_filtered (name, stream);
	}
      else
	{
	  print_longest (stream, 'd', 0, val);
	}
      break;

    case TYPE_CODE_FLAGS:
      if (options->format)
	print_scalar_formatted (valaddr, type, options, 0, stream);
      else
	val_print_type_code_flags (type, valaddr, stream);
      break;

    case TYPE_CODE_FLT:
      if (options->format)
	return c_val_print (type, valaddr0, embedded_offset, address, stream,
			    recurse, original_value, options);
      else
	ada_print_floating (valaddr0 + embedded_offset, type, stream);
      break;

    case TYPE_CODE_UNION:
    case TYPE_CODE_STRUCT:
      if (ada_is_bogus_array_descriptor (type))
	{
	  fprintf_filtered (stream, "(...?)");
	  return 0;
	}
      else
	{
	  print_record (type, valaddr, stream, recurse, original_value,
			options);
	  return 0;
	}

    case TYPE_CODE_ARRAY:
      return ada_val_print_array (type, valaddr, address, stream,
				  recurse, original_value, options);

    case TYPE_CODE_REF:
      /* For references, the debugger is expected to print the value as
         an address if DEREF_REF is null.  But printing an address in place
         of the object value would be confusing to an Ada programmer.
         So, for Ada values, we print the actual dereferenced value
         regardless.  */
      elttype = check_typedef (TYPE_TARGET_TYPE (type));
      
      if (TYPE_CODE (elttype) != TYPE_CODE_UNDEF)
        {
          LONGEST deref_val_int = (LONGEST) unpack_pointer (type, valaddr);

          if (deref_val_int != 0)
            {
              struct value *deref_val =
                ada_value_ind (value_from_longest
                               (lookup_pointer_type (elttype),
                                deref_val_int));

              val_print (value_type (deref_val),
                         value_contents (deref_val), 0,
                         value_address (deref_val), stream, recurse + 1,
			 original_value, options, current_language);
            }
          else
            fputs_filtered ("(null)", stream);
        }
      else
        fputs_filtered ("???", stream);

      break;
    }
  gdb_flush (stream);
  return 0;
}

static int
print_variant_part (struct type *type, int field_num, const gdb_byte *valaddr,
		    struct ui_file *stream, int recurse,
		    const struct value *val,
		    const struct value_print_options *options, int comma_needed,
		    struct type *outer_type, const gdb_byte *outer_valaddr)
{
  struct type *var_type = TYPE_FIELD_TYPE (type, field_num);
  int which = ada_which_variant_applies (var_type, outer_type, outer_valaddr);

  if (which < 0)
    return 0;
  else
    return print_field_values
      (TYPE_FIELD_TYPE (var_type, which),
       valaddr + TYPE_FIELD_BITPOS (type, field_num) / HOST_CHAR_BIT
       + TYPE_FIELD_BITPOS (var_type, which) / HOST_CHAR_BIT,
       stream, recurse, val, options,
       comma_needed, outer_type, outer_valaddr);
}

int
ada_value_print (struct value *val0, struct ui_file *stream,
		 const struct value_print_options *options)
{
  struct value *val = ada_to_fixed_value (val0);
  CORE_ADDR address = value_address (val);
  struct type *type = value_type (val);
  struct value_print_options opts;

  /* If it is a pointer, indicate what it points to.  */
  if (TYPE_CODE (type) == TYPE_CODE_PTR)
    {
      /* Hack:  don't print (char *) for char strings.  Their
         type is indicated by the quoted string anyway.  */
      if (TYPE_LENGTH (TYPE_TARGET_TYPE (type)) != sizeof (char)
	  || TYPE_CODE (TYPE_TARGET_TYPE (type)) != TYPE_CODE_INT 
	  || TYPE_UNSIGNED (TYPE_TARGET_TYPE (type)))
	{
	  fprintf_filtered (stream, "(");
	  type_print (type, "", stream, -1);
	  fprintf_filtered (stream, ") ");
	}
    }
  else if (ada_is_array_descriptor_type (type))
    {
      fprintf_filtered (stream, "(");
      type_print (type, "", stream, -1);
      fprintf_filtered (stream, ") ");
    }
  else if (ada_is_bogus_array_descriptor (type))
    {
      fprintf_filtered (stream, "(");
      type_print (type, "", stream, -1);
      fprintf_filtered (stream, ") (...?)");
      return 0;
    }

  opts = *options;
  opts.deref_ref = 1;
  return (val_print (type, value_contents (val), 0, address,
		     stream, 0, val, &opts, current_language));
}

static void
print_record (struct type *type, const gdb_byte *valaddr,
	      struct ui_file *stream, int recurse,
	      const struct value *val,
	      const struct value_print_options *options)
{
  type = ada_check_typedef (type);

  fprintf_filtered (stream, "(");

  if (print_field_values (type, valaddr, stream, recurse, val, options,
			  0, type, valaddr) != 0 && options->pretty)
    {
      fprintf_filtered (stream, "\n");
      print_spaces_filtered (2 * recurse, stream);
    }

  fprintf_filtered (stream, ")");
}

/* Print out fields of value at VALADDR having structure type TYPE.

   TYPE, VALADDR, STREAM, RECURSE, and OPTIONS have the
   same meanings as in ada_print_value and ada_val_print.

   OUTER_TYPE and OUTER_VALADDR give type and address of enclosing record
   (used to get discriminant values when printing variant parts).

   COMMA_NEEDED is 1 if fields have been printed at the current recursion
   level, so that a comma is needed before any field printed by this
   call.

   Returns 1 if COMMA_NEEDED or any fields were printed.  */

static int
print_field_values (struct type *type, const gdb_byte *valaddr,
		    struct ui_file *stream, int recurse,
		    const struct value *val,
		    const struct value_print_options *options,
		    int comma_needed,
		    struct type *outer_type, const gdb_byte *outer_valaddr)
{
  int i, len;

  len = TYPE_NFIELDS (type);

  for (i = 0; i < len; i += 1)
    {
      if (ada_is_ignored_field (type, i))
	continue;

      if (ada_is_wrapper_field (type, i))
	{
	  comma_needed =
	    print_field_values (TYPE_FIELD_TYPE (type, i),
				valaddr
				+ TYPE_FIELD_BITPOS (type, i) / HOST_CHAR_BIT,
				stream, recurse, val, options,
				comma_needed, type, valaddr);
	  continue;
	}
      else if (ada_is_variant_part (type, i))
	{
	  comma_needed =
	    print_variant_part (type, i, valaddr,
				stream, recurse, val, options, comma_needed,
				outer_type, outer_valaddr);
	  continue;
	}

      if (comma_needed)
	fprintf_filtered (stream, ", ");
      comma_needed = 1;

      if (options->pretty)
	{
	  fprintf_filtered (stream, "\n");
	  print_spaces_filtered (2 + 2 * recurse, stream);
	}
      else
	{
	  wrap_here (n_spaces (2 + 2 * recurse));
	}
      if (options->inspect_it)
	{
	  if (TYPE_CODE (TYPE_FIELD_TYPE (type, i)) == TYPE_CODE_PTR)
	    fputs_filtered ("\"( ptr \"", stream);
	  else
	    fputs_filtered ("\"( nodef \"", stream);
	  fprintf_symbol_filtered (stream, TYPE_FIELD_NAME (type, i),
				   language_cplus, DMGL_NO_OPTS);
	  fputs_filtered ("\" \"", stream);
	  fprintf_symbol_filtered (stream, TYPE_FIELD_NAME (type, i),
				   language_cplus, DMGL_NO_OPTS);
	  fputs_filtered ("\") \"", stream);
	}
      else
	{
	  annotate_field_begin (TYPE_FIELD_TYPE (type, i));
	  fprintf_filtered (stream, "%.*s",
			    ada_name_prefix_len (TYPE_FIELD_NAME (type, i)),
			    TYPE_FIELD_NAME (type, i));
	  annotate_field_name_end ();
	  fputs_filtered (" => ", stream);
	  annotate_field_value ();
	}

      if (TYPE_FIELD_PACKED (type, i))
	{
	  struct value *v;

	  /* Bitfields require special handling, especially due to byte
	     order problems.  */
	  if (HAVE_CPLUS_STRUCT (type) && TYPE_FIELD_IGNORE (type, i))
	    {
	      fputs_filtered (_("<optimized out or zero length>"), stream);
	    }
	  else
	    {
	      int bit_pos = TYPE_FIELD_BITPOS (type, i);
	      int bit_size = TYPE_FIELD_BITSIZE (type, i);
	      struct value_print_options opts;

	      adjust_type_signedness (TYPE_FIELD_TYPE (type, i));
	      v = ada_value_primitive_packed_val (NULL, valaddr,
						  bit_pos / HOST_CHAR_BIT,
						  bit_pos % HOST_CHAR_BIT,
						  bit_size,
						  TYPE_FIELD_TYPE (type, i));
	      opts = *options;
	      opts.deref_ref = 0;
	      val_print (TYPE_FIELD_TYPE (type, i), value_contents (v), 0, 0,
			 stream, recurse + 1, v,
			 &opts, current_language);
	    }
	}
      else
	{
	  struct value_print_options opts = *options;

	  opts.deref_ref = 0;
	  ada_val_print (TYPE_FIELD_TYPE (type, i),
			 valaddr + TYPE_FIELD_BITPOS (type, i) / HOST_CHAR_BIT,
			 0, 0, stream, recurse + 1, val, &opts);
	}
      annotate_field_end ();
    }

  return comma_needed;
}
