/* Ada language support routines for GDB, the GNU debugger.

   Copyright (C) 1992-2021 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_regex.h"
#include "frame.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "gdbcmd.h"
#include "expression.h"
#include "parser-defs.h"
#include "language.h"
#include "varobj.h"
#include "inferior.h"
#include "symfile.h"
#include "objfiles.h"
#include "breakpoint.h"
#include "gdbcore.h"
#include "hashtab.h"
#include "gdb_obstack.h"
#include "ada-lang.h"
#include "completer.h"
#include "ui-out.h"
#include "block.h"
#include "infcall.h"
#include "annotate.h"
#include "valprint.h"
#include "source.h"
#include "observable.h"
#include "stack.h"
#include "typeprint.h"
#include "namespace.h"
#include "cli/cli-style.h"
#include "cli/cli-decode.h"

#include "value.h"
#include "mi/mi-common.h"
#include "arch-utils.h"
#include "cli/cli-utils.h"
#include "gdbsupport/function-view.h"
#include "gdbsupport/byte-vector.h"
#include <algorithm>
#include "ada-exp.h"

/* Define whether or not the C operator '/' truncates towards zero for
   differently signed operands (truncation direction is undefined in C).
   Copied from valarith.c.  */

#ifndef TRUNCATION_TOWARDS_ZERO
#define TRUNCATION_TOWARDS_ZERO ((-5 / 2) == -2)
#endif

static struct type *desc_base_type (struct type *);

static struct type *desc_bounds_type (struct type *);

static struct value *desc_bounds (struct value *);

static int fat_pntr_bounds_bitpos (struct type *);

static int fat_pntr_bounds_bitsize (struct type *);

static struct type *desc_data_target_type (struct type *);

static struct value *desc_data (struct value *);

static int fat_pntr_data_bitpos (struct type *);

static int fat_pntr_data_bitsize (struct type *);

static struct value *desc_one_bound (struct value *, int, int);

static int desc_bound_bitpos (struct type *, int, int);

static int desc_bound_bitsize (struct type *, int, int);

static struct type *desc_index_type (struct type *, int);

static int desc_arity (struct type *);

static int ada_args_match (struct symbol *, struct value **, int);

static struct value *make_array_descriptor (struct type *, struct value *);

static void ada_add_block_symbols (std::vector<struct block_symbol> &,
				   const struct block *,
				   const lookup_name_info &lookup_name,
				   domain_enum, struct objfile *);

static void ada_add_all_symbols (std::vector<struct block_symbol> &,
				 const struct block *,
				 const lookup_name_info &lookup_name,
				 domain_enum, int, int *);

static int is_nonfunction (const std::vector<struct block_symbol> &);

static void add_defn_to_vec (std::vector<struct block_symbol> &,
			     struct symbol *,
			     const struct block *);

static int possible_user_operator_p (enum exp_opcode, struct value **);

static const char *ada_decoded_op_name (enum exp_opcode);

static int numeric_type_p (struct type *);

static int integer_type_p (struct type *);

static int scalar_type_p (struct type *);

static int discrete_type_p (struct type *);

static struct type *ada_lookup_struct_elt_type (struct type *, const char *,
						int, int);

static struct type *ada_find_parallel_type_with_name (struct type *,
						      const char *);

static int is_dynamic_field (struct type *, int);

static struct type *to_fixed_variant_branch_type (struct type *,
						  const gdb_byte *,
						  CORE_ADDR, struct value *);

static struct type *to_fixed_array_type (struct type *, struct value *, int);

static struct type *to_fixed_range_type (struct type *, struct value *);

static struct type *to_static_fixed_type (struct type *);
static struct type *static_unwrap_type (struct type *type);

static struct value *unwrap_value (struct value *);

static struct type *constrained_packed_array_type (struct type *, long *);

static struct type *decode_constrained_packed_array_type (struct type *);

static long decode_packed_array_bitsize (struct type *);

static struct value *decode_constrained_packed_array (struct value *);

static int ada_is_unconstrained_packed_array_type (struct type *);

static struct value *value_subscript_packed (struct value *, int,
					     struct value **);

static struct value *coerce_unspec_val_to_type (struct value *,
						struct type *);

static int lesseq_defined_than (struct symbol *, struct symbol *);

static int equiv_types (struct type *, struct type *);

static int is_name_suffix (const char *);

static int advance_wild_match (const char **, const char *, char);

static bool wild_match (const char *name, const char *patn);

static struct value *ada_coerce_ref (struct value *);

static LONGEST pos_atr (struct value *);

static struct value *val_atr (struct type *, LONGEST);

static struct symbol *standard_lookup (const char *, const struct block *,
				       domain_enum);

static struct value *ada_search_struct_field (const char *, struct value *, int,
					      struct type *);

static int find_struct_field (const char *, struct type *, int,
			      struct type **, int *, int *, int *, int *);

static int ada_resolve_function (std::vector<struct block_symbol> &,
				 struct value **, int, const char *,
				 struct type *, bool);

static int ada_is_direct_array_type (struct type *);

static struct value *ada_index_struct_field (int, struct value *, int,
					     struct type *);

static void add_component_interval (LONGEST, LONGEST, std::vector<LONGEST> &);


static struct type *ada_find_any_type (const char *name);

static symbol_name_matcher_ftype *ada_get_symbol_name_matcher
  (const lookup_name_info &lookup_name);



/* The result of a symbol lookup to be stored in our symbol cache.  */

struct cache_entry
{
  /* The name used to perform the lookup.  */
  const char *name;
  /* The namespace used during the lookup.  */
  domain_enum domain;
  /* The symbol returned by the lookup, or NULL if no matching symbol
     was found.  */
  struct symbol *sym;
  /* The block where the symbol was found, or NULL if no matching
     symbol was found.  */
  const struct block *block;
  /* A pointer to the next entry with the same hash.  */
  struct cache_entry *next;
};

/* The Ada symbol cache, used to store the result of Ada-mode symbol
   lookups in the course of executing the user's commands.

   The cache is implemented using a simple, fixed-sized hash.
   The size is fixed on the grounds that there are not likely to be
   all that many symbols looked up during any given session, regardless
   of the size of the symbol table.  If we decide to go to a resizable
   table, let's just use the stuff from libiberty instead.  */

#define HASH_SIZE 1009

struct ada_symbol_cache
{
  /* An obstack used to store the entries in our cache.  */
  struct auto_obstack cache_space;

  /* The root of the hash table used to implement our symbol cache.  */
  struct cache_entry *root[HASH_SIZE] {};
};

/* Maximum-sized dynamic type.  */
static unsigned int varsize_limit;

static const char ada_completer_word_break_characters[] =
#ifdef VMS
  " \t\n!@#%^&*()+=|~`}{[]\";:?/,-";
#else
  " \t\n!@#$%^&*()+=|~`}{[]\";:?/,-";
#endif

/* The name of the symbol to use to get the name of the main subprogram.  */
static const char ADA_MAIN_PROGRAM_SYMBOL_NAME[]
  = "__gnat_ada_main_program_name";

/* Limit on the number of warnings to raise per expression evaluation.  */
static int warning_limit = 2;

/* Number of warning messages issued; reset to 0 by cleanups after
   expression evaluation.  */
static int warnings_issued = 0;

static const char * const known_runtime_file_name_patterns[] = {
  ADA_KNOWN_RUNTIME_FILE_NAME_PATTERNS NULL
};

static const char * const known_auxiliary_function_name_patterns[] = {
  ADA_KNOWN_AUXILIARY_FUNCTION_NAME_PATTERNS NULL
};

/* Maintenance-related settings for this module.  */

static struct cmd_list_element *maint_set_ada_cmdlist;
static struct cmd_list_element *maint_show_ada_cmdlist;

/* The "maintenance ada set/show ignore-descriptive-type" value.  */

static bool ada_ignore_descriptive_types_p = false;

			/* Inferior-specific data.  */

/* Per-inferior data for this module.  */

struct ada_inferior_data
{
  /* The ada__tags__type_specific_data type, which is used when decoding
     tagged types.  With older versions of GNAT, this type was directly
     accessible through a component ("tsd") in the object tag.  But this
     is no longer the case, so we cache it for each inferior.  */
  struct type *tsd_type = nullptr;

  /* The exception_support_info data.  This data is used to determine
     how to implement support for Ada exception catchpoints in a given
     inferior.  */
  const struct exception_support_info *exception_info = nullptr;
};

/* Our key to this module's inferior data.  */
static const struct inferior_key<ada_inferior_data> ada_inferior_data;

/* Return our inferior data for the given inferior (INF).

   This function always returns a valid pointer to an allocated
   ada_inferior_data structure.  If INF's inferior data has not
   been previously set, this functions creates a new one with all
   fields set to zero, sets INF's inferior to it, and then returns
   a pointer to that newly allocated ada_inferior_data.  */

static struct ada_inferior_data *
get_ada_inferior_data (struct inferior *inf)
{
  struct ada_inferior_data *data;

  data = ada_inferior_data.get (inf);
  if (data == NULL)
    data = ada_inferior_data.emplace (inf);

  return data;
}

/* Perform all necessary cleanups regarding our module's inferior data
   that is required after the inferior INF just exited.  */

static void
ada_inferior_exit (struct inferior *inf)
{
  ada_inferior_data.clear (inf);
}


			/* program-space-specific data.  */

/* This module's per-program-space data.  */
struct ada_pspace_data
{
  /* The Ada symbol cache.  */
  std::unique_ptr<ada_symbol_cache> sym_cache;
};

/* Key to our per-program-space data.  */
static const struct program_space_key<ada_pspace_data> ada_pspace_data_handle;

/* Return this module's data for the given program space (PSPACE).
   If not is found, add a zero'ed one now.

   This function always returns a valid object.  */

static struct ada_pspace_data *
get_ada_pspace_data (struct program_space *pspace)
{
  struct ada_pspace_data *data;

  data = ada_pspace_data_handle.get (pspace);
  if (data == NULL)
    data = ada_pspace_data_handle.emplace (pspace);

  return data;
}

			/* Utilities */

/* If TYPE is a TYPE_CODE_TYPEDEF type, return the target type after
   all typedef layers have been peeled.  Otherwise, return TYPE.

   Normally, we really expect a typedef type to only have 1 typedef layer.
   In other words, we really expect the target type of a typedef type to be
   a non-typedef type.  This is particularly true for Ada units, because
   the language does not have a typedef vs not-typedef distinction.
   In that respect, the Ada compiler has been trying to eliminate as many
   typedef definitions in the debugging information, since they generally
   do not bring any extra information (we still use typedef under certain
   circumstances related mostly to the GNAT encoding).

   Unfortunately, we have seen situations where the debugging information
   generated by the compiler leads to such multiple typedef layers.  For
   instance, consider the following example with stabs:

     .stabs  "pck__float_array___XUP:Tt(0,46)=s16P_ARRAY:(0,47)=[...]"[...]
     .stabs  "pck__float_array___XUP:t(0,36)=(0,46)",128,0,6,0

   This is an error in the debugging information which causes type
   pck__float_array___XUP to be defined twice, and the second time,
   it is defined as a typedef of a typedef.

   This is on the fringe of legality as far as debugging information is
   concerned, and certainly unexpected.  But it is easy to handle these
   situations correctly, so we can afford to be lenient in this case.  */

static struct type *
ada_typedef_target_type (struct type *type)
{
  while (type->code () == TYPE_CODE_TYPEDEF)
    type = TYPE_TARGET_TYPE (type);
  return type;
}

/* Given DECODED_NAME a string holding a symbol name in its
   decoded form (ie using the Ada dotted notation), returns
   its unqualified name.  */

static const char *
ada_unqualified_name (const char *decoded_name)
{
  const char *result;
  
  /* If the decoded name starts with '<', it means that the encoded
     name does not follow standard naming conventions, and thus that
     it is not your typical Ada symbol name.  Trying to unqualify it
     is therefore pointless and possibly erroneous.  */
  if (decoded_name[0] == '<')
    return decoded_name;

  result = strrchr (decoded_name, '.');
  if (result != NULL)
    result++;                   /* Skip the dot...  */
  else
    result = decoded_name;

  return result;
}

/* Return a string starting with '<', followed by STR, and '>'.  */

static std::string
add_angle_brackets (const char *str)
{
  return string_printf ("<%s>", str);
}

/* True (non-zero) iff TARGET matches FIELD_NAME up to any trailing
   suffix of FIELD_NAME beginning "___".  */

static int
field_name_match (const char *field_name, const char *target)
{
  int len = strlen (target);

  return
    (strncmp (field_name, target, len) == 0
     && (field_name[len] == '\0'
	 || (startswith (field_name + len, "___")
	     && strcmp (field_name + strlen (field_name) - 6,
			"___XVN") != 0)));
}


/* Assuming TYPE is a TYPE_CODE_STRUCT or a TYPE_CODE_TYPDEF to
   a TYPE_CODE_STRUCT, find the field whose name matches FIELD_NAME,
   and return its index.  This function also handles fields whose name
   have ___ suffixes because the compiler sometimes alters their name
   by adding such a suffix to represent fields with certain constraints.
   If the field could not be found, return a negative number if
   MAYBE_MISSING is set.  Otherwise raise an error.  */

int
ada_get_field_index (const struct type *type, const char *field_name,
		     int maybe_missing)
{
  int fieldno;
  struct type *struct_type = check_typedef ((struct type *) type);

  for (fieldno = 0; fieldno < struct_type->num_fields (); fieldno++)
    if (field_name_match (TYPE_FIELD_NAME (struct_type, fieldno), field_name))
      return fieldno;

  if (!maybe_missing)
    error (_("Unable to find field %s in struct %s.  Aborting"),
	   field_name, struct_type->name ());

  return -1;
}

/* The length of the prefix of NAME prior to any "___" suffix.  */

int
ada_name_prefix_len (const char *name)
{
  if (name == NULL)
    return 0;
  else
    {
      const char *p = strstr (name, "___");

      if (p == NULL)
	return strlen (name);
      else
	return p - name;
    }
}

/* Return non-zero if SUFFIX is a suffix of STR.
   Return zero if STR is null.  */

static int
is_suffix (const char *str, const char *suffix)
{
  int len1, len2;

  if (str == NULL)
    return 0;
  len1 = strlen (str);
  len2 = strlen (suffix);
  return (len1 >= len2 && strcmp (str + len1 - len2, suffix) == 0);
}

/* The contents of value VAL, treated as a value of type TYPE.  The
   result is an lval in memory if VAL is.  */

static struct value *
coerce_unspec_val_to_type (struct value *val, struct type *type)
{
  type = ada_check_typedef (type);
  if (value_type (val) == type)
    return val;
  else
    {
      struct value *result;

      /* Make sure that the object size is not unreasonable before
	 trying to allocate some memory for it.  */
      ada_ensure_varsize_limit (type);

      if (value_optimized_out (val))
	result = allocate_optimized_out_value (type);
      else if (value_lazy (val)
	       /* Be careful not to make a lazy not_lval value.  */
	       || (VALUE_LVAL (val) != not_lval
		   && TYPE_LENGTH (type) > TYPE_LENGTH (value_type (val))))
	result = allocate_value_lazy (type);
      else
	{
	  result = allocate_value (type);
	  value_contents_copy (result, 0, val, 0, TYPE_LENGTH (type));
	}
      set_value_component_location (result, val);
      set_value_bitsize (result, value_bitsize (val));
      set_value_bitpos (result, value_bitpos (val));
      if (VALUE_LVAL (result) == lval_memory)
	set_value_address (result, value_address (val));
      return result;
    }
}

static const gdb_byte *
cond_offset_host (const gdb_byte *valaddr, long offset)
{
  if (valaddr == NULL)
    return NULL;
  else
    return valaddr + offset;
}

static CORE_ADDR
cond_offset_target (CORE_ADDR address, long offset)
{
  if (address == 0)
    return 0;
  else
    return address + offset;
}

/* Issue a warning (as for the definition of warning in utils.c, but
   with exactly one argument rather than ...), unless the limit on the
   number of warnings has passed during the evaluation of the current
   expression.  */

/* FIXME: cagney/2004-10-10: This function is mimicking the behavior
   provided by "complaint".  */
static void lim_warning (const char *format, ...) ATTRIBUTE_PRINTF (1, 2);

static void
lim_warning (const char *format, ...)
{
  va_list args;

  va_start (args, format);
  warnings_issued += 1;
  if (warnings_issued <= warning_limit)
    vwarning (format, args);

  va_end (args);
}

/* Issue an error if the size of an object of type T is unreasonable,
   i.e. if it would be a bad idea to allocate a value of this type in
   GDB.  */

void
ada_ensure_varsize_limit (const struct type *type)
{
  if (TYPE_LENGTH (type) > varsize_limit)
    error (_("object size is larger than varsize-limit"));
}

/* Maximum value of a SIZE-byte signed integer type.  */
static LONGEST
max_of_size (int size)
{
  LONGEST top_bit = (LONGEST) 1 << (size * 8 - 2);

  return top_bit | (top_bit - 1);
}

/* Minimum value of a SIZE-byte signed integer type.  */
static LONGEST
min_of_size (int size)
{
  return -max_of_size (size) - 1;
}

/* Maximum value of a SIZE-byte unsigned integer type.  */
static ULONGEST
umax_of_size (int size)
{
  ULONGEST top_bit = (ULONGEST) 1 << (size * 8 - 1);

  return top_bit | (top_bit - 1);
}

/* Maximum value of integral type T, as a signed quantity.  */
static LONGEST
max_of_type (struct type *t)
{
  if (t->is_unsigned ())
    return (LONGEST) umax_of_size (TYPE_LENGTH (t));
  else
    return max_of_size (TYPE_LENGTH (t));
}

/* Minimum value of integral type T, as a signed quantity.  */
static LONGEST
min_of_type (struct type *t)
{
  if (t->is_unsigned ())
    return 0;
  else
    return min_of_size (TYPE_LENGTH (t));
}

/* The largest value in the domain of TYPE, a discrete type, as an integer.  */
LONGEST
ada_discrete_type_high_bound (struct type *type)
{
  type = resolve_dynamic_type (type, {}, 0);
  switch (type->code ())
    {
    case TYPE_CODE_RANGE:
      {
	const dynamic_prop &high = type->bounds ()->high;

	if (high.kind () == PROP_CONST)
	  return high.const_val ();
	else
	  {
	    gdb_assert (high.kind () == PROP_UNDEFINED);

	    /* This happens when trying to evaluate a type's dynamic bound
	       without a live target.  There is nothing relevant for us to
	       return here, so return 0.  */
	    return 0;
	  }
      }
    case TYPE_CODE_ENUM:
      return TYPE_FIELD_ENUMVAL (type, type->num_fields () - 1);
    case TYPE_CODE_BOOL:
      return 1;
    case TYPE_CODE_CHAR:
    case TYPE_CODE_INT:
      return max_of_type (type);
    default:
      error (_("Unexpected type in ada_discrete_type_high_bound."));
    }
}

/* The smallest value in the domain of TYPE, a discrete type, as an integer.  */
LONGEST
ada_discrete_type_low_bound (struct type *type)
{
  type = resolve_dynamic_type (type, {}, 0);
  switch (type->code ())
    {
    case TYPE_CODE_RANGE:
      {
	const dynamic_prop &low = type->bounds ()->low;

	if (low.kind () == PROP_CONST)
	  return low.const_val ();
	else
	  {
	    gdb_assert (low.kind () == PROP_UNDEFINED);

	    /* This happens when trying to evaluate a type's dynamic bound
	       without a live target.  There is nothing relevant for us to
	       return here, so return 0.  */
	    return 0;
	  }
      }
    case TYPE_CODE_ENUM:
      return TYPE_FIELD_ENUMVAL (type, 0);
    case TYPE_CODE_BOOL:
      return 0;
    case TYPE_CODE_CHAR:
    case TYPE_CODE_INT:
      return min_of_type (type);
    default:
      error (_("Unexpected type in ada_discrete_type_low_bound."));
    }
}

/* The identity on non-range types.  For range types, the underlying
   non-range scalar type.  */

static struct type *
get_base_type (struct type *type)
{
  while (type != NULL && type->code () == TYPE_CODE_RANGE)
    {
      if (type == TYPE_TARGET_TYPE (type) || TYPE_TARGET_TYPE (type) == NULL)
	return type;
      type = TYPE_TARGET_TYPE (type);
    }
  return type;
}

/* Return a decoded version of the given VALUE.  This means returning
   a value whose type is obtained by applying all the GNAT-specific
   encodings, making the resulting type a static but standard description
   of the initial type.  */

struct value *
ada_get_decoded_value (struct value *value)
{
  struct type *type = ada_check_typedef (value_type (value));

  if (ada_is_array_descriptor_type (type)
      || (ada_is_constrained_packed_array_type (type)
	  && type->code () != TYPE_CODE_PTR))
    {
      if (type->code () == TYPE_CODE_TYPEDEF)  /* array access type.  */
	value = ada_coerce_to_simple_array_ptr (value);
      else
	value = ada_coerce_to_simple_array (value);
    }
  else
    value = ada_to_fixed_value (value);

  return value;
}

/* Same as ada_get_decoded_value, but with the given TYPE.
   Because there is no associated actual value for this type,
   the resulting type might be a best-effort approximation in
   the case of dynamic types.  */

struct type *
ada_get_decoded_type (struct type *type)
{
  type = to_static_fixed_type (type);
  if (ada_is_constrained_packed_array_type (type))
    type = ada_coerce_to_simple_array_type (type);
  return type;
}



				/* Language Selection */

/* If the main program is in Ada, return language_ada, otherwise return LANG
   (the main program is in Ada iif the adainit symbol is found).  */

static enum language
ada_update_initial_language (enum language lang)
{
  if (lookup_minimal_symbol ("adainit", NULL, NULL).minsym != NULL)
    return language_ada;

  return lang;
}

/* If the main procedure is written in Ada, then return its name.
   The result is good until the next call.  Return NULL if the main
   procedure doesn't appear to be in Ada.  */

char *
ada_main_name (void)
{
  struct bound_minimal_symbol msym;
  static gdb::unique_xmalloc_ptr<char> main_program_name;

  /* For Ada, the name of the main procedure is stored in a specific
     string constant, generated by the binder.  Look for that symbol,
     extract its address, and then read that string.  If we didn't find
     that string, then most probably the main procedure is not written
     in Ada.  */
  msym = lookup_minimal_symbol (ADA_MAIN_PROGRAM_SYMBOL_NAME, NULL, NULL);

  if (msym.minsym != NULL)
    {
      CORE_ADDR main_program_name_addr = BMSYMBOL_VALUE_ADDRESS (msym);
      if (main_program_name_addr == 0)
	error (_("Invalid address for Ada main program name."));

      main_program_name = target_read_string (main_program_name_addr, 1024);
      return main_program_name.get ();
    }

  /* The main procedure doesn't seem to be in Ada.  */
  return NULL;
}

				/* Symbols */

/* Table of Ada operators and their GNAT-encoded names.  Last entry is pair
   of NULLs.  */

const struct ada_opname_map ada_opname_table[] = {
  {"Oadd", "\"+\"", BINOP_ADD},
  {"Osubtract", "\"-\"", BINOP_SUB},
  {"Omultiply", "\"*\"", BINOP_MUL},
  {"Odivide", "\"/\"", BINOP_DIV},
  {"Omod", "\"mod\"", BINOP_MOD},
  {"Orem", "\"rem\"", BINOP_REM},
  {"Oexpon", "\"**\"", BINOP_EXP},
  {"Olt", "\"<\"", BINOP_LESS},
  {"Ole", "\"<=\"", BINOP_LEQ},
  {"Ogt", "\">\"", BINOP_GTR},
  {"Oge", "\">=\"", BINOP_GEQ},
  {"Oeq", "\"=\"", BINOP_EQUAL},
  {"One", "\"/=\"", BINOP_NOTEQUAL},
  {"Oand", "\"and\"", BINOP_BITWISE_AND},
  {"Oor", "\"or\"", BINOP_BITWISE_IOR},
  {"Oxor", "\"xor\"", BINOP_BITWISE_XOR},
  {"Oconcat", "\"&\"", BINOP_CONCAT},
  {"Oabs", "\"abs\"", UNOP_ABS},
  {"Onot", "\"not\"", UNOP_LOGICAL_NOT},
  {"Oadd", "\"+\"", UNOP_PLUS},
  {"Osubtract", "\"-\"", UNOP_NEG},
  {NULL, NULL}
};

/* If STR is a decoded version of a compiler-provided suffix (like the
   "[cold]" in "symbol[cold]"), return true.  Otherwise, return
   false.  */

static bool
is_compiler_suffix (const char *str)
{
  gdb_assert (*str == '[');
  ++str;
  while (*str != '\0' && isalpha (*str))
    ++str;
  /* We accept a missing "]" in order to support completion.  */
  return *str == '\0' || (str[0] == ']' && str[1] == '\0');
}

/* The "encoded" form of DECODED, according to GNAT conventions.  If
   THROW_ERRORS, throw an error if invalid operator name is found.
   Otherwise, return the empty string in that case.  */

static std::string
ada_encode_1 (const char *decoded, bool throw_errors)
{
  if (decoded == NULL)
    return {};

  std::string encoding_buffer;
  for (const char *p = decoded; *p != '\0'; p += 1)
    {
      if (*p == '.')
	encoding_buffer.append ("__");
      else if (*p == '[' && is_compiler_suffix (p))
	{
	  encoding_buffer = encoding_buffer + "." + (p + 1);
	  if (encoding_buffer.back () == ']')
	    encoding_buffer.pop_back ();
	  break;
	}
      else if (*p == '"')
	{
	  const struct ada_opname_map *mapping;

	  for (mapping = ada_opname_table;
	       mapping->encoded != NULL
	       && !startswith (p, mapping->decoded); mapping += 1)
	    ;
	  if (mapping->encoded == NULL)
	    {
	      if (throw_errors)
		error (_("invalid Ada operator name: %s"), p);
	      else
		return {};
	    }
	  encoding_buffer.append (mapping->encoded);
	  break;
	}
      else
	encoding_buffer.push_back (*p);
    }

  return encoding_buffer;
}

/* The "encoded" form of DECODED, according to GNAT conventions.  */

std::string
ada_encode (const char *decoded)
{
  return ada_encode_1 (decoded, true);
}

/* Return NAME folded to lower case, or, if surrounded by single
   quotes, unfolded, but with the quotes stripped away.  Result good
   to next call.  */

static const char *
ada_fold_name (gdb::string_view name)
{
  static std::string fold_storage;

  if (!name.empty () && name[0] == '\'')
    fold_storage = gdb::to_string (name.substr (1, name.size () - 2));
  else
    {
      fold_storage = gdb::to_string (name);
      for (int i = 0; i < name.size (); i += 1)
	fold_storage[i] = tolower (fold_storage[i]);
    }

  return fold_storage.c_str ();
}

/* Return nonzero if C is either a digit or a lowercase alphabet character.  */

static int
is_lower_alphanum (const char c)
{
  return (isdigit (c) || (isalpha (c) && islower (c)));
}

/* ENCODED is the linkage name of a symbol and LEN contains its length.
   This function saves in LEN the length of that same symbol name but
   without either of these suffixes:
     . .{DIGIT}+
     . ${DIGIT}+
     . ___{DIGIT}+
     . __{DIGIT}+.

   These are suffixes introduced by the compiler for entities such as
   nested subprogram for instance, in order to avoid name clashes.
   They do not serve any purpose for the debugger.  */

static void
ada_remove_trailing_digits (const char *encoded, int *len)
{
  if (*len > 1 && isdigit (encoded[*len - 1]))
    {
      int i = *len - 2;

      while (i > 0 && isdigit (encoded[i]))
	i--;
      if (i >= 0 && encoded[i] == '.')
	*len = i;
      else if (i >= 0 && encoded[i] == '$')
	*len = i;
      else if (i >= 2 && startswith (encoded + i - 2, "___"))
	*len = i - 2;
      else if (i >= 1 && startswith (encoded + i - 1, "__"))
	*len = i - 1;
    }
}

/* Remove the suffix introduced by the compiler for protected object
   subprograms.  */

static void
ada_remove_po_subprogram_suffix (const char *encoded, int *len)
{
  /* Remove trailing N.  */

  /* Protected entry subprograms are broken into two
     separate subprograms: The first one is unprotected, and has
     a 'N' suffix; the second is the protected version, and has
     the 'P' suffix.  The second calls the first one after handling
     the protection.  Since the P subprograms are internally generated,
     we leave these names undecoded, giving the user a clue that this
     entity is internal.  */

  if (*len > 1
      && encoded[*len - 1] == 'N'
      && (isdigit (encoded[*len - 2]) || islower (encoded[*len - 2])))
    *len = *len - 1;
}

/* If ENCODED ends with a compiler-provided suffix (like ".cold"),
   then update *LEN to remove the suffix and return the offset of the
   character just past the ".".  Otherwise, return -1.  */

static int
remove_compiler_suffix (const char *encoded, int *len)
{
  int offset = *len - 1;
  while (offset > 0 && isalpha (encoded[offset]))
    --offset;
  if (offset > 0 && encoded[offset] == '.')
    {
      *len = offset;
      return offset + 1;
    }
  return -1;
}

/* See ada-lang.h.  */

std::string
ada_decode (const char *encoded, bool wrap)
{
  int i, j;
  int len0;
  const char *p;
  int at_start_name;
  std::string decoded;
  int suffix = -1;

  /* With function descriptors on PPC64, the value of a symbol named
     ".FN", if it exists, is the entry point of the function "FN".  */
  if (encoded[0] == '.')
    encoded += 1;

  /* The name of the Ada main procedure starts with "_ada_".
     This prefix is not part of the decoded name, so skip this part
     if we see this prefix.  */
  if (startswith (encoded, "_ada_"))
    encoded += 5;

  /* If the name starts with '_', then it is not a properly encoded
     name, so do not attempt to decode it.  Similarly, if the name
     starts with '<', the name should not be decoded.  */
  if (encoded[0] == '_' || encoded[0] == '<')
    goto Suppress;

  len0 = strlen (encoded);

  suffix = remove_compiler_suffix (encoded, &len0);

  ada_remove_trailing_digits (encoded, &len0);
  ada_remove_po_subprogram_suffix (encoded, &len0);

  /* Remove the ___X.* suffix if present.  Do not forget to verify that
     the suffix is located before the current "end" of ENCODED.  We want
     to avoid re-matching parts of ENCODED that have previously been
     marked as discarded (by decrementing LEN0).  */
  p = strstr (encoded, "___");
  if (p != NULL && p - encoded < len0 - 3)
    {
      if (p[3] == 'X')
	len0 = p - encoded;
      else
	goto Suppress;
    }

  /* Remove any trailing TKB suffix.  It tells us that this symbol
     is for the body of a task, but that information does not actually
     appear in the decoded name.  */

  if (len0 > 3 && startswith (encoded + len0 - 3, "TKB"))
    len0 -= 3;

  /* Remove any trailing TB suffix.  The TB suffix is slightly different
     from the TKB suffix because it is used for non-anonymous task
     bodies.  */

  if (len0 > 2 && startswith (encoded + len0 - 2, "TB"))
    len0 -= 2;

  /* Remove trailing "B" suffixes.  */
  /* FIXME: brobecker/2006-04-19: Not sure what this are used for...  */

  if (len0 > 1 && startswith (encoded + len0 - 1, "B"))
    len0 -= 1;

  /* Make decoded big enough for possible expansion by operator name.  */

  decoded.resize (2 * len0 + 1, 'X');

  /* Remove trailing __{digit}+ or trailing ${digit}+.  */

  if (len0 > 1 && isdigit (encoded[len0 - 1]))
    {
      i = len0 - 2;
      while ((i >= 0 && isdigit (encoded[i]))
	     || (i >= 1 && encoded[i] == '_' && isdigit (encoded[i - 1])))
	i -= 1;
      if (i > 1 && encoded[i] == '_' && encoded[i - 1] == '_')
	len0 = i - 1;
      else if (encoded[i] == '$')
	len0 = i;
    }

  /* The first few characters that are not alphabetic are not part
     of any encoding we use, so we can copy them over verbatim.  */

  for (i = 0, j = 0; i < len0 && !isalpha (encoded[i]); i += 1, j += 1)
    decoded[j] = encoded[i];

  at_start_name = 1;
  while (i < len0)
    {
      /* Is this a symbol function?  */
      if (at_start_name && encoded[i] == 'O')
	{
	  int k;

	  for (k = 0; ada_opname_table[k].encoded != NULL; k += 1)
	    {
	      int op_len = strlen (ada_opname_table[k].encoded);
	      if ((strncmp (ada_opname_table[k].encoded + 1, encoded + i + 1,
			    op_len - 1) == 0)
		  && !isalnum (encoded[i + op_len]))
		{
		  strcpy (&decoded.front() + j, ada_opname_table[k].decoded);
		  at_start_name = 0;
		  i += op_len;
		  j += strlen (ada_opname_table[k].decoded);
		  break;
		}
	    }
	  if (ada_opname_table[k].encoded != NULL)
	    continue;
	}
      at_start_name = 0;

      /* Replace "TK__" with "__", which will eventually be translated
	 into "." (just below).  */

      if (i < len0 - 4 && startswith (encoded + i, "TK__"))
	i += 2;

      /* Replace "__B_{DIGITS}+__" sequences by "__", which will eventually
	 be translated into "." (just below).  These are internal names
	 generated for anonymous blocks inside which our symbol is nested.  */

      if (len0 - i > 5 && encoded [i] == '_' && encoded [i+1] == '_'
	  && encoded [i+2] == 'B' && encoded [i+3] == '_'
	  && isdigit (encoded [i+4]))
	{
	  int k = i + 5;
	  
	  while (k < len0 && isdigit (encoded[k]))
	    k++;  /* Skip any extra digit.  */

	  /* Double-check that the "__B_{DIGITS}+" sequence we found
	     is indeed followed by "__".  */
	  if (len0 - k > 2 && encoded [k] == '_' && encoded [k+1] == '_')
	    i = k;
	}

      /* Remove _E{DIGITS}+[sb] */

      /* Just as for protected object subprograms, there are 2 categories
	 of subprograms created by the compiler for each entry.  The first
	 one implements the actual entry code, and has a suffix following
	 the convention above; the second one implements the barrier and
	 uses the same convention as above, except that the 'E' is replaced
	 by a 'B'.

	 Just as above, we do not decode the name of barrier functions
	 to give the user a clue that the code he is debugging has been
	 internally generated.  */

      if (len0 - i > 3 && encoded [i] == '_' && encoded[i+1] == 'E'
	  && isdigit (encoded[i+2]))
	{
	  int k = i + 3;

	  while (k < len0 && isdigit (encoded[k]))
	    k++;

	  if (k < len0
	      && (encoded[k] == 'b' || encoded[k] == 's'))
	    {
	      k++;
	      /* Just as an extra precaution, make sure that if this
		 suffix is followed by anything else, it is a '_'.
		 Otherwise, we matched this sequence by accident.  */
	      if (k == len0
		  || (k < len0 && encoded[k] == '_'))
		i = k;
	    }
	}

      /* Remove trailing "N" in [a-z0-9]+N__.  The N is added by
	 the GNAT front-end in protected object subprograms.  */

      if (i < len0 + 3
	  && encoded[i] == 'N' && encoded[i+1] == '_' && encoded[i+2] == '_')
	{
	  /* Backtrack a bit up until we reach either the begining of
	     the encoded name, or "__".  Make sure that we only find
	     digits or lowercase characters.  */
	  const char *ptr = encoded + i - 1;

	  while (ptr >= encoded && is_lower_alphanum (ptr[0]))
	    ptr--;
	  if (ptr < encoded
	      || (ptr > encoded && ptr[0] == '_' && ptr[-1] == '_'))
	    i++;
	}

      if (encoded[i] == 'X' && i != 0 && isalnum (encoded[i - 1]))
	{
	  /* This is a X[bn]* sequence not separated from the previous
	     part of the name with a non-alpha-numeric character (in other
	     words, immediately following an alpha-numeric character), then
	     verify that it is placed at the end of the encoded name.  If
	     not, then the encoding is not valid and we should abort the
	     decoding.  Otherwise, just skip it, it is used in body-nested
	     package names.  */
	  do
	    i += 1;
	  while (i < len0 && (encoded[i] == 'b' || encoded[i] == 'n'));
	  if (i < len0)
	    goto Suppress;
	}
      else if (i < len0 - 2 && encoded[i] == '_' && encoded[i + 1] == '_')
	{
	 /* Replace '__' by '.'.  */
	  decoded[j] = '.';
	  at_start_name = 1;
	  i += 2;
	  j += 1;
	}
      else
	{
	  /* It's a character part of the decoded name, so just copy it
	     over.  */
	  decoded[j] = encoded[i];
	  i += 1;
	  j += 1;
	}
    }
  decoded.resize (j);

  /* Decoded names should never contain any uppercase character.
     Double-check this, and abort the decoding if we find one.  */

  for (i = 0; i < decoded.length(); ++i)
    if (isupper (decoded[i]) || decoded[i] == ' ')
      goto Suppress;

  /* If the compiler added a suffix, append it now.  */
  if (suffix >= 0)
    decoded = decoded + "[" + &encoded[suffix] + "]";

  return decoded;

Suppress:
  if (!wrap)
    return {};

  if (encoded[0] == '<')
    decoded = encoded;
  else
    decoded = '<' + std::string(encoded) + '>';
  return decoded;
}

/* Table for keeping permanent unique copies of decoded names.  Once
   allocated, names in this table are never released.  While this is a
   storage leak, it should not be significant unless there are massive
   changes in the set of decoded names in successive versions of a 
   symbol table loaded during a single session.  */
static struct htab *decoded_names_store;

/* Returns the decoded name of GSYMBOL, as for ada_decode, caching it
   in the language-specific part of GSYMBOL, if it has not been
   previously computed.  Tries to save the decoded name in the same
   obstack as GSYMBOL, if possible, and otherwise on the heap (so that,
   in any case, the decoded symbol has a lifetime at least that of
   GSYMBOL).
   The GSYMBOL parameter is "mutable" in the C++ sense: logically
   const, but nevertheless modified to a semantically equivalent form
   when a decoded name is cached in it.  */

const char *
ada_decode_symbol (const struct general_symbol_info *arg)
{
  struct general_symbol_info *gsymbol = (struct general_symbol_info *) arg;
  const char **resultp =
    &gsymbol->language_specific.demangled_name;

  if (!gsymbol->ada_mangled)
    {
      std::string decoded = ada_decode (gsymbol->linkage_name ());
      struct obstack *obstack = gsymbol->language_specific.obstack;

      gsymbol->ada_mangled = 1;

      if (obstack != NULL)
	*resultp = obstack_strdup (obstack, decoded.c_str ());
      else
	{
	  /* Sometimes, we can't find a corresponding objfile, in
	     which case, we put the result on the heap.  Since we only
	     decode when needed, we hope this usually does not cause a
	     significant memory leak (FIXME).  */

	  char **slot = (char **) htab_find_slot (decoded_names_store,
						  decoded.c_str (), INSERT);

	  if (*slot == NULL)
	    *slot = xstrdup (decoded.c_str ());
	  *resultp = *slot;
	}
    }

  return *resultp;
}

static char *
ada_la_decode (const char *encoded, int options)
{
  return xstrdup (ada_decode (encoded).c_str ());
}



				/* Arrays */

/* Assuming that INDEX_DESC_TYPE is an ___XA structure, a structure
   generated by the GNAT compiler to describe the index type used
   for each dimension of an array, check whether it follows the latest
   known encoding.  If not, fix it up to conform to the latest encoding.
   Otherwise, do nothing.  This function also does nothing if
   INDEX_DESC_TYPE is NULL.

   The GNAT encoding used to describe the array index type evolved a bit.
   Initially, the information would be provided through the name of each
   field of the structure type only, while the type of these fields was
   described as unspecified and irrelevant.  The debugger was then expected
   to perform a global type lookup using the name of that field in order
   to get access to the full index type description.  Because these global
   lookups can be very expensive, the encoding was later enhanced to make
   the global lookup unnecessary by defining the field type as being
   the full index type description.

   The purpose of this routine is to allow us to support older versions
   of the compiler by detecting the use of the older encoding, and by
   fixing up the INDEX_DESC_TYPE to follow the new one (at this point,
   we essentially replace each field's meaningless type by the associated
   index subtype).  */

void
ada_fixup_array_indexes_type (struct type *index_desc_type)
{
  int i;

  if (index_desc_type == NULL)
    return;
  gdb_assert (index_desc_type->num_fields () > 0);

  /* Check if INDEX_DESC_TYPE follows the older encoding (it is sufficient
     to check one field only, no need to check them all).  If not, return
     now.

     If our INDEX_DESC_TYPE was generated using the older encoding,
     the field type should be a meaningless integer type whose name
     is not equal to the field name.  */
  if (index_desc_type->field (0).type ()->name () != NULL
      && strcmp (index_desc_type->field (0).type ()->name (),
		 TYPE_FIELD_NAME (index_desc_type, 0)) == 0)
    return;

  /* Fixup each field of INDEX_DESC_TYPE.  */
  for (i = 0; i < index_desc_type->num_fields (); i++)
   {
     const char *name = TYPE_FIELD_NAME (index_desc_type, i);
     struct type *raw_type = ada_check_typedef (ada_find_any_type (name));

     if (raw_type)
       index_desc_type->field (i).set_type (raw_type);
   }
}

/* The desc_* routines return primitive portions of array descriptors
   (fat pointers).  */

/* The descriptor or array type, if any, indicated by TYPE; removes
   level of indirection, if needed.  */

static struct type *
desc_base_type (struct type *type)
{
  if (type == NULL)
    return NULL;
  type = ada_check_typedef (type);
  if (type->code () == TYPE_CODE_TYPEDEF)
    type = ada_typedef_target_type (type);

  if (type != NULL
      && (type->code () == TYPE_CODE_PTR
	  || type->code () == TYPE_CODE_REF))
    return ada_check_typedef (TYPE_TARGET_TYPE (type));
  else
    return type;
}

/* True iff TYPE indicates a "thin" array pointer type.  */

static int
is_thin_pntr (struct type *type)
{
  return
    is_suffix (ada_type_name (desc_base_type (type)), "___XUT")
    || is_suffix (ada_type_name (desc_base_type (type)), "___XUT___XVE");
}

/* The descriptor type for thin pointer type TYPE.  */

static struct type *
thin_descriptor_type (struct type *type)
{
  struct type *base_type = desc_base_type (type);

  if (base_type == NULL)
    return NULL;
  if (is_suffix (ada_type_name (base_type), "___XVE"))
    return base_type;
  else
    {
      struct type *alt_type = ada_find_parallel_type (base_type, "___XVE");

      if (alt_type == NULL)
	return base_type;
      else
	return alt_type;
    }
}

/* A pointer to the array data for thin-pointer value VAL.  */

static struct value *
thin_data_pntr (struct value *val)
{
  struct type *type = ada_check_typedef (value_type (val));
  struct type *data_type = desc_data_target_type (thin_descriptor_type (type));

  data_type = lookup_pointer_type (data_type);

  if (type->code () == TYPE_CODE_PTR)
    return value_cast (data_type, value_copy (val));
  else
    return value_from_longest (data_type, value_address (val));
}

/* True iff TYPE indicates a "thick" array pointer type.  */

static int
is_thick_pntr (struct type *type)
{
  type = desc_base_type (type);
  return (type != NULL && type->code () == TYPE_CODE_STRUCT
	  && lookup_struct_elt_type (type, "P_BOUNDS", 1) != NULL);
}

/* If TYPE is the type of an array descriptor (fat or thin pointer) or a
   pointer to one, the type of its bounds data; otherwise, NULL.  */

static struct type *
desc_bounds_type (struct type *type)
{
  struct type *r;

  type = desc_base_type (type);

  if (type == NULL)
    return NULL;
  else if (is_thin_pntr (type))
    {
      type = thin_descriptor_type (type);
      if (type == NULL)
	return NULL;
      r = lookup_struct_elt_type (type, "BOUNDS", 1);
      if (r != NULL)
	return ada_check_typedef (r);
    }
  else if (type->code () == TYPE_CODE_STRUCT)
    {
      r = lookup_struct_elt_type (type, "P_BOUNDS", 1);
      if (r != NULL)
	return ada_check_typedef (TYPE_TARGET_TYPE (ada_check_typedef (r)));
    }
  return NULL;
}

/* If ARR is an array descriptor (fat or thin pointer), or pointer to
   one, a pointer to its bounds data.   Otherwise NULL.  */

static struct value *
desc_bounds (struct value *arr)
{
  struct type *type = ada_check_typedef (value_type (arr));

  if (is_thin_pntr (type))
    {
      struct type *bounds_type =
	desc_bounds_type (thin_descriptor_type (type));
      LONGEST addr;

      if (bounds_type == NULL)
	error (_("Bad GNAT array descriptor"));

      /* NOTE: The following calculation is not really kosher, but
	 since desc_type is an XVE-encoded type (and shouldn't be),
	 the correct calculation is a real pain.  FIXME (and fix GCC).  */
      if (type->code () == TYPE_CODE_PTR)
	addr = value_as_long (arr);
      else
	addr = value_address (arr);

      return
	value_from_longest (lookup_pointer_type (bounds_type),
			    addr - TYPE_LENGTH (bounds_type));
    }

  else if (is_thick_pntr (type))
    {
      struct value *p_bounds = value_struct_elt (&arr, {}, "P_BOUNDS", NULL,
					       _("Bad GNAT array descriptor"));
      struct type *p_bounds_type = value_type (p_bounds);

      if (p_bounds_type
	  && p_bounds_type->code () == TYPE_CODE_PTR)
	{
	  struct type *target_type = TYPE_TARGET_TYPE (p_bounds_type);

	  if (target_type->is_stub ())
	    p_bounds = value_cast (lookup_pointer_type
				   (ada_check_typedef (target_type)),
				   p_bounds);
	}
      else
	error (_("Bad GNAT array descriptor"));

      return p_bounds;
    }
  else
    return NULL;
}

/* If TYPE is the type of an array-descriptor (fat pointer),  the bit
   position of the field containing the address of the bounds data.  */

static int
fat_pntr_bounds_bitpos (struct type *type)
{
  return TYPE_FIELD_BITPOS (desc_base_type (type), 1);
}

/* If TYPE is the type of an array-descriptor (fat pointer), the bit
   size of the field containing the address of the bounds data.  */

static int
fat_pntr_bounds_bitsize (struct type *type)
{
  type = desc_base_type (type);

  if (TYPE_FIELD_BITSIZE (type, 1) > 0)
    return TYPE_FIELD_BITSIZE (type, 1);
  else
    return 8 * TYPE_LENGTH (ada_check_typedef (type->field (1).type ()));
}

/* If TYPE is the type of an array descriptor (fat or thin pointer) or a
   pointer to one, the type of its array data (a array-with-no-bounds type);
   otherwise, NULL.  Use ada_type_of_array to get an array type with bounds
   data.  */

static struct type *
desc_data_target_type (struct type *type)
{
  type = desc_base_type (type);

  /* NOTE: The following is bogus; see comment in desc_bounds.  */
  if (is_thin_pntr (type))
    return desc_base_type (thin_descriptor_type (type)->field (1).type ());
  else if (is_thick_pntr (type))
    {
      struct type *data_type = lookup_struct_elt_type (type, "P_ARRAY", 1);

      if (data_type
	  && ada_check_typedef (data_type)->code () == TYPE_CODE_PTR)
	return ada_check_typedef (TYPE_TARGET_TYPE (data_type));
    }

  return NULL;
}

/* If ARR is an array descriptor (fat or thin pointer), a pointer to
   its array data.  */

static struct value *
desc_data (struct value *arr)
{
  struct type *type = value_type (arr);

  if (is_thin_pntr (type))
    return thin_data_pntr (arr);
  else if (is_thick_pntr (type))
    return value_struct_elt (&arr, {}, "P_ARRAY", NULL,
			     _("Bad GNAT array descriptor"));
  else
    return NULL;
}


/* If TYPE is the type of an array-descriptor (fat pointer), the bit
   position of the field containing the address of the data.  */

static int
fat_pntr_data_bitpos (struct type *type)
{
  return TYPE_FIELD_BITPOS (desc_base_type (type), 0);
}

/* If TYPE is the type of an array-descriptor (fat pointer), the bit
   size of the field containing the address of the data.  */

static int
fat_pntr_data_bitsize (struct type *type)
{
  type = desc_base_type (type);

  if (TYPE_FIELD_BITSIZE (type, 0) > 0)
    return TYPE_FIELD_BITSIZE (type, 0);
  else
    return TARGET_CHAR_BIT * TYPE_LENGTH (type->field (0).type ());
}

/* If BOUNDS is an array-bounds structure (or pointer to one), return
   the Ith lower bound stored in it, if WHICH is 0, and the Ith upper
   bound, if WHICH is 1.  The first bound is I=1.  */

static struct value *
desc_one_bound (struct value *bounds, int i, int which)
{
  char bound_name[20];
  xsnprintf (bound_name, sizeof (bound_name), "%cB%d",
	     which ? 'U' : 'L', i - 1);
  return value_struct_elt (&bounds, {}, bound_name, NULL,
			   _("Bad GNAT array descriptor bounds"));
}

/* If BOUNDS is an array-bounds structure type, return the bit position
   of the Ith lower bound stored in it, if WHICH is 0, and the Ith upper
   bound, if WHICH is 1.  The first bound is I=1.  */

static int
desc_bound_bitpos (struct type *type, int i, int which)
{
  return TYPE_FIELD_BITPOS (desc_base_type (type), 2 * i + which - 2);
}

/* If BOUNDS is an array-bounds structure type, return the bit field size
   of the Ith lower bound stored in it, if WHICH is 0, and the Ith upper
   bound, if WHICH is 1.  The first bound is I=1.  */

static int
desc_bound_bitsize (struct type *type, int i, int which)
{
  type = desc_base_type (type);

  if (TYPE_FIELD_BITSIZE (type, 2 * i + which - 2) > 0)
    return TYPE_FIELD_BITSIZE (type, 2 * i + which - 2);
  else
    return 8 * TYPE_LENGTH (type->field (2 * i + which - 2).type ());
}

/* If TYPE is the type of an array-bounds structure, the type of its
   Ith bound (numbering from 1).  Otherwise, NULL.  */

static struct type *
desc_index_type (struct type *type, int i)
{
  type = desc_base_type (type);

  if (type->code () == TYPE_CODE_STRUCT)
    {
      char bound_name[20];
      xsnprintf (bound_name, sizeof (bound_name), "LB%d", i - 1);
      return lookup_struct_elt_type (type, bound_name, 1);
    }
  else
    return NULL;
}

/* The number of index positions in the array-bounds type TYPE.
   Return 0 if TYPE is NULL.  */

static int
desc_arity (struct type *type)
{
  type = desc_base_type (type);

  if (type != NULL)
    return type->num_fields () / 2;
  return 0;
}

/* Non-zero iff TYPE is a simple array type (not a pointer to one) or 
   an array descriptor type (representing an unconstrained array
   type).  */

static int
ada_is_direct_array_type (struct type *type)
{
  if (type == NULL)
    return 0;
  type = ada_check_typedef (type);
  return (type->code () == TYPE_CODE_ARRAY
	  || ada_is_array_descriptor_type (type));
}

/* Non-zero iff TYPE represents any kind of array in Ada, or a pointer
 * to one.  */

static int
ada_is_array_type (struct type *type)
{
  while (type != NULL
	 && (type->code () == TYPE_CODE_PTR
	     || type->code () == TYPE_CODE_REF))
    type = TYPE_TARGET_TYPE (type);
  return ada_is_direct_array_type (type);
}

/* Non-zero iff TYPE is a simple array type or pointer to one.  */

int
ada_is_simple_array_type (struct type *type)
{
  if (type == NULL)
    return 0;
  type = ada_check_typedef (type);
  return (type->code () == TYPE_CODE_ARRAY
	  || (type->code () == TYPE_CODE_PTR
	      && (ada_check_typedef (TYPE_TARGET_TYPE (type))->code ()
		  == TYPE_CODE_ARRAY)));
}

/* Non-zero iff TYPE belongs to a GNAT array descriptor.  */

int
ada_is_array_descriptor_type (struct type *type)
{
  struct type *data_type = desc_data_target_type (type);

  if (type == NULL)
    return 0;
  type = ada_check_typedef (type);
  return (data_type != NULL
	  && data_type->code () == TYPE_CODE_ARRAY
	  && desc_arity (desc_bounds_type (type)) > 0);
}

/* Non-zero iff type is a partially mal-formed GNAT array
   descriptor.  FIXME: This is to compensate for some problems with
   debugging output from GNAT.  Re-examine periodically to see if it
   is still needed.  */

int
ada_is_bogus_array_descriptor (struct type *type)
{
  return
    type != NULL
    && type->code () == TYPE_CODE_STRUCT
    && (lookup_struct_elt_type (type, "P_BOUNDS", 1) != NULL
	|| lookup_struct_elt_type (type, "P_ARRAY", 1) != NULL)
    && !ada_is_array_descriptor_type (type);
}


/* If ARR has a record type in the form of a standard GNAT array descriptor,
   (fat pointer) returns the type of the array data described---specifically,
   a pointer-to-array type.  If BOUNDS is non-zero, the bounds data are filled
   in from the descriptor; otherwise, they are left unspecified.  If
   the ARR denotes a null array descriptor and BOUNDS is non-zero,
   returns NULL.  The result is simply the type of ARR if ARR is not
   a descriptor.  */

static struct type *
ada_type_of_array (struct value *arr, int bounds)
{
  if (ada_is_constrained_packed_array_type (value_type (arr)))
    return decode_constrained_packed_array_type (value_type (arr));

  if (!ada_is_array_descriptor_type (value_type (arr)))
    return value_type (arr);

  if (!bounds)
    {
      struct type *array_type =
	ada_check_typedef (desc_data_target_type (value_type (arr)));

      if (ada_is_unconstrained_packed_array_type (value_type (arr)))
	TYPE_FIELD_BITSIZE (array_type, 0) =
	  decode_packed_array_bitsize (value_type (arr));
      
      return array_type;
    }
  else
    {
      struct type *elt_type;
      int arity;
      struct value *descriptor;

      elt_type = ada_array_element_type (value_type (arr), -1);
      arity = ada_array_arity (value_type (arr));

      if (elt_type == NULL || arity == 0)
	return ada_check_typedef (value_type (arr));

      descriptor = desc_bounds (arr);
      if (value_as_long (descriptor) == 0)
	return NULL;
      while (arity > 0)
	{
	  struct type *range_type = alloc_type_copy (value_type (arr));
	  struct type *array_type = alloc_type_copy (value_type (arr));
	  struct value *low = desc_one_bound (descriptor, arity, 0);
	  struct value *high = desc_one_bound (descriptor, arity, 1);

	  arity -= 1;
	  create_static_range_type (range_type, value_type (low),
				    longest_to_int (value_as_long (low)),
				    longest_to_int (value_as_long (high)));
	  elt_type = create_array_type (array_type, elt_type, range_type);

	  if (ada_is_unconstrained_packed_array_type (value_type (arr)))
	    {
	      /* We need to store the element packed bitsize, as well as
		 recompute the array size, because it was previously
		 computed based on the unpacked element size.  */
	      LONGEST lo = value_as_long (low);
	      LONGEST hi = value_as_long (high);

	      TYPE_FIELD_BITSIZE (elt_type, 0) =
		decode_packed_array_bitsize (value_type (arr));
	      /* If the array has no element, then the size is already
		 zero, and does not need to be recomputed.  */
	      if (lo < hi)
		{
		  int array_bitsize =
			(hi - lo + 1) * TYPE_FIELD_BITSIZE (elt_type, 0);

		  TYPE_LENGTH (array_type) = (array_bitsize + 7) / 8;
		}
	    }
	}

      return lookup_pointer_type (elt_type);
    }
}

/* If ARR does not represent an array, returns ARR unchanged.
   Otherwise, returns either a standard GDB array with bounds set
   appropriately or, if ARR is a non-null fat pointer, a pointer to a standard
   GDB array.  Returns NULL if ARR is a null fat pointer.  */

struct value *
ada_coerce_to_simple_array_ptr (struct value *arr)
{
  if (ada_is_array_descriptor_type (value_type (arr)))
    {
      struct type *arrType = ada_type_of_array (arr, 1);

      if (arrType == NULL)
	return NULL;
      return value_cast (arrType, value_copy (desc_data (arr)));
    }
  else if (ada_is_constrained_packed_array_type (value_type (arr)))
    return decode_constrained_packed_array (arr);
  else
    return arr;
}

/* If ARR does not represent an array, returns ARR unchanged.
   Otherwise, returns a standard GDB array describing ARR (which may
   be ARR itself if it already is in the proper form).  */

struct value *
ada_coerce_to_simple_array (struct value *arr)
{
  if (ada_is_array_descriptor_type (value_type (arr)))
    {
      struct value *arrVal = ada_coerce_to_simple_array_ptr (arr);

      if (arrVal == NULL)
	error (_("Bounds unavailable for null array pointer."));
      ada_ensure_varsize_limit (TYPE_TARGET_TYPE (value_type (arrVal)));
      return value_ind (arrVal);
    }
  else if (ada_is_constrained_packed_array_type (value_type (arr)))
    return decode_constrained_packed_array (arr);
  else
    return arr;
}

/* If TYPE represents a GNAT array type, return it translated to an
   ordinary GDB array type (possibly with BITSIZE fields indicating
   packing).  For other types, is the identity.  */

struct type *
ada_coerce_to_simple_array_type (struct type *type)
{
  if (ada_is_constrained_packed_array_type (type))
    return decode_constrained_packed_array_type (type);

  if (ada_is_array_descriptor_type (type))
    return ada_check_typedef (desc_data_target_type (type));

  return type;
}

/* Non-zero iff TYPE represents a standard GNAT packed-array type.  */

static int
ada_is_gnat_encoded_packed_array_type  (struct type *type)
{
  if (type == NULL)
    return 0;
  type = desc_base_type (type);
  type = ada_check_typedef (type);
  return
    ada_type_name (type) != NULL
    && strstr (ada_type_name (type), "___XP") != NULL;
}

/* Non-zero iff TYPE represents a standard GNAT constrained
   packed-array type.  */

int
ada_is_constrained_packed_array_type (struct type *type)
{
  return ada_is_gnat_encoded_packed_array_type (type)
    && !ada_is_array_descriptor_type (type);
}

/* Non-zero iff TYPE represents an array descriptor for a
   unconstrained packed-array type.  */

static int
ada_is_unconstrained_packed_array_type (struct type *type)
{
  if (!ada_is_array_descriptor_type (type))
    return 0;

  if (ada_is_gnat_encoded_packed_array_type (type))
    return 1;

  /* If we saw GNAT encodings, then the above code is sufficient.
     However, with minimal encodings, we will just have a thick
     pointer instead.  */
  if (is_thick_pntr (type))
    {
      type = desc_base_type (type);
      /* The structure's first field is a pointer to an array, so this
	 fetches the array type.  */
      type = TYPE_TARGET_TYPE (type->field (0).type ());
      /* Now we can see if the array elements are packed.  */
      return TYPE_FIELD_BITSIZE (type, 0) > 0;
    }

  return 0;
}

/* Return true if TYPE is a (Gnat-encoded) constrained packed array
   type, or if it is an ordinary (non-Gnat-encoded) packed array.  */

static bool
ada_is_any_packed_array_type (struct type *type)
{
  return (ada_is_constrained_packed_array_type (type)
	  || (type->code () == TYPE_CODE_ARRAY
	      && TYPE_FIELD_BITSIZE (type, 0) % 8 != 0));
}

/* Given that TYPE encodes a packed array type (constrained or unconstrained),
   return the size of its elements in bits.  */

static long
decode_packed_array_bitsize (struct type *type)
{
  const char *raw_name;
  const char *tail;
  long bits;

  /* Access to arrays implemented as fat pointers are encoded as a typedef
     of the fat pointer type.  We need the name of the fat pointer type
     to do the decoding, so strip the typedef layer.  */
  if (type->code () == TYPE_CODE_TYPEDEF)
    type = ada_typedef_target_type (type);

  raw_name = ada_type_name (ada_check_typedef (type));
  if (!raw_name)
    raw_name = ada_type_name (desc_base_type (type));

  if (!raw_name)
    return 0;

  tail = strstr (raw_name, "___XP");
  if (tail == nullptr)
    {
      gdb_assert (is_thick_pntr (type));
      /* The structure's first field is a pointer to an array, so this
	 fetches the array type.  */
      type = TYPE_TARGET_TYPE (type->field (0).type ());
      /* Now we can see if the array elements are packed.  */
      return TYPE_FIELD_BITSIZE (type, 0);
    }

  if (sscanf (tail + sizeof ("___XP") - 1, "%ld", &bits) != 1)
    {
      lim_warning
	(_("could not understand bit size information on packed array"));
      return 0;
    }

  return bits;
}

/* Given that TYPE is a standard GDB array type with all bounds filled
   in, and that the element size of its ultimate scalar constituents
   (that is, either its elements, or, if it is an array of arrays, its
   elements' elements, etc.) is *ELT_BITS, return an identical type,
   but with the bit sizes of its elements (and those of any
   constituent arrays) recorded in the BITSIZE components of its
   TYPE_FIELD_BITSIZE values, and with *ELT_BITS set to its total size
   in bits.

   Note that, for arrays whose index type has an XA encoding where
   a bound references a record discriminant, getting that discriminant,
   and therefore the actual value of that bound, is not possible
   because none of the given parameters gives us access to the record.
   This function assumes that it is OK in the context where it is being
   used to return an array whose bounds are still dynamic and where
   the length is arbitrary.  */

static struct type *
constrained_packed_array_type (struct type *type, long *elt_bits)
{
  struct type *new_elt_type;
  struct type *new_type;
  struct type *index_type_desc;
  struct type *index_type;
  LONGEST low_bound, high_bound;

  type = ada_check_typedef (type);
  if (type->code () != TYPE_CODE_ARRAY)
    return type;

  index_type_desc = ada_find_parallel_type (type, "___XA");
  if (index_type_desc)
    index_type = to_fixed_range_type (index_type_desc->field (0).type (),
				      NULL);
  else
    index_type = type->index_type ();

  new_type = alloc_type_copy (type);
  new_elt_type =
    constrained_packed_array_type (ada_check_typedef (TYPE_TARGET_TYPE (type)),
				   elt_bits);
  create_array_type (new_type, new_elt_type, index_type);
  TYPE_FIELD_BITSIZE (new_type, 0) = *elt_bits;
  new_type->set_name (ada_type_name (type));

  if ((check_typedef (index_type)->code () == TYPE_CODE_RANGE
       && is_dynamic_type (check_typedef (index_type)))
      || !get_discrete_bounds (index_type, &low_bound, &high_bound))
    low_bound = high_bound = 0;
  if (high_bound < low_bound)
    *elt_bits = TYPE_LENGTH (new_type) = 0;
  else
    {
      *elt_bits *= (high_bound - low_bound + 1);
      TYPE_LENGTH (new_type) =
	(*elt_bits + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
    }

  new_type->set_is_fixed_instance (true);
  return new_type;
}

/* The array type encoded by TYPE, where
   ada_is_constrained_packed_array_type (TYPE).  */

static struct type *
decode_constrained_packed_array_type (struct type *type)
{
  const char *raw_name = ada_type_name (ada_check_typedef (type));
  char *name;
  const char *tail;
  struct type *shadow_type;
  long bits;

  if (!raw_name)
    raw_name = ada_type_name (desc_base_type (type));

  if (!raw_name)
    return NULL;

  name = (char *) alloca (strlen (raw_name) + 1);
  tail = strstr (raw_name, "___XP");
  type = desc_base_type (type);

  memcpy (name, raw_name, tail - raw_name);
  name[tail - raw_name] = '\000';

  shadow_type = ada_find_parallel_type_with_name (type, name);

  if (shadow_type == NULL)
    {
      lim_warning (_("could not find bounds information on packed array"));
      return NULL;
    }
  shadow_type = check_typedef (shadow_type);

  if (shadow_type->code () != TYPE_CODE_ARRAY)
    {
      lim_warning (_("could not understand bounds "
		     "information on packed array"));
      return NULL;
    }

  bits = decode_packed_array_bitsize (type);
  return constrained_packed_array_type (shadow_type, &bits);
}

/* Helper function for decode_constrained_packed_array.  Set the field
   bitsize on a series of packed arrays.  Returns the number of
   elements in TYPE.  */

static LONGEST
recursively_update_array_bitsize (struct type *type)
{
  gdb_assert (type->code () == TYPE_CODE_ARRAY);

  LONGEST low, high;
  if (!get_discrete_bounds (type->index_type (), &low, &high)
      || low > high)
    return 0;
  LONGEST our_len = high - low + 1;

  struct type *elt_type = TYPE_TARGET_TYPE (type);
  if (elt_type->code () == TYPE_CODE_ARRAY)
    {
      LONGEST elt_len = recursively_update_array_bitsize (elt_type);
      LONGEST elt_bitsize = elt_len * TYPE_FIELD_BITSIZE (elt_type, 0);
      TYPE_FIELD_BITSIZE (type, 0) = elt_bitsize;

      TYPE_LENGTH (type) = ((our_len * elt_bitsize + HOST_CHAR_BIT - 1)
			    / HOST_CHAR_BIT);
    }

  return our_len;
}

/* Given that ARR is a struct value *indicating a GNAT constrained packed
   array, returns a simple array that denotes that array.  Its type is a
   standard GDB array type except that the BITSIZEs of the array
   target types are set to the number of bits in each element, and the
   type length is set appropriately.  */

static struct value *
decode_constrained_packed_array (struct value *arr)
{
  struct type *type;

  /* If our value is a pointer, then dereference it. Likewise if
     the value is a reference.  Make sure that this operation does not
     cause the target type to be fixed, as this would indirectly cause
     this array to be decoded.  The rest of the routine assumes that
     the array hasn't been decoded yet, so we use the basic "coerce_ref"
     and "value_ind" routines to perform the dereferencing, as opposed
     to using "ada_coerce_ref" or "ada_value_ind".  */
  arr = coerce_ref (arr);
  if (ada_check_typedef (value_type (arr))->code () == TYPE_CODE_PTR)
    arr = value_ind (arr);

  type = decode_constrained_packed_array_type (value_type (arr));
  if (type == NULL)
    {
      error (_("can't unpack array"));
      return NULL;
    }

  /* Decoding the packed array type could not correctly set the field
     bitsizes for any dimension except the innermost, because the
     bounds may be variable and were not passed to that function.  So,
     we further resolve the array bounds here and then update the
     sizes.  */
  const gdb_byte *valaddr = value_contents_for_printing (arr);
  CORE_ADDR address = value_address (arr);
  gdb::array_view<const gdb_byte> view
    = gdb::make_array_view (valaddr, TYPE_LENGTH (type));
  type = resolve_dynamic_type (type, view, address);
  recursively_update_array_bitsize (type);

  if (type_byte_order (value_type (arr)) == BFD_ENDIAN_BIG
      && ada_is_modular_type (value_type (arr)))
    {
       /* This is a (right-justified) modular type representing a packed
	  array with no wrapper.  In order to interpret the value through
	  the (left-justified) packed array type we just built, we must
	  first left-justify it.  */
      int bit_size, bit_pos;
      ULONGEST mod;

      mod = ada_modulus (value_type (arr)) - 1;
      bit_size = 0;
      while (mod > 0)
	{
	  bit_size += 1;
	  mod >>= 1;
	}
      bit_pos = HOST_CHAR_BIT * TYPE_LENGTH (value_type (arr)) - bit_size;
      arr = ada_value_primitive_packed_val (arr, NULL,
					    bit_pos / HOST_CHAR_BIT,
					    bit_pos % HOST_CHAR_BIT,
					    bit_size,
					    type);
    }

  return coerce_unspec_val_to_type (arr, type);
}


/* The value of the element of packed array ARR at the ARITY indices
   given in IND.   ARR must be a simple array.  */

static struct value *
value_subscript_packed (struct value *arr, int arity, struct value **ind)
{
  int i;
  int bits, elt_off, bit_off;
  long elt_total_bit_offset;
  struct type *elt_type;
  struct value *v;

  bits = 0;
  elt_total_bit_offset = 0;
  elt_type = ada_check_typedef (value_type (arr));
  for (i = 0; i < arity; i += 1)
    {
      if (elt_type->code () != TYPE_CODE_ARRAY
	  || TYPE_FIELD_BITSIZE (elt_type, 0) == 0)
	error
	  (_("attempt to do packed indexing of "
	     "something other than a packed array"));
      else
	{
	  struct type *range_type = elt_type->index_type ();
	  LONGEST lowerbound, upperbound;
	  LONGEST idx;

	  if (!get_discrete_bounds (range_type, &lowerbound, &upperbound))
	    {
	      lim_warning (_("don't know bounds of array"));
	      lowerbound = upperbound = 0;
	    }

	  idx = pos_atr (ind[i]);
	  if (idx < lowerbound || idx > upperbound)
	    lim_warning (_("packed array index %ld out of bounds"),
			 (long) idx);
	  bits = TYPE_FIELD_BITSIZE (elt_type, 0);
	  elt_total_bit_offset += (idx - lowerbound) * bits;
	  elt_type = ada_check_typedef (TYPE_TARGET_TYPE (elt_type));
	}
    }
  elt_off = elt_total_bit_offset / HOST_CHAR_BIT;
  bit_off = elt_total_bit_offset % HOST_CHAR_BIT;

  v = ada_value_primitive_packed_val (arr, NULL, elt_off, bit_off,
				      bits, elt_type);
  return v;
}

/* Non-zero iff TYPE includes negative integer values.  */

static int
has_negatives (struct type *type)
{
  switch (type->code ())
    {
    default:
      return 0;
    case TYPE_CODE_INT:
      return !type->is_unsigned ();
    case TYPE_CODE_RANGE:
      return type->bounds ()->low.const_val () - type->bounds ()->bias < 0;
    }
}

/* With SRC being a buffer containing BIT_SIZE bits of data at BIT_OFFSET,
   unpack that data into UNPACKED.  UNPACKED_LEN is the size in bytes of
   the unpacked buffer.

   The size of the unpacked buffer (UNPACKED_LEN) is expected to be large
   enough to contain at least BIT_OFFSET bits.  If not, an error is raised.

   IS_BIG_ENDIAN is nonzero if the data is stored in big endian mode,
   zero otherwise.

   IS_SIGNED_TYPE is nonzero if the data corresponds to a signed type.

   IS_SCALAR is nonzero if the data corresponds to a signed type.  */

static void
ada_unpack_from_contents (const gdb_byte *src, int bit_offset, int bit_size,
			  gdb_byte *unpacked, int unpacked_len,
			  int is_big_endian, int is_signed_type,
			  int is_scalar)
{
  int src_len = (bit_size + bit_offset + HOST_CHAR_BIT - 1) / 8;
  int src_idx;                  /* Index into the source area */
  int src_bytes_left;           /* Number of source bytes left to process.  */
  int srcBitsLeft;              /* Number of source bits left to move */
  int unusedLS;                 /* Number of bits in next significant
				   byte of source that are unused */

  int unpacked_idx;             /* Index into the unpacked buffer */
  int unpacked_bytes_left;      /* Number of bytes left to set in unpacked.  */

  unsigned long accum;          /* Staging area for bits being transferred */
  int accumSize;                /* Number of meaningful bits in accum */
  unsigned char sign;

  /* Transmit bytes from least to most significant; delta is the direction
     the indices move.  */
  int delta = is_big_endian ? -1 : 1;

  /* Make sure that unpacked is large enough to receive the BIT_SIZE
     bits from SRC.  .*/
  if ((bit_size + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT > unpacked_len)
    error (_("Cannot unpack %d bits into buffer of %d bytes"),
	   bit_size, unpacked_len);

  srcBitsLeft = bit_size;
  src_bytes_left = src_len;
  unpacked_bytes_left = unpacked_len;
  sign = 0;

  if (is_big_endian)
    {
      src_idx = src_len - 1;
      if (is_signed_type
	  && ((src[0] << bit_offset) & (1 << (HOST_CHAR_BIT - 1))))
	sign = ~0;

      unusedLS =
	(HOST_CHAR_BIT - (bit_size + bit_offset) % HOST_CHAR_BIT)
	% HOST_CHAR_BIT;

      if (is_scalar)
	{
	  accumSize = 0;
	  unpacked_idx = unpacked_len - 1;
	}
      else
	{
	  /* Non-scalar values must be aligned at a byte boundary...  */
	  accumSize =
	    (HOST_CHAR_BIT - bit_size % HOST_CHAR_BIT) % HOST_CHAR_BIT;
	  /* ... And are placed at the beginning (most-significant) bytes
	     of the target.  */
	  unpacked_idx = (bit_size + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT - 1;
	  unpacked_bytes_left = unpacked_idx + 1;
	}
    }
  else
    {
      int sign_bit_offset = (bit_size + bit_offset - 1) % 8;

      src_idx = unpacked_idx = 0;
      unusedLS = bit_offset;
      accumSize = 0;

      if (is_signed_type && (src[src_len - 1] & (1 << sign_bit_offset)))
	sign = ~0;
    }

  accum = 0;
  while (src_bytes_left > 0)
    {
      /* Mask for removing bits of the next source byte that are not
	 part of the value.  */
      unsigned int unusedMSMask =
	(1 << (srcBitsLeft >= HOST_CHAR_BIT ? HOST_CHAR_BIT : srcBitsLeft)) -
	1;
      /* Sign-extend bits for this byte.  */
      unsigned int signMask = sign & ~unusedMSMask;

      accum |=
	(((src[src_idx] >> unusedLS) & unusedMSMask) | signMask) << accumSize;
      accumSize += HOST_CHAR_BIT - unusedLS;
      if (accumSize >= HOST_CHAR_BIT)
	{
	  unpacked[unpacked_idx] = accum & ~(~0UL << HOST_CHAR_BIT);
	  accumSize -= HOST_CHAR_BIT;
	  accum >>= HOST_CHAR_BIT;
	  unpacked_bytes_left -= 1;
	  unpacked_idx += delta;
	}
      srcBitsLeft -= HOST_CHAR_BIT - unusedLS;
      unusedLS = 0;
      src_bytes_left -= 1;
      src_idx += delta;
    }
  while (unpacked_bytes_left > 0)
    {
      accum |= sign << accumSize;
      unpacked[unpacked_idx] = accum & ~(~0UL << HOST_CHAR_BIT);
      accumSize -= HOST_CHAR_BIT;
      if (accumSize < 0)
	accumSize = 0;
      accum >>= HOST_CHAR_BIT;
      unpacked_bytes_left -= 1;
      unpacked_idx += delta;
    }
}

/* Create a new value of type TYPE from the contents of OBJ starting
   at byte OFFSET, and bit offset BIT_OFFSET within that byte,
   proceeding for BIT_SIZE bits.  If OBJ is an lval in memory, then
   assigning through the result will set the field fetched from.
   VALADDR is ignored unless OBJ is NULL, in which case,
   VALADDR+OFFSET must address the start of storage containing the 
   packed value.  The value returned  in this case is never an lval.
   Assumes 0 <= BIT_OFFSET < HOST_CHAR_BIT.  */

struct value *
ada_value_primitive_packed_val (struct value *obj, const gdb_byte *valaddr,
				long offset, int bit_offset, int bit_size,
				struct type *type)
{
  struct value *v;
  const gdb_byte *src;                /* First byte containing data to unpack */
  gdb_byte *unpacked;
  const int is_scalar = is_scalar_type (type);
  const int is_big_endian = type_byte_order (type) == BFD_ENDIAN_BIG;
  gdb::byte_vector staging;

  type = ada_check_typedef (type);

  if (obj == NULL)
    src = valaddr + offset;
  else
    src = value_contents (obj) + offset;

  if (is_dynamic_type (type))
    {
      /* The length of TYPE might by dynamic, so we need to resolve
	 TYPE in order to know its actual size, which we then use
	 to create the contents buffer of the value we return.
	 The difficulty is that the data containing our object is
	 packed, and therefore maybe not at a byte boundary.  So, what
	 we do, is unpack the data into a byte-aligned buffer, and then
	 use that buffer as our object's value for resolving the type.  */
      int staging_len = (bit_size + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
      staging.resize (staging_len);

      ada_unpack_from_contents (src, bit_offset, bit_size,
				staging.data (), staging.size (),
				is_big_endian, has_negatives (type),
				is_scalar);
      type = resolve_dynamic_type (type, staging, 0);
      if (TYPE_LENGTH (type) < (bit_size + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT)
	{
	  /* This happens when the length of the object is dynamic,
	     and is actually smaller than the space reserved for it.
	     For instance, in an array of variant records, the bit_size
	     we're given is the array stride, which is constant and
	     normally equal to the maximum size of its element.
	     But, in reality, each element only actually spans a portion
	     of that stride.  */
	  bit_size = TYPE_LENGTH (type) * HOST_CHAR_BIT;
	}
    }

  if (obj == NULL)
    {
      v = allocate_value (type);
      src = valaddr + offset;
    }
  else if (VALUE_LVAL (obj) == lval_memory && value_lazy (obj))
    {
      int src_len = (bit_size + bit_offset + HOST_CHAR_BIT - 1) / 8;
      gdb_byte *buf;

      v = value_at (type, value_address (obj) + offset);
      buf = (gdb_byte *) alloca (src_len);
      read_memory (value_address (v), buf, src_len);
      src = buf;
    }
  else
    {
      v = allocate_value (type);
      src = value_contents (obj) + offset;
    }

  if (obj != NULL)
    {
      long new_offset = offset;

      set_value_component_location (v, obj);
      set_value_bitpos (v, bit_offset + value_bitpos (obj));
      set_value_bitsize (v, bit_size);
      if (value_bitpos (v) >= HOST_CHAR_BIT)
	{
	  ++new_offset;
	  set_value_bitpos (v, value_bitpos (v) - HOST_CHAR_BIT);
	}
      set_value_offset (v, new_offset);

      /* Also set the parent value.  This is needed when trying to
	 assign a new value (in inferior memory).  */
      set_value_parent (v, obj);
    }
  else
    set_value_bitsize (v, bit_size);
  unpacked = value_contents_writeable (v);

  if (bit_size == 0)
    {
      memset (unpacked, 0, TYPE_LENGTH (type));
      return v;
    }

  if (staging.size () == TYPE_LENGTH (type))
    {
      /* Small short-cut: If we've unpacked the data into a buffer
	 of the same size as TYPE's length, then we can reuse that,
	 instead of doing the unpacking again.  */
      memcpy (unpacked, staging.data (), staging.size ());
    }
  else
    ada_unpack_from_contents (src, bit_offset, bit_size,
			      unpacked, TYPE_LENGTH (type),
			      is_big_endian, has_negatives (type), is_scalar);

  return v;
}

/* Store the contents of FROMVAL into the location of TOVAL.
   Return a new value with the location of TOVAL and contents of
   FROMVAL.   Handles assignment into packed fields that have
   floating-point or non-scalar types.  */

static struct value *
ada_value_assign (struct value *toval, struct value *fromval)
{
  struct type *type = value_type (toval);
  int bits = value_bitsize (toval);

  toval = ada_coerce_ref (toval);
  fromval = ada_coerce_ref (fromval);

  if (ada_is_direct_array_type (value_type (toval)))
    toval = ada_coerce_to_simple_array (toval);
  if (ada_is_direct_array_type (value_type (fromval)))
    fromval = ada_coerce_to_simple_array (fromval);

  if (!deprecated_value_modifiable (toval))
    error (_("Left operand of assignment is not a modifiable lvalue."));

  if (VALUE_LVAL (toval) == lval_memory
      && bits > 0
      && (type->code () == TYPE_CODE_FLT
	  || type->code () == TYPE_CODE_STRUCT))
    {
      int len = (value_bitpos (toval)
		 + bits + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
      int from_size;
      gdb_byte *buffer = (gdb_byte *) alloca (len);
      struct value *val;
      CORE_ADDR to_addr = value_address (toval);

      if (type->code () == TYPE_CODE_FLT)
	fromval = value_cast (type, fromval);

      read_memory (to_addr, buffer, len);
      from_size = value_bitsize (fromval);
      if (from_size == 0)
	from_size = TYPE_LENGTH (value_type (fromval)) * TARGET_CHAR_BIT;

      const int is_big_endian = type_byte_order (type) == BFD_ENDIAN_BIG;
      ULONGEST from_offset = 0;
      if (is_big_endian && is_scalar_type (value_type (fromval)))
	from_offset = from_size - bits;
      copy_bitwise (buffer, value_bitpos (toval),
		    value_contents (fromval), from_offset,
		    bits, is_big_endian);
      write_memory_with_notification (to_addr, buffer, len);

      val = value_copy (toval);
      memcpy (value_contents_raw (val), value_contents (fromval),
	      TYPE_LENGTH (type));
      deprecated_set_value_type (val, type);

      return val;
    }

  return value_assign (toval, fromval);
}


/* Given that COMPONENT is a memory lvalue that is part of the lvalue
   CONTAINER, assign the contents of VAL to COMPONENTS's place in
   CONTAINER.  Modifies the VALUE_CONTENTS of CONTAINER only, not
   COMPONENT, and not the inferior's memory.  The current contents
   of COMPONENT are ignored.

   Although not part of the initial design, this function also works
   when CONTAINER and COMPONENT are not_lval's: it works as if CONTAINER
   had a null address, and COMPONENT had an address which is equal to
   its offset inside CONTAINER.  */

static void
value_assign_to_component (struct value *container, struct value *component,
			   struct value *val)
{
  LONGEST offset_in_container =
    (LONGEST)  (value_address (component) - value_address (container));
  int bit_offset_in_container =
    value_bitpos (component) - value_bitpos (container);
  int bits;

  val = value_cast (value_type (component), val);

  if (value_bitsize (component) == 0)
    bits = TARGET_CHAR_BIT * TYPE_LENGTH (value_type (component));
  else
    bits = value_bitsize (component);

  if (type_byte_order (value_type (container)) == BFD_ENDIAN_BIG)
    {
      int src_offset;

      if (is_scalar_type (check_typedef (value_type (component))))
	src_offset
	  = TYPE_LENGTH (value_type (component)) * TARGET_CHAR_BIT - bits;
      else
	src_offset = 0;
      copy_bitwise (value_contents_writeable (container) + offset_in_container,
		    value_bitpos (container) + bit_offset_in_container,
		    value_contents (val), src_offset, bits, 1);
    }
  else
    copy_bitwise (value_contents_writeable (container) + offset_in_container,
		  value_bitpos (container) + bit_offset_in_container,
		  value_contents (val), 0, bits, 0);
}

/* Determine if TYPE is an access to an unconstrained array.  */

bool
ada_is_access_to_unconstrained_array (struct type *type)
{
  return (type->code () == TYPE_CODE_TYPEDEF
	  && is_thick_pntr (ada_typedef_target_type (type)));
}

/* The value of the element of array ARR at the ARITY indices given in IND.
   ARR may be either a simple array, GNAT array descriptor, or pointer
   thereto.  */

struct value *
ada_value_subscript (struct value *arr, int arity, struct value **ind)
{
  int k;
  struct value *elt;
  struct type *elt_type;

  elt = ada_coerce_to_simple_array (arr);

  elt_type = ada_check_typedef (value_type (elt));
  if (elt_type->code () == TYPE_CODE_ARRAY
      && TYPE_FIELD_BITSIZE (elt_type, 0) > 0)
    return value_subscript_packed (elt, arity, ind);

  for (k = 0; k < arity; k += 1)
    {
      struct type *saved_elt_type = TYPE_TARGET_TYPE (elt_type);

      if (elt_type->code () != TYPE_CODE_ARRAY)
	error (_("too many subscripts (%d expected)"), k);

      elt = value_subscript (elt, pos_atr (ind[k]));

      if (ada_is_access_to_unconstrained_array (saved_elt_type)
	  && value_type (elt)->code () != TYPE_CODE_TYPEDEF)
	{
	  /* The element is a typedef to an unconstrained array,
	     except that the value_subscript call stripped the
	     typedef layer.  The typedef layer is GNAT's way to
	     specify that the element is, at the source level, an
	     access to the unconstrained array, rather than the
	     unconstrained array.  So, we need to restore that
	     typedef layer, which we can do by forcing the element's
	     type back to its original type. Otherwise, the returned
	     value is going to be printed as the array, rather
	     than as an access.  Another symptom of the same issue
	     would be that an expression trying to dereference the
	     element would also be improperly rejected.  */
	  deprecated_set_value_type (elt, saved_elt_type);
	}

      elt_type = ada_check_typedef (value_type (elt));
    }

  return elt;
}

/* Assuming ARR is a pointer to a GDB array, the value of the element
   of *ARR at the ARITY indices given in IND.
   Does not read the entire array into memory.

   Note: Unlike what one would expect, this function is used instead of
   ada_value_subscript for basically all non-packed array types.  The reason
   for this is that a side effect of doing our own pointer arithmetics instead
   of relying on value_subscript is that there is no implicit typedef peeling.
   This is important for arrays of array accesses, where it allows us to
   preserve the fact that the array's element is an array access, where the
   access part os encoded in a typedef layer.  */

static struct value *
ada_value_ptr_subscript (struct value *arr, int arity, struct value **ind)
{
  int k;
  struct value *array_ind = ada_value_ind (arr);
  struct type *type
    = check_typedef (value_enclosing_type (array_ind));

  if (type->code () == TYPE_CODE_ARRAY
      && TYPE_FIELD_BITSIZE (type, 0) > 0)
    return value_subscript_packed (array_ind, arity, ind);

  for (k = 0; k < arity; k += 1)
    {
      LONGEST lwb, upb;

      if (type->code () != TYPE_CODE_ARRAY)
	error (_("too many subscripts (%d expected)"), k);
      arr = value_cast (lookup_pointer_type (TYPE_TARGET_TYPE (type)),
			value_copy (arr));
      get_discrete_bounds (type->index_type (), &lwb, &upb);
      arr = value_ptradd (arr, pos_atr (ind[k]) - lwb);
      type = TYPE_TARGET_TYPE (type);
    }

  return value_ind (arr);
}

/* Given that ARRAY_PTR is a pointer or reference to an array of type TYPE (the
   actual type of ARRAY_PTR is ignored), returns the Ada slice of
   HIGH'Pos-LOW'Pos+1 elements starting at index LOW.  The lower bound of
   this array is LOW, as per Ada rules.  */
static struct value *
ada_value_slice_from_ptr (struct value *array_ptr, struct type *type,
			  int low, int high)
{
  struct type *type0 = ada_check_typedef (type);
  struct type *base_index_type = TYPE_TARGET_TYPE (type0->index_type ());
  struct type *index_type
    = create_static_range_type (NULL, base_index_type, low, high);
  struct type *slice_type = create_array_type_with_stride
			      (NULL, TYPE_TARGET_TYPE (type0), index_type,
			       type0->dyn_prop (DYN_PROP_BYTE_STRIDE),
			       TYPE_FIELD_BITSIZE (type0, 0));
  int base_low =  ada_discrete_type_low_bound (type0->index_type ());
  gdb::optional<LONGEST> base_low_pos, low_pos;
  CORE_ADDR base;

  low_pos = discrete_position (base_index_type, low);
  base_low_pos = discrete_position (base_index_type, base_low);

  if (!low_pos.has_value () || !base_low_pos.has_value ())
    {
      warning (_("unable to get positions in slice, use bounds instead"));
      low_pos = low;
      base_low_pos = base_low;
    }

  ULONGEST stride = TYPE_FIELD_BITSIZE (slice_type, 0) / 8;
  if (stride == 0)
    stride = TYPE_LENGTH (TYPE_TARGET_TYPE (type0));

  base = value_as_address (array_ptr) + (*low_pos - *base_low_pos) * stride;
  return value_at_lazy (slice_type, base);
}


static struct value *
ada_value_slice (struct value *array, int low, int high)
{
  struct type *type = ada_check_typedef (value_type (array));
  struct type *base_index_type = TYPE_TARGET_TYPE (type->index_type ());
  struct type *index_type
    = create_static_range_type (NULL, type->index_type (), low, high);
  struct type *slice_type = create_array_type_with_stride
			      (NULL, TYPE_TARGET_TYPE (type), index_type,
			       type->dyn_prop (DYN_PROP_BYTE_STRIDE),
			       TYPE_FIELD_BITSIZE (type, 0));
  gdb::optional<LONGEST> low_pos, high_pos;


  low_pos = discrete_position (base_index_type, low);
  high_pos = discrete_position (base_index_type, high);

  if (!low_pos.has_value () || !high_pos.has_value ())
    {
      warning (_("unable to get positions in slice, use bounds instead"));
      low_pos = low;
      high_pos = high;
    }

  return value_cast (slice_type,
		     value_slice (array, low, *high_pos - *low_pos + 1));
}

/* If type is a record type in the form of a standard GNAT array
   descriptor, returns the number of dimensions for type.  If arr is a
   simple array, returns the number of "array of"s that prefix its
   type designation.  Otherwise, returns 0.  */

int
ada_array_arity (struct type *type)
{
  int arity;

  if (type == NULL)
    return 0;

  type = desc_base_type (type);

  arity = 0;
  if (type->code () == TYPE_CODE_STRUCT)
    return desc_arity (desc_bounds_type (type));
  else
    while (type->code () == TYPE_CODE_ARRAY)
      {
	arity += 1;
	type = ada_check_typedef (TYPE_TARGET_TYPE (type));
      }

  return arity;
}

/* If TYPE is a record type in the form of a standard GNAT array
   descriptor or a simple array type, returns the element type for
   TYPE after indexing by NINDICES indices, or by all indices if
   NINDICES is -1.  Otherwise, returns NULL.  */

struct type *
ada_array_element_type (struct type *type, int nindices)
{
  type = desc_base_type (type);

  if (type->code () == TYPE_CODE_STRUCT)
    {
      int k;
      struct type *p_array_type;

      p_array_type = desc_data_target_type (type);

      k = ada_array_arity (type);
      if (k == 0)
	return NULL;

      /* Initially p_array_type = elt_type(*)[]...(k times)...[].  */
      if (nindices >= 0 && k > nindices)
	k = nindices;
      while (k > 0 && p_array_type != NULL)
	{
	  p_array_type = ada_check_typedef (TYPE_TARGET_TYPE (p_array_type));
	  k -= 1;
	}
      return p_array_type;
    }
  else if (type->code () == TYPE_CODE_ARRAY)
    {
      while (nindices != 0 && type->code () == TYPE_CODE_ARRAY)
	{
	  type = TYPE_TARGET_TYPE (type);
	  nindices -= 1;
	}
      return type;
    }

  return NULL;
}

/* See ada-lang.h.  */

struct type *
ada_index_type (struct type *type, int n, const char *name)
{
  struct type *result_type;

  type = desc_base_type (type);

  if (n < 0 || n > ada_array_arity (type))
    error (_("invalid dimension number to '%s"), name);

  if (ada_is_simple_array_type (type))
    {
      int i;

      for (i = 1; i < n; i += 1)
	{
	  type = ada_check_typedef (type);
	  type = TYPE_TARGET_TYPE (type);
	}
      result_type = TYPE_TARGET_TYPE (ada_check_typedef (type)->index_type ());
      /* FIXME: The stabs type r(0,0);bound;bound in an array type
	 has a target type of TYPE_CODE_UNDEF.  We compensate here, but
	 perhaps stabsread.c would make more sense.  */
      if (result_type && result_type->code () == TYPE_CODE_UNDEF)
	result_type = NULL;
    }
  else
    {
      result_type = desc_index_type (desc_bounds_type (type), n);
      if (result_type == NULL)
	error (_("attempt to take bound of something that is not an array"));
    }

  return result_type;
}

/* Given that arr is an array type, returns the lower bound of the
   Nth index (numbering from 1) if WHICH is 0, and the upper bound if
   WHICH is 1.  This returns bounds 0 .. -1 if ARR_TYPE is an
   array-descriptor type.  It works for other arrays with bounds supplied
   by run-time quantities other than discriminants.  */

static LONGEST
ada_array_bound_from_type (struct type *arr_type, int n, int which)
{
  struct type *type, *index_type_desc, *index_type;
  int i;

  gdb_assert (which == 0 || which == 1);

  if (ada_is_constrained_packed_array_type (arr_type))
    arr_type = decode_constrained_packed_array_type (arr_type);

  if (arr_type == NULL || !ada_is_simple_array_type (arr_type))
    return (LONGEST) - which;

  if (arr_type->code () == TYPE_CODE_PTR)
    type = TYPE_TARGET_TYPE (arr_type);
  else
    type = arr_type;

  if (type->is_fixed_instance ())
    {
      /* The array has already been fixed, so we do not need to
	 check the parallel ___XA type again.  That encoding has
	 already been applied, so ignore it now.  */
      index_type_desc = NULL;
    }
  else
    {
      index_type_desc = ada_find_parallel_type (type, "___XA");
      ada_fixup_array_indexes_type (index_type_desc);
    }

  if (index_type_desc != NULL)
    index_type = to_fixed_range_type (index_type_desc->field (n - 1).type (),
				      NULL);
  else
    {
      struct type *elt_type = check_typedef (type);

      for (i = 1; i < n; i++)
	elt_type = check_typedef (TYPE_TARGET_TYPE (elt_type));

      index_type = elt_type->index_type ();
    }

  return
    (LONGEST) (which == 0
	       ? ada_discrete_type_low_bound (index_type)
	       : ada_discrete_type_high_bound (index_type));
}

/* Given that arr is an array value, returns the lower bound of the
   nth index (numbering from 1) if WHICH is 0, and the upper bound if
   WHICH is 1.  This routine will also work for arrays with bounds
   supplied by run-time quantities other than discriminants.  */

static LONGEST
ada_array_bound (struct value *arr, int n, int which)
{
  struct type *arr_type;

  if (check_typedef (value_type (arr))->code () == TYPE_CODE_PTR)
    arr = value_ind (arr);
  arr_type = value_enclosing_type (arr);

  if (ada_is_constrained_packed_array_type (arr_type))
    return ada_array_bound (decode_constrained_packed_array (arr), n, which);
  else if (ada_is_simple_array_type (arr_type))
    return ada_array_bound_from_type (arr_type, n, which);
  else
    return value_as_long (desc_one_bound (desc_bounds (arr), n, which));
}

/* Given that arr is an array value, returns the length of the
   nth index.  This routine will also work for arrays with bounds
   supplied by run-time quantities other than discriminants.
   Does not work for arrays indexed by enumeration types with representation
   clauses at the moment.  */

static LONGEST
ada_array_length (struct value *arr, int n)
{
  struct type *arr_type, *index_type;
  int low, high;

  if (check_typedef (value_type (arr))->code () == TYPE_CODE_PTR)
    arr = value_ind (arr);
  arr_type = value_enclosing_type (arr);

  if (ada_is_constrained_packed_array_type (arr_type))
    return ada_array_length (decode_constrained_packed_array (arr), n);

  if (ada_is_simple_array_type (arr_type))
    {
      low = ada_array_bound_from_type (arr_type, n, 0);
      high = ada_array_bound_from_type (arr_type, n, 1);
    }
  else
    {
      low = value_as_long (desc_one_bound (desc_bounds (arr), n, 0));
      high = value_as_long (desc_one_bound (desc_bounds (arr), n, 1));
    }

  arr_type = check_typedef (arr_type);
  index_type = ada_index_type (arr_type, n, "length");
  if (index_type != NULL)
    {
      struct type *base_type;
      if (index_type->code () == TYPE_CODE_RANGE)
	base_type = TYPE_TARGET_TYPE (index_type);
      else
	base_type = index_type;

      low = pos_atr (value_from_longest (base_type, low));
      high = pos_atr (value_from_longest (base_type, high));
    }
  return high - low + 1;
}

/* An array whose type is that of ARR_TYPE (an array type), with
   bounds LOW to HIGH, but whose contents are unimportant.  If HIGH is
   less than LOW, then LOW-1 is used.  */

static struct value *
empty_array (struct type *arr_type, int low, int high)
{
  struct type *arr_type0 = ada_check_typedef (arr_type);
  struct type *index_type
    = create_static_range_type
	(NULL, TYPE_TARGET_TYPE (arr_type0->index_type ()), low,
	 high < low ? low - 1 : high);
  struct type *elt_type = ada_array_element_type (arr_type0, 1);

  return allocate_value (create_array_type (NULL, elt_type, index_type));
}


				/* Name resolution */

/* The "decoded" name for the user-definable Ada operator corresponding
   to OP.  */

static const char *
ada_decoded_op_name (enum exp_opcode op)
{
  int i;

  for (i = 0; ada_opname_table[i].encoded != NULL; i += 1)
    {
      if (ada_opname_table[i].op == op)
	return ada_opname_table[i].decoded;
    }
  error (_("Could not find operator name for opcode"));
}

/* Returns true (non-zero) iff decoded name N0 should appear before N1
   in a listing of choices during disambiguation (see sort_choices, below).
   The idea is that overloadings of a subprogram name from the
   same package should sort in their source order.  We settle for ordering
   such symbols by their trailing number (__N  or $N).  */

static int
encoded_ordered_before (const char *N0, const char *N1)
{
  if (N1 == NULL)
    return 0;
  else if (N0 == NULL)
    return 1;
  else
    {
      int k0, k1;

      for (k0 = strlen (N0) - 1; k0 > 0 && isdigit (N0[k0]); k0 -= 1)
	;
      for (k1 = strlen (N1) - 1; k1 > 0 && isdigit (N1[k1]); k1 -= 1)
	;
      if ((N0[k0] == '_' || N0[k0] == '$') && N0[k0 + 1] != '\000'
	  && (N1[k1] == '_' || N1[k1] == '$') && N1[k1 + 1] != '\000')
	{
	  int n0, n1;

	  n0 = k0;
	  while (N0[n0] == '_' && n0 > 0 && N0[n0 - 1] == '_')
	    n0 -= 1;
	  n1 = k1;
	  while (N1[n1] == '_' && n1 > 0 && N1[n1 - 1] == '_')
	    n1 -= 1;
	  if (n0 == n1 && strncmp (N0, N1, n0) == 0)
	    return (atoi (N0 + k0 + 1) < atoi (N1 + k1 + 1));
	}
      return (strcmp (N0, N1) < 0);
    }
}

/* Sort SYMS[0..NSYMS-1] to put the choices in a canonical order by the
   encoded names.  */

static void
sort_choices (struct block_symbol syms[], int nsyms)
{
  int i;

  for (i = 1; i < nsyms; i += 1)
    {
      struct block_symbol sym = syms[i];
      int j;

      for (j = i - 1; j >= 0; j -= 1)
	{
	  if (encoded_ordered_before (syms[j].symbol->linkage_name (),
				      sym.symbol->linkage_name ()))
	    break;
	  syms[j + 1] = syms[j];
	}
      syms[j + 1] = sym;
    }
}

/* Whether GDB should display formals and return types for functions in the
   overloads selection menu.  */
static bool print_signatures = true;

/* Print the signature for SYM on STREAM according to the FLAGS options.  For
   all but functions, the signature is just the name of the symbol.  For
   functions, this is the name of the function, the list of types for formals
   and the return type (if any).  */

static void
ada_print_symbol_signature (struct ui_file *stream, struct symbol *sym,
			    const struct type_print_options *flags)
{
  struct type *type = SYMBOL_TYPE (sym);

  fprintf_filtered (stream, "%s", sym->print_name ());
  if (!print_signatures
      || type == NULL
      || type->code () != TYPE_CODE_FUNC)
    return;

  if (type->num_fields () > 0)
    {
      int i;

      fprintf_filtered (stream, " (");
      for (i = 0; i < type->num_fields (); ++i)
	{
	  if (i > 0)
	    fprintf_filtered (stream, "; ");
	  ada_print_type (type->field (i).type (), NULL, stream, -1, 0,
			  flags);
	}
      fprintf_filtered (stream, ")");
    }
  if (TYPE_TARGET_TYPE (type) != NULL
      && TYPE_TARGET_TYPE (type)->code () != TYPE_CODE_VOID)
    {
      fprintf_filtered (stream, " return ");
      ada_print_type (TYPE_TARGET_TYPE (type), NULL, stream, -1, 0, flags);
    }
}

/* Read and validate a set of numeric choices from the user in the
   range 0 .. N_CHOICES-1.  Place the results in increasing
   order in CHOICES[0 .. N-1], and return N.

   The user types choices as a sequence of numbers on one line
   separated by blanks, encoding them as follows:

     + A choice of 0 means to cancel the selection, throwing an error.
     + If IS_ALL_CHOICE, a choice of 1 selects the entire set 0 .. N_CHOICES-1.
     + The user chooses k by typing k+IS_ALL_CHOICE+1.

   The user is not allowed to choose more than MAX_RESULTS values.

   ANNOTATION_SUFFIX, if present, is used to annotate the input
   prompts (for use with the -f switch).  */

static int
get_selections (int *choices, int n_choices, int max_results,
		int is_all_choice, const char *annotation_suffix)
{
  const char *args;
  const char *prompt;
  int n_chosen;
  int first_choice = is_all_choice ? 2 : 1;

  prompt = getenv ("PS2");
  if (prompt == NULL)
    prompt = "> ";

  args = command_line_input (prompt, annotation_suffix);

  if (args == NULL)
    error_no_arg (_("one or more choice numbers"));

  n_chosen = 0;

  /* Set choices[0 .. n_chosen-1] to the users' choices in ascending
     order, as given in args.  Choices are validated.  */
  while (1)
    {
      char *args2;
      int choice, j;

      args = skip_spaces (args);
      if (*args == '\0' && n_chosen == 0)
	error_no_arg (_("one or more choice numbers"));
      else if (*args == '\0')
	break;

      choice = strtol (args, &args2, 10);
      if (args == args2 || choice < 0
	  || choice > n_choices + first_choice - 1)
	error (_("Argument must be choice number"));
      args = args2;

      if (choice == 0)
	error (_("cancelled"));

      if (choice < first_choice)
	{
	  n_chosen = n_choices;
	  for (j = 0; j < n_choices; j += 1)
	    choices[j] = j;
	  break;
	}
      choice -= first_choice;

      for (j = n_chosen - 1; j >= 0 && choice < choices[j]; j -= 1)
	{
	}

      if (j < 0 || choice != choices[j])
	{
	  int k;

	  for (k = n_chosen - 1; k > j; k -= 1)
	    choices[k + 1] = choices[k];
	  choices[j + 1] = choice;
	  n_chosen += 1;
	}
    }

  if (n_chosen > max_results)
    error (_("Select no more than %d of the above"), max_results);

  return n_chosen;
}

/* Given a list of NSYMS symbols in SYMS, select up to MAX_RESULTS>0
   by asking the user (if necessary), returning the number selected,
   and setting the first elements of SYMS items.  Error if no symbols
   selected.  */

/* NOTE: Adapted from decode_line_2 in symtab.c, with which it ought
   to be re-integrated one of these days.  */

static int
user_select_syms (struct block_symbol *syms, int nsyms, int max_results)
{
  int i;
  int *chosen = XALLOCAVEC (int , nsyms);
  int n_chosen;
  int first_choice = (max_results == 1) ? 1 : 2;
  const char *select_mode = multiple_symbols_select_mode ();

  if (max_results < 1)
    error (_("Request to select 0 symbols!"));
  if (nsyms <= 1)
    return nsyms;

  if (select_mode == multiple_symbols_cancel)
    error (_("\
canceled because the command is ambiguous\n\
See set/show multiple-symbol."));

  /* If select_mode is "all", then return all possible symbols.
     Only do that if more than one symbol can be selected, of course.
     Otherwise, display the menu as usual.  */
  if (select_mode == multiple_symbols_all && max_results > 1)
    return nsyms;

  printf_filtered (_("[0] cancel\n"));
  if (max_results > 1)
    printf_filtered (_("[1] all\n"));

  sort_choices (syms, nsyms);

  for (i = 0; i < nsyms; i += 1)
    {
      if (syms[i].symbol == NULL)
	continue;

      if (SYMBOL_CLASS (syms[i].symbol) == LOC_BLOCK)
	{
	  struct symtab_and_line sal =
	    find_function_start_sal (syms[i].symbol, 1);

	  printf_filtered ("[%d] ", i + first_choice);
	  ada_print_symbol_signature (gdb_stdout, syms[i].symbol,
				      &type_print_raw_options);
	  if (sal.symtab == NULL)
	    printf_filtered (_(" at %p[<no source file available>%p]:%d\n"),
			     metadata_style.style ().ptr (), nullptr, sal.line);
	  else
	    printf_filtered
	      (_(" at %ps:%d\n"),
	       styled_string (file_name_style.style (),
			      symtab_to_filename_for_display (sal.symtab)),
	       sal.line);
	  continue;
	}
      else
	{
	  int is_enumeral =
	    (SYMBOL_CLASS (syms[i].symbol) == LOC_CONST
	     && SYMBOL_TYPE (syms[i].symbol) != NULL
	     && SYMBOL_TYPE (syms[i].symbol)->code () == TYPE_CODE_ENUM);
	  struct symtab *symtab = NULL;

	  if (SYMBOL_OBJFILE_OWNED (syms[i].symbol))
	    symtab = symbol_symtab (syms[i].symbol);

	  if (SYMBOL_LINE (syms[i].symbol) != 0 && symtab != NULL)
	    {
	      printf_filtered ("[%d] ", i + first_choice);
	      ada_print_symbol_signature (gdb_stdout, syms[i].symbol,
					  &type_print_raw_options);
	      printf_filtered (_(" at %s:%d\n"),
			       symtab_to_filename_for_display (symtab),
			       SYMBOL_LINE (syms[i].symbol));
	    }
	  else if (is_enumeral
		   && SYMBOL_TYPE (syms[i].symbol)->name () != NULL)
	    {
	      printf_filtered (("[%d] "), i + first_choice);
	      ada_print_type (SYMBOL_TYPE (syms[i].symbol), NULL,
			      gdb_stdout, -1, 0, &type_print_raw_options);
	      printf_filtered (_("'(%s) (enumeral)\n"),
			       syms[i].symbol->print_name ());
	    }
	  else
	    {
	      printf_filtered ("[%d] ", i + first_choice);
	      ada_print_symbol_signature (gdb_stdout, syms[i].symbol,
					  &type_print_raw_options);

	      if (symtab != NULL)
		printf_filtered (is_enumeral
				 ? _(" in %s (enumeral)\n")
				 : _(" at %s:?\n"),
				 symtab_to_filename_for_display (symtab));
	      else
		printf_filtered (is_enumeral
				 ? _(" (enumeral)\n")
				 : _(" at ?\n"));
	    }
	}
    }

  n_chosen = get_selections (chosen, nsyms, max_results, max_results > 1,
			     "overload-choice");

  for (i = 0; i < n_chosen; i += 1)
    syms[i] = syms[chosen[i]];

  return n_chosen;
}

/* See ada-lang.h.  */

block_symbol
ada_find_operator_symbol (enum exp_opcode op, bool parse_completion,
			  int nargs, value *argvec[])
{
  if (possible_user_operator_p (op, argvec))
    {
      std::vector<struct block_symbol> candidates
	= ada_lookup_symbol_list (ada_decoded_op_name (op),
				  NULL, VAR_DOMAIN);

      int i = ada_resolve_function (candidates, argvec,
				    nargs, ada_decoded_op_name (op), NULL,
				    parse_completion);
      if (i >= 0)
	return candidates[i];
    }
  return {};
}

/* See ada-lang.h.  */

block_symbol
ada_resolve_funcall (struct symbol *sym, const struct block *block,
		     struct type *context_type,
		     bool parse_completion,
		     int nargs, value *argvec[],
		     innermost_block_tracker *tracker)
{
  std::vector<struct block_symbol> candidates
    = ada_lookup_symbol_list (sym->linkage_name (), block, VAR_DOMAIN);

  int i;
  if (candidates.size () == 1)
    i = 0;
  else
    {
      i = ada_resolve_function
	(candidates,
	 argvec, nargs,
	 sym->linkage_name (),
	 context_type, parse_completion);
      if (i < 0)
	error (_("Could not find a match for %s"), sym->print_name ());
    }

  tracker->update (candidates[i]);
  return candidates[i];
}

/* Resolve a mention of a name where the context type is an
   enumeration type.  */

static int
ada_resolve_enum (std::vector<struct block_symbol> &syms,
		  const char *name, struct type *context_type,
		  bool parse_completion)
{
  gdb_assert (context_type->code () == TYPE_CODE_ENUM);
  context_type = ada_check_typedef (context_type);

  for (int i = 0; i < syms.size (); ++i)
    {
      /* We already know the name matches, so we're just looking for
	 an element of the correct enum type.  */
      if (ada_check_typedef (SYMBOL_TYPE (syms[i].symbol)) == context_type)
	return i;
    }

  error (_("No name '%s' in enumeration type '%s'"), name,
	 ada_type_name (context_type));
}

/* See ada-lang.h.  */

block_symbol
ada_resolve_variable (struct symbol *sym, const struct block *block,
		      struct type *context_type,
		      bool parse_completion,
		      int deprocedure_p,
		      innermost_block_tracker *tracker)
{
  std::vector<struct block_symbol> candidates
    = ada_lookup_symbol_list (sym->linkage_name (), block, VAR_DOMAIN);

  if (std::any_of (candidates.begin (),
		   candidates.end (),
		   [] (block_symbol &bsym)
		   {
		     switch (SYMBOL_CLASS (bsym.symbol))
		       {
		       case LOC_REGISTER:
		       case LOC_ARG:
		       case LOC_REF_ARG:
		       case LOC_REGPARM_ADDR:
		       case LOC_LOCAL:
		       case LOC_COMPUTED:
			 return true;
		       default:
			 return false;
		       }
		   }))
    {
      /* Types tend to get re-introduced locally, so if there
	 are any local symbols that are not types, first filter
	 out all types.  */
      candidates.erase
	(std::remove_if
	 (candidates.begin (),
	  candidates.end (),
	  [] (block_symbol &bsym)
	  {
	    return SYMBOL_CLASS (bsym.symbol) == LOC_TYPEDEF;
	  }),
	 candidates.end ());
    }

  /* Filter out artificial symbols.  */
  candidates.erase
    (std::remove_if
     (candidates.begin (),
      candidates.end (),
      [] (block_symbol &bsym)
      {
       return bsym.symbol->artificial;
      }),
     candidates.end ());

  int i;
  if (candidates.empty ())
    error (_("No definition found for %s"), sym->print_name ());
  else if (candidates.size () == 1)
    i = 0;
  else if (context_type != nullptr
	   && context_type->code () == TYPE_CODE_ENUM)
    i = ada_resolve_enum (candidates, sym->linkage_name (), context_type,
			  parse_completion);
  else if (deprocedure_p && !is_nonfunction (candidates))
    {
      i = ada_resolve_function
	(candidates, NULL, 0,
	 sym->linkage_name (),
	 context_type, parse_completion);
      if (i < 0)
	error (_("Could not find a match for %s"), sym->print_name ());
    }
  else
    {
      printf_filtered (_("Multiple matches for %s\n"), sym->print_name ());
      user_select_syms (candidates.data (), candidates.size (), 1);
      i = 0;
    }

  tracker->update (candidates[i]);
  return candidates[i];
}

/* Return non-zero if formal type FTYPE matches actual type ATYPE.  */
/* The term "match" here is rather loose.  The match is heuristic and
   liberal.  */

static int
ada_type_match (struct type *ftype, struct type *atype)
{
  ftype = ada_check_typedef (ftype);
  atype = ada_check_typedef (atype);

  if (ftype->code () == TYPE_CODE_REF)
    ftype = TYPE_TARGET_TYPE (ftype);
  if (atype->code () == TYPE_CODE_REF)
    atype = TYPE_TARGET_TYPE (atype);

  switch (ftype->code ())
    {
    default:
      return ftype->code () == atype->code ();
    case TYPE_CODE_PTR:
      if (atype->code () != TYPE_CODE_PTR)
	return 0;
      atype = TYPE_TARGET_TYPE (atype);
      /* This can only happen if the actual argument is 'null'.  */
      if (atype->code () == TYPE_CODE_INT && TYPE_LENGTH (atype) == 0)
	return 1;
      return ada_type_match (TYPE_TARGET_TYPE (ftype), atype);
    case TYPE_CODE_INT:
    case TYPE_CODE_ENUM:
    case TYPE_CODE_RANGE:
      switch (atype->code ())
	{
	case TYPE_CODE_INT:
	case TYPE_CODE_ENUM:
	case TYPE_CODE_RANGE:
	  return 1;
	default:
	  return 0;
	}

    case TYPE_CODE_ARRAY:
      return (atype->code () == TYPE_CODE_ARRAY
	      || ada_is_array_descriptor_type (atype));

    case TYPE_CODE_STRUCT:
      if (ada_is_array_descriptor_type (ftype))
	return (atype->code () == TYPE_CODE_ARRAY
		|| ada_is_array_descriptor_type (atype));
      else
	return (atype->code () == TYPE_CODE_STRUCT
		&& !ada_is_array_descriptor_type (atype));

    case TYPE_CODE_UNION:
    case TYPE_CODE_FLT:
      return (atype->code () == ftype->code ());
    }
}

/* Return non-zero if the formals of FUNC "sufficiently match" the
   vector of actual argument types ACTUALS of size N_ACTUALS.  FUNC
   may also be an enumeral, in which case it is treated as a 0-
   argument function.  */

static int
ada_args_match (struct symbol *func, struct value **actuals, int n_actuals)
{
  int i;
  struct type *func_type = SYMBOL_TYPE (func);

  if (SYMBOL_CLASS (func) == LOC_CONST
      && func_type->code () == TYPE_CODE_ENUM)
    return (n_actuals == 0);
  else if (func_type == NULL || func_type->code () != TYPE_CODE_FUNC)
    return 0;

  if (func_type->num_fields () != n_actuals)
    return 0;

  for (i = 0; i < n_actuals; i += 1)
    {
      if (actuals[i] == NULL)
	return 0;
      else
	{
	  struct type *ftype = ada_check_typedef (func_type->field (i).type ());
	  struct type *atype = ada_check_typedef (value_type (actuals[i]));

	  if (!ada_type_match (ftype, atype))
	    return 0;
	}
    }
  return 1;
}

/* False iff function type FUNC_TYPE definitely does not produce a value
   compatible with type CONTEXT_TYPE.  Conservatively returns 1 if
   FUNC_TYPE is not a valid function type with a non-null return type
   or an enumerated type.  A null CONTEXT_TYPE indicates any non-void type.  */

static int
return_match (struct type *func_type, struct type *context_type)
{
  struct type *return_type;

  if (func_type == NULL)
    return 1;

  if (func_type->code () == TYPE_CODE_FUNC)
    return_type = get_base_type (TYPE_TARGET_TYPE (func_type));
  else
    return_type = get_base_type (func_type);
  if (return_type == NULL)
    return 1;

  context_type = get_base_type (context_type);

  if (return_type->code () == TYPE_CODE_ENUM)
    return context_type == NULL || return_type == context_type;
  else if (context_type == NULL)
    return return_type->code () != TYPE_CODE_VOID;
  else
    return return_type->code () == context_type->code ();
}


/* Returns the index in SYMS that contains the symbol for the
   function (if any) that matches the types of the NARGS arguments in
   ARGS.  If CONTEXT_TYPE is non-null and there is at least one match
   that returns that type, then eliminate matches that don't.  If
   CONTEXT_TYPE is void and there is at least one match that does not
   return void, eliminate all matches that do.

   Asks the user if there is more than one match remaining.  Returns -1
   if there is no such symbol or none is selected.  NAME is used
   solely for messages.  May re-arrange and modify SYMS in
   the process; the index returned is for the modified vector.  */

static int
ada_resolve_function (std::vector<struct block_symbol> &syms,
		      struct value **args, int nargs,
		      const char *name, struct type *context_type,
		      bool parse_completion)
{
  int fallback;
  int k;
  int m;                        /* Number of hits */

  m = 0;
  /* In the first pass of the loop, we only accept functions matching
     context_type.  If none are found, we add a second pass of the loop
     where every function is accepted.  */
  for (fallback = 0; m == 0 && fallback < 2; fallback++)
    {
      for (k = 0; k < syms.size (); k += 1)
	{
	  struct type *type = ada_check_typedef (SYMBOL_TYPE (syms[k].symbol));

	  if (ada_args_match (syms[k].symbol, args, nargs)
	      && (fallback || return_match (type, context_type)))
	    {
	      syms[m] = syms[k];
	      m += 1;
	    }
	}
    }

  /* If we got multiple matches, ask the user which one to use.  Don't do this
     interactive thing during completion, though, as the purpose of the
     completion is providing a list of all possible matches.  Prompting the
     user to filter it down would be completely unexpected in this case.  */
  if (m == 0)
    return -1;
  else if (m > 1 && !parse_completion)
    {
      printf_filtered (_("Multiple matches for %s\n"), name);
      user_select_syms (syms.data (), m, 1);
      return 0;
    }
  return 0;
}

/* Type-class predicates */

/* True iff TYPE is numeric (i.e., an INT, RANGE (of numeric type),
   or FLOAT).  */

static int
numeric_type_p (struct type *type)
{
  if (type == NULL)
    return 0;
  else
    {
      switch (type->code ())
	{
	case TYPE_CODE_INT:
	case TYPE_CODE_FLT:
	case TYPE_CODE_FIXED_POINT:
	  return 1;
	case TYPE_CODE_RANGE:
	  return (type == TYPE_TARGET_TYPE (type)
		  || numeric_type_p (TYPE_TARGET_TYPE (type)));
	default:
	  return 0;
	}
    }
}

/* True iff TYPE is integral (an INT or RANGE of INTs).  */

static int
integer_type_p (struct type *type)
{
  if (type == NULL)
    return 0;
  else
    {
      switch (type->code ())
	{
	case TYPE_CODE_INT:
	  return 1;
	case TYPE_CODE_RANGE:
	  return (type == TYPE_TARGET_TYPE (type)
		  || integer_type_p (TYPE_TARGET_TYPE (type)));
	default:
	  return 0;
	}
    }
}

/* True iff TYPE is scalar (INT, RANGE, FLOAT, ENUM).  */

static int
scalar_type_p (struct type *type)
{
  if (type == NULL)
    return 0;
  else
    {
      switch (type->code ())
	{
	case TYPE_CODE_INT:
	case TYPE_CODE_RANGE:
	case TYPE_CODE_ENUM:
	case TYPE_CODE_FLT:
	case TYPE_CODE_FIXED_POINT:
	  return 1;
	default:
	  return 0;
	}
    }
}

/* True iff TYPE is discrete (INT, RANGE, ENUM).  */

static int
discrete_type_p (struct type *type)
{
  if (type == NULL)
    return 0;
  else
    {
      switch (type->code ())
	{
	case TYPE_CODE_INT:
	case TYPE_CODE_RANGE:
	case TYPE_CODE_ENUM:
	case TYPE_CODE_BOOL:
	  return 1;
	default:
	  return 0;
	}
    }
}

/* Returns non-zero if OP with operands in the vector ARGS could be
   a user-defined function.  Errs on the side of pre-defined operators
   (i.e., result 0).  */

static int
possible_user_operator_p (enum exp_opcode op, struct value *args[])
{
  struct type *type0 =
    (args[0] == NULL) ? NULL : ada_check_typedef (value_type (args[0]));
  struct type *type1 =
    (args[1] == NULL) ? NULL : ada_check_typedef (value_type (args[1]));

  if (type0 == NULL)
    return 0;

  switch (op)
    {
    default:
      return 0;

    case BINOP_ADD:
    case BINOP_SUB:
    case BINOP_MUL:
    case BINOP_DIV:
      return (!(numeric_type_p (type0) && numeric_type_p (type1)));

    case BINOP_REM:
    case BINOP_MOD:
    case BINOP_BITWISE_AND:
    case BINOP_BITWISE_IOR:
    case BINOP_BITWISE_XOR:
      return (!(integer_type_p (type0) && integer_type_p (type1)));

    case BINOP_EQUAL:
    case BINOP_NOTEQUAL:
    case BINOP_LESS:
    case BINOP_GTR:
    case BINOP_LEQ:
    case BINOP_GEQ:
      return (!(scalar_type_p (type0) && scalar_type_p (type1)));

    case BINOP_CONCAT:
      return !ada_is_array_type (type0) || !ada_is_array_type (type1);

    case BINOP_EXP:
      return (!(numeric_type_p (type0) && integer_type_p (type1)));

    case UNOP_NEG:
    case UNOP_PLUS:
    case UNOP_LOGICAL_NOT:
    case UNOP_ABS:
      return (!numeric_type_p (type0));

    }
}

				/* Renaming */

/* NOTES: 

   1. In the following, we assume that a renaming type's name may
      have an ___XD suffix.  It would be nice if this went away at some
      point.
   2. We handle both the (old) purely type-based representation of 
      renamings and the (new) variable-based encoding.  At some point,
      it is devoutly to be hoped that the former goes away 
      (FIXME: hilfinger-2007-07-09).
   3. Subprogram renamings are not implemented, although the XRS
      suffix is recognized (FIXME: hilfinger-2007-07-09).  */

/* If SYM encodes a renaming, 

       <renaming> renames <renamed entity>,

   sets *LEN to the length of the renamed entity's name,
   *RENAMED_ENTITY to that name (not null-terminated), and *RENAMING_EXPR to
   the string describing the subcomponent selected from the renamed
   entity.  Returns ADA_NOT_RENAMING if SYM does not encode a renaming
   (in which case, the values of *RENAMED_ENTITY, *LEN, and *RENAMING_EXPR
   are undefined).  Otherwise, returns a value indicating the category
   of entity renamed: an object (ADA_OBJECT_RENAMING), exception
   (ADA_EXCEPTION_RENAMING), package (ADA_PACKAGE_RENAMING), or
   subprogram (ADA_SUBPROGRAM_RENAMING).  Does no allocation; the
   strings returned in *RENAMED_ENTITY and *RENAMING_EXPR should not be
   deallocated.  The values of RENAMED_ENTITY, LEN, or RENAMING_EXPR
   may be NULL, in which case they are not assigned.

   [Currently, however, GCC does not generate subprogram renamings.]  */

enum ada_renaming_category
ada_parse_renaming (struct symbol *sym,
		    const char **renamed_entity, int *len, 
		    const char **renaming_expr)
{
  enum ada_renaming_category kind;
  const char *info;
  const char *suffix;

  if (sym == NULL)
    return ADA_NOT_RENAMING;
  switch (SYMBOL_CLASS (sym)) 
    {
    default:
      return ADA_NOT_RENAMING;
    case LOC_LOCAL:
    case LOC_STATIC:
    case LOC_COMPUTED:
    case LOC_OPTIMIZED_OUT:
      info = strstr (sym->linkage_name (), "___XR");
      if (info == NULL)
	return ADA_NOT_RENAMING;
      switch (info[5])
	{
	case '_':
	  kind = ADA_OBJECT_RENAMING;
	  info += 6;
	  break;
	case 'E':
	  kind = ADA_EXCEPTION_RENAMING;
	  info += 7;
	  break;
	case 'P':
	  kind = ADA_PACKAGE_RENAMING;
	  info += 7;
	  break;
	case 'S':
	  kind = ADA_SUBPROGRAM_RENAMING;
	  info += 7;
	  break;
	default:
	  return ADA_NOT_RENAMING;
	}
    }

  if (renamed_entity != NULL)
    *renamed_entity = info;
  suffix = strstr (info, "___XE");
  if (suffix == NULL || suffix == info)
    return ADA_NOT_RENAMING;
  if (len != NULL)
    *len = strlen (info) - strlen (suffix);
  suffix += 5;
  if (renaming_expr != NULL)
    *renaming_expr = suffix;
  return kind;
}

/* Compute the value of the given RENAMING_SYM, which is expected to
   be a symbol encoding a renaming expression.  BLOCK is the block
   used to evaluate the renaming.  */

static struct value *
ada_read_renaming_var_value (struct symbol *renaming_sym,
			     const struct block *block)
{
  const char *sym_name;

  sym_name = renaming_sym->linkage_name ();
  expression_up expr = parse_exp_1 (&sym_name, 0, block, 0);
  return evaluate_expression (expr.get ());
}


				/* Evaluation: Function Calls */

/* Return an lvalue containing the value VAL.  This is the identity on
   lvalues, and otherwise has the side-effect of allocating memory
   in the inferior where a copy of the value contents is copied.  */

static struct value *
ensure_lval (struct value *val)
{
  if (VALUE_LVAL (val) == not_lval
      || VALUE_LVAL (val) == lval_internalvar)
    {
      int len = TYPE_LENGTH (ada_check_typedef (value_type (val)));
      const CORE_ADDR addr =
	value_as_long (value_allocate_space_in_inferior (len));

      VALUE_LVAL (val) = lval_memory;
      set_value_address (val, addr);
      write_memory (addr, value_contents (val), len);
    }

  return val;
}

/* Given ARG, a value of type (pointer or reference to a)*
   structure/union, extract the component named NAME from the ultimate
   target structure/union and return it as a value with its
   appropriate type.

   The routine searches for NAME among all members of the structure itself
   and (recursively) among all members of any wrapper members
   (e.g., '_parent').

   If NO_ERR, then simply return NULL in case of error, rather than
   calling error.  */

static struct value *
ada_value_struct_elt (struct value *arg, const char *name, int no_err)
{
  struct type *t, *t1;
  struct value *v;
  int check_tag;

  v = NULL;
  t1 = t = ada_check_typedef (value_type (arg));
  if (t->code () == TYPE_CODE_REF)
    {
      t1 = TYPE_TARGET_TYPE (t);
      if (t1 == NULL)
	goto BadValue;
      t1 = ada_check_typedef (t1);
      if (t1->code () == TYPE_CODE_PTR)
	{
	  arg = coerce_ref (arg);
	  t = t1;
	}
    }

  while (t->code () == TYPE_CODE_PTR)
    {
      t1 = TYPE_TARGET_TYPE (t);
      if (t1 == NULL)
	goto BadValue;
      t1 = ada_check_typedef (t1);
      if (t1->code () == TYPE_CODE_PTR)
	{
	  arg = value_ind (arg);
	  t = t1;
	}
      else
	break;
    }

  if (t1->code () != TYPE_CODE_STRUCT && t1->code () != TYPE_CODE_UNION)
    goto BadValue;

  if (t1 == t)
    v = ada_search_struct_field (name, arg, 0, t);
  else
    {
      int bit_offset, bit_size, byte_offset;
      struct type *field_type;
      CORE_ADDR address;

      if (t->code () == TYPE_CODE_PTR)
	address = value_address (ada_value_ind (arg));
      else
	address = value_address (ada_coerce_ref (arg));

      /* Check to see if this is a tagged type.  We also need to handle
	 the case where the type is a reference to a tagged type, but
	 we have to be careful to exclude pointers to tagged types.
	 The latter should be shown as usual (as a pointer), whereas
	 a reference should mostly be transparent to the user.  */

      if (ada_is_tagged_type (t1, 0)
	  || (t1->code () == TYPE_CODE_REF
	      && ada_is_tagged_type (TYPE_TARGET_TYPE (t1), 0)))
	{
	  /* We first try to find the searched field in the current type.
	     If not found then let's look in the fixed type.  */

	  if (!find_struct_field (name, t1, 0,
				  &field_type, &byte_offset, &bit_offset,
				  &bit_size, NULL))
	    check_tag = 1;
	  else
	    check_tag = 0;
	}
      else
	check_tag = 0;

      /* Convert to fixed type in all cases, so that we have proper
	 offsets to each field in unconstrained record types.  */
      t1 = ada_to_fixed_type (ada_get_base_type (t1), NULL,
			      address, NULL, check_tag);

      /* Resolve the dynamic type as well.  */
      arg = value_from_contents_and_address (t1, nullptr, address);
      t1 = value_type (arg);

      if (find_struct_field (name, t1, 0,
			     &field_type, &byte_offset, &bit_offset,
			     &bit_size, NULL))
	{
	  if (bit_size != 0)
	    {
	      if (t->code () == TYPE_CODE_REF)
		arg = ada_coerce_ref (arg);
	      else
		arg = ada_value_ind (arg);
	      v = ada_value_primitive_packed_val (arg, NULL, byte_offset,
						  bit_offset, bit_size,
						  field_type);
	    }
	  else
	    v = value_at_lazy (field_type, address + byte_offset);
	}
    }

  if (v != NULL || no_err)
    return v;
  else
    error (_("There is no member named %s."), name);

 BadValue:
  if (no_err)
    return NULL;
  else
    error (_("Attempt to extract a component of "
	     "a value that is not a record."));
}

/* Return the value ACTUAL, converted to be an appropriate value for a
   formal of type FORMAL_TYPE.  Use *SP as a stack pointer for
   allocating any necessary descriptors (fat pointers), or copies of
   values not residing in memory, updating it as needed.  */

struct value *
ada_convert_actual (struct value *actual, struct type *formal_type0)
{
  struct type *actual_type = ada_check_typedef (value_type (actual));
  struct type *formal_type = ada_check_typedef (formal_type0);
  struct type *formal_target =
    formal_type->code () == TYPE_CODE_PTR
    ? ada_check_typedef (TYPE_TARGET_TYPE (formal_type)) : formal_type;
  struct type *actual_target =
    actual_type->code () == TYPE_CODE_PTR
    ? ada_check_typedef (TYPE_TARGET_TYPE (actual_type)) : actual_type;

  if (ada_is_array_descriptor_type (formal_target)
      && actual_target->code () == TYPE_CODE_ARRAY)
    return make_array_descriptor (formal_type, actual);
  else if (formal_type->code () == TYPE_CODE_PTR
	   || formal_type->code () == TYPE_CODE_REF)
    {
      struct value *result;

      if (formal_target->code () == TYPE_CODE_ARRAY
	  && ada_is_array_descriptor_type (actual_target))
	result = desc_data (actual);
      else if (formal_type->code () != TYPE_CODE_PTR)
	{
	  if (VALUE_LVAL (actual) != lval_memory)
	    {
	      struct value *val;

	      actual_type = ada_check_typedef (value_type (actual));
	      val = allocate_value (actual_type);
	      memcpy ((char *) value_contents_raw (val),
		      (char *) value_contents (actual),
		      TYPE_LENGTH (actual_type));
	      actual = ensure_lval (val);
	    }
	  result = value_addr (actual);
	}
      else
	return actual;
      return value_cast_pointers (formal_type, result, 0);
    }
  else if (actual_type->code () == TYPE_CODE_PTR)
    return ada_value_ind (actual);
  else if (ada_is_aligner_type (formal_type))
    {
      /* We need to turn this parameter into an aligner type
	 as well.  */
      struct value *aligner = allocate_value (formal_type);
      struct value *component = ada_value_struct_elt (aligner, "F", 0);

      value_assign_to_component (aligner, component, actual);
      return aligner;
    }

  return actual;
}

/* Convert VALUE (which must be an address) to a CORE_ADDR that is a pointer of
   type TYPE.  This is usually an inefficient no-op except on some targets
   (such as AVR) where the representation of a pointer and an address
   differs.  */

static CORE_ADDR
value_pointer (struct value *value, struct type *type)
{
  unsigned len = TYPE_LENGTH (type);
  gdb_byte *buf = (gdb_byte *) alloca (len);
  CORE_ADDR addr;

  addr = value_address (value);
  gdbarch_address_to_pointer (type->arch (), type, buf, addr);
  addr = extract_unsigned_integer (buf, len, type_byte_order (type));
  return addr;
}


/* Push a descriptor of type TYPE for array value ARR on the stack at
   *SP, updating *SP to reflect the new descriptor.  Return either
   an lvalue representing the new descriptor, or (if TYPE is a pointer-
   to-descriptor type rather than a descriptor type), a struct value *
   representing a pointer to this descriptor.  */

static struct value *
make_array_descriptor (struct type *type, struct value *arr)
{
  struct type *bounds_type = desc_bounds_type (type);
  struct type *desc_type = desc_base_type (type);
  struct value *descriptor = allocate_value (desc_type);
  struct value *bounds = allocate_value (bounds_type);
  int i;

  for (i = ada_array_arity (ada_check_typedef (value_type (arr)));
       i > 0; i -= 1)
    {
      modify_field (value_type (bounds), value_contents_writeable (bounds),
		    ada_array_bound (arr, i, 0),
		    desc_bound_bitpos (bounds_type, i, 0),
		    desc_bound_bitsize (bounds_type, i, 0));
      modify_field (value_type (bounds), value_contents_writeable (bounds),
		    ada_array_bound (arr, i, 1),
		    desc_bound_bitpos (bounds_type, i, 1),
		    desc_bound_bitsize (bounds_type, i, 1));
    }

  bounds = ensure_lval (bounds);

  modify_field (value_type (descriptor),
		value_contents_writeable (descriptor),
		value_pointer (ensure_lval (arr),
			       desc_type->field (0).type ()),
		fat_pntr_data_bitpos (desc_type),
		fat_pntr_data_bitsize (desc_type));

  modify_field (value_type (descriptor),
		value_contents_writeable (descriptor),
		value_pointer (bounds,
			       desc_type->field (1).type ()),
		fat_pntr_bounds_bitpos (desc_type),
		fat_pntr_bounds_bitsize (desc_type));

  descriptor = ensure_lval (descriptor);

  if (type->code () == TYPE_CODE_PTR)
    return value_addr (descriptor);
  else
    return descriptor;
}

				/* Symbol Cache Module */

/* Performance measurements made as of 2010-01-15 indicate that
   this cache does bring some noticeable improvements.  Depending
   on the type of entity being printed, the cache can make it as much
   as an order of magnitude faster than without it.

   The descriptive type DWARF extension has significantly reduced
   the need for this cache, at least when DWARF is being used.  However,
   even in this case, some expensive name-based symbol searches are still
   sometimes necessary - to find an XVZ variable, mostly.  */

/* Return the symbol cache associated to the given program space PSPACE.
   If not allocated for this PSPACE yet, allocate and initialize one.  */

static struct ada_symbol_cache *
ada_get_symbol_cache (struct program_space *pspace)
{
  struct ada_pspace_data *pspace_data = get_ada_pspace_data (pspace);

  if (pspace_data->sym_cache == nullptr)
    pspace_data->sym_cache.reset (new ada_symbol_cache);

  return pspace_data->sym_cache.get ();
}

/* Clear all entries from the symbol cache.  */

static void
ada_clear_symbol_cache ()
{
  struct ada_pspace_data *pspace_data
    = get_ada_pspace_data (current_program_space);

  if (pspace_data->sym_cache != nullptr)
    pspace_data->sym_cache.reset ();
}

/* Search our cache for an entry matching NAME and DOMAIN.
   Return it if found, or NULL otherwise.  */

static struct cache_entry **
find_entry (const char *name, domain_enum domain)
{
  struct ada_symbol_cache *sym_cache
    = ada_get_symbol_cache (current_program_space);
  int h = msymbol_hash (name) % HASH_SIZE;
  struct cache_entry **e;

  for (e = &sym_cache->root[h]; *e != NULL; e = &(*e)->next)
    {
      if (domain == (*e)->domain && strcmp (name, (*e)->name) == 0)
	return e;
    }
  return NULL;
}

/* Search the symbol cache for an entry matching NAME and DOMAIN.
   Return 1 if found, 0 otherwise.

   If an entry was found and SYM is not NULL, set *SYM to the entry's
   SYM.  Same principle for BLOCK if not NULL.  */

static int
lookup_cached_symbol (const char *name, domain_enum domain,
		      struct symbol **sym, const struct block **block)
{
  struct cache_entry **e = find_entry (name, domain);

  if (e == NULL)
    return 0;
  if (sym != NULL)
    *sym = (*e)->sym;
  if (block != NULL)
    *block = (*e)->block;
  return 1;
}

/* Assuming that (SYM, BLOCK) is the result of the lookup of NAME
   in domain DOMAIN, save this result in our symbol cache.  */

static void
cache_symbol (const char *name, domain_enum domain, struct symbol *sym,
	      const struct block *block)
{
  struct ada_symbol_cache *sym_cache
    = ada_get_symbol_cache (current_program_space);
  int h;
  struct cache_entry *e;

  /* Symbols for builtin types don't have a block.
     For now don't cache such symbols.  */
  if (sym != NULL && !SYMBOL_OBJFILE_OWNED (sym))
    return;

  /* If the symbol is a local symbol, then do not cache it, as a search
     for that symbol depends on the context.  To determine whether
     the symbol is local or not, we check the block where we found it
     against the global and static blocks of its associated symtab.  */
  if (sym
      && BLOCKVECTOR_BLOCK (SYMTAB_BLOCKVECTOR (symbol_symtab (sym)),
			    GLOBAL_BLOCK) != block
      && BLOCKVECTOR_BLOCK (SYMTAB_BLOCKVECTOR (symbol_symtab (sym)),
			    STATIC_BLOCK) != block)
    return;

  h = msymbol_hash (name) % HASH_SIZE;
  e = XOBNEW (&sym_cache->cache_space, cache_entry);
  e->next = sym_cache->root[h];
  sym_cache->root[h] = e;
  e->name = obstack_strdup (&sym_cache->cache_space, name);
  e->sym = sym;
  e->domain = domain;
  e->block = block;
}

				/* Symbol Lookup */

/* Return the symbol name match type that should be used used when
   searching for all symbols matching LOOKUP_NAME.

   LOOKUP_NAME is expected to be a symbol name after transformation
   for Ada lookups.  */

static symbol_name_match_type
name_match_type_from_name (const char *lookup_name)
{
  return (strstr (lookup_name, "__") == NULL
	  ? symbol_name_match_type::WILD
	  : symbol_name_match_type::FULL);
}

/* Return the result of a standard (literal, C-like) lookup of NAME in
   given DOMAIN, visible from lexical block BLOCK.  */

static struct symbol *
standard_lookup (const char *name, const struct block *block,
		 domain_enum domain)
{
  /* Initialize it just to avoid a GCC false warning.  */
  struct block_symbol sym = {};

  if (lookup_cached_symbol (name, domain, &sym.symbol, NULL))
    return sym.symbol;
  ada_lookup_encoded_symbol (name, block, domain, &sym);
  cache_symbol (name, domain, sym.symbol, sym.block);
  return sym.symbol;
}


/* Non-zero iff there is at least one non-function/non-enumeral symbol
   in the symbol fields of SYMS.  We treat enumerals as functions, 
   since they contend in overloading in the same way.  */
static int
is_nonfunction (const std::vector<struct block_symbol> &syms)
{
  for (const block_symbol &sym : syms)
    if (SYMBOL_TYPE (sym.symbol)->code () != TYPE_CODE_FUNC
	&& (SYMBOL_TYPE (sym.symbol)->code () != TYPE_CODE_ENUM
	    || SYMBOL_CLASS (sym.symbol) != LOC_CONST))
      return 1;

  return 0;
}

/* If true (non-zero), then TYPE0 and TYPE1 represent equivalent
   struct types.  Otherwise, they may not.  */

static int
equiv_types (struct type *type0, struct type *type1)
{
  if (type0 == type1)
    return 1;
  if (type0 == NULL || type1 == NULL
      || type0->code () != type1->code ())
    return 0;
  if ((type0->code () == TYPE_CODE_STRUCT
       || type0->code () == TYPE_CODE_ENUM)
      && ada_type_name (type0) != NULL && ada_type_name (type1) != NULL
      && strcmp (ada_type_name (type0), ada_type_name (type1)) == 0)
    return 1;

  return 0;
}

/* True iff SYM0 represents the same entity as SYM1, or one that is
   no more defined than that of SYM1.  */

static int
lesseq_defined_than (struct symbol *sym0, struct symbol *sym1)
{
  if (sym0 == sym1)
    return 1;
  if (SYMBOL_DOMAIN (sym0) != SYMBOL_DOMAIN (sym1)
      || SYMBOL_CLASS (sym0) != SYMBOL_CLASS (sym1))
    return 0;

  switch (SYMBOL_CLASS (sym0))
    {
    case LOC_UNDEF:
      return 1;
    case LOC_TYPEDEF:
      {
	struct type *type0 = SYMBOL_TYPE (sym0);
	struct type *type1 = SYMBOL_TYPE (sym1);
	const char *name0 = sym0->linkage_name ();
	const char *name1 = sym1->linkage_name ();
	int len0 = strlen (name0);

	return
	  type0->code () == type1->code ()
	  && (equiv_types (type0, type1)
	      || (len0 < strlen (name1) && strncmp (name0, name1, len0) == 0
		  && startswith (name1 + len0, "___XV")));
      }
    case LOC_CONST:
      return SYMBOL_VALUE (sym0) == SYMBOL_VALUE (sym1)
	&& equiv_types (SYMBOL_TYPE (sym0), SYMBOL_TYPE (sym1));

    case LOC_STATIC:
      {
	const char *name0 = sym0->linkage_name ();
	const char *name1 = sym1->linkage_name ();
	return (strcmp (name0, name1) == 0
		&& SYMBOL_VALUE_ADDRESS (sym0) == SYMBOL_VALUE_ADDRESS (sym1));
      }

    default:
      return 0;
    }
}

/* Append (SYM,BLOCK) to the end of the array of struct block_symbol
   records in RESULT.  Do nothing if SYM is a duplicate.  */

static void
add_defn_to_vec (std::vector<struct block_symbol> &result,
		 struct symbol *sym,
		 const struct block *block)
{
  /* Do not try to complete stub types, as the debugger is probably
     already scanning all symbols matching a certain name at the
     time when this function is called.  Trying to replace the stub
     type by its associated full type will cause us to restart a scan
     which may lead to an infinite recursion.  Instead, the client
     collecting the matching symbols will end up collecting several
     matches, with at least one of them complete.  It can then filter
     out the stub ones if needed.  */

  for (int i = result.size () - 1; i >= 0; i -= 1)
    {
      if (lesseq_defined_than (sym, result[i].symbol))
	return;
      else if (lesseq_defined_than (result[i].symbol, sym))
	{
	  result[i].symbol = sym;
	  result[i].block = block;
	  return;
	}
    }

  struct block_symbol info;
  info.symbol = sym;
  info.block = block;
  result.push_back (info);
}

/* Return a bound minimal symbol matching NAME according to Ada
   decoding rules.  Returns an invalid symbol if there is no such
   minimal symbol.  Names prefixed with "standard__" are handled
   specially: "standard__" is first stripped off, and only static and
   global symbols are searched.  */

struct bound_minimal_symbol
ada_lookup_simple_minsym (const char *name)
{
  struct bound_minimal_symbol result;

  memset (&result, 0, sizeof (result));

  symbol_name_match_type match_type = name_match_type_from_name (name);
  lookup_name_info lookup_name (name, match_type);

  symbol_name_matcher_ftype *match_name
    = ada_get_symbol_name_matcher (lookup_name);

  for (objfile *objfile : current_program_space->objfiles ())
    {
      for (minimal_symbol *msymbol : objfile->msymbols ())
	{
	  if (match_name (msymbol->linkage_name (), lookup_name, NULL)
	      && MSYMBOL_TYPE (msymbol) != mst_solib_trampoline)
	    {
	      result.minsym = msymbol;
	      result.objfile = objfile;
	      break;
	    }
	}
    }

  return result;
}

/* True if TYPE is definitely an artificial type supplied to a symbol
   for which no debugging information was given in the symbol file.  */

static int
is_nondebugging_type (struct type *type)
{
  const char *name = ada_type_name (type);

  return (name != NULL && strcmp (name, "<variable, no debug info>") == 0);
}

/* Return nonzero if TYPE1 and TYPE2 are two enumeration types
   that are deemed "identical" for practical purposes.

   This function assumes that TYPE1 and TYPE2 are both TYPE_CODE_ENUM
   types and that their number of enumerals is identical (in other
   words, type1->num_fields () == type2->num_fields ()).  */

static int
ada_identical_enum_types_p (struct type *type1, struct type *type2)
{
  int i;

  /* The heuristic we use here is fairly conservative.  We consider
     that 2 enumerate types are identical if they have the same
     number of enumerals and that all enumerals have the same
     underlying value and name.  */

  /* All enums in the type should have an identical underlying value.  */
  for (i = 0; i < type1->num_fields (); i++)
    if (TYPE_FIELD_ENUMVAL (type1, i) != TYPE_FIELD_ENUMVAL (type2, i))
      return 0;

  /* All enumerals should also have the same name (modulo any numerical
     suffix).  */
  for (i = 0; i < type1->num_fields (); i++)
    {
      const char *name_1 = TYPE_FIELD_NAME (type1, i);
      const char *name_2 = TYPE_FIELD_NAME (type2, i);
      int len_1 = strlen (name_1);
      int len_2 = strlen (name_2);

      ada_remove_trailing_digits (TYPE_FIELD_NAME (type1, i), &len_1);
      ada_remove_trailing_digits (TYPE_FIELD_NAME (type2, i), &len_2);
      if (len_1 != len_2
	  || strncmp (TYPE_FIELD_NAME (type1, i),
		      TYPE_FIELD_NAME (type2, i),
		      len_1) != 0)
	return 0;
    }

  return 1;
}

/* Return nonzero if all the symbols in SYMS are all enumeral symbols
   that are deemed "identical" for practical purposes.  Sometimes,
   enumerals are not strictly identical, but their types are so similar
   that they can be considered identical.

   For instance, consider the following code:

      type Color is (Black, Red, Green, Blue, White);
      type RGB_Color is new Color range Red .. Blue;

   Type RGB_Color is a subrange of an implicit type which is a copy
   of type Color. If we call that implicit type RGB_ColorB ("B" is
   for "Base Type"), then type RGB_ColorB is a copy of type Color.
   As a result, when an expression references any of the enumeral
   by name (Eg. "print green"), the expression is technically
   ambiguous and the user should be asked to disambiguate. But
   doing so would only hinder the user, since it wouldn't matter
   what choice he makes, the outcome would always be the same.
   So, for practical purposes, we consider them as the same.  */

static int
symbols_are_identical_enums (const std::vector<struct block_symbol> &syms)
{
  int i;

  /* Before performing a thorough comparison check of each type,
     we perform a series of inexpensive checks.  We expect that these
     checks will quickly fail in the vast majority of cases, and thus
     help prevent the unnecessary use of a more expensive comparison.
     Said comparison also expects us to make some of these checks
     (see ada_identical_enum_types_p).  */

  /* Quick check: All symbols should have an enum type.  */
  for (i = 0; i < syms.size (); i++)
    if (SYMBOL_TYPE (syms[i].symbol)->code () != TYPE_CODE_ENUM)
      return 0;

  /* Quick check: They should all have the same value.  */
  for (i = 1; i < syms.size (); i++)
    if (SYMBOL_VALUE (syms[i].symbol) != SYMBOL_VALUE (syms[0].symbol))
      return 0;

  /* Quick check: They should all have the same number of enumerals.  */
  for (i = 1; i < syms.size (); i++)
    if (SYMBOL_TYPE (syms[i].symbol)->num_fields ()
	!= SYMBOL_TYPE (syms[0].symbol)->num_fields ())
      return 0;

  /* All the sanity checks passed, so we might have a set of
     identical enumeration types.  Perform a more complete
     comparison of the type of each symbol.  */
  for (i = 1; i < syms.size (); i++)
    if (!ada_identical_enum_types_p (SYMBOL_TYPE (syms[i].symbol),
				     SYMBOL_TYPE (syms[0].symbol)))
      return 0;

  return 1;
}

/* Remove any non-debugging symbols in SYMS that definitely
   duplicate other symbols in the list (The only case I know of where
   this happens is when object files containing stabs-in-ecoff are
   linked with files containing ordinary ecoff debugging symbols (or no
   debugging symbols)).  Modifies SYMS to squeeze out deleted entries.  */

static void
remove_extra_symbols (std::vector<struct block_symbol> *syms)
{
  int i, j;

  /* We should never be called with less than 2 symbols, as there
     cannot be any extra symbol in that case.  But it's easy to
     handle, since we have nothing to do in that case.  */
  if (syms->size () < 2)
    return;

  i = 0;
  while (i < syms->size ())
    {
      int remove_p = 0;

      /* If two symbols have the same name and one of them is a stub type,
	 the get rid of the stub.  */

      if (SYMBOL_TYPE ((*syms)[i].symbol)->is_stub ()
	  && (*syms)[i].symbol->linkage_name () != NULL)
	{
	  for (j = 0; j < syms->size (); j++)
	    {
	      if (j != i
		  && !SYMBOL_TYPE ((*syms)[j].symbol)->is_stub ()
		  && (*syms)[j].symbol->linkage_name () != NULL
		  && strcmp ((*syms)[i].symbol->linkage_name (),
			     (*syms)[j].symbol->linkage_name ()) == 0)
		remove_p = 1;
	    }
	}

      /* Two symbols with the same name, same class and same address
	 should be identical.  */

      else if ((*syms)[i].symbol->linkage_name () != NULL
	  && SYMBOL_CLASS ((*syms)[i].symbol) == LOC_STATIC
	  && is_nondebugging_type (SYMBOL_TYPE ((*syms)[i].symbol)))
	{
	  for (j = 0; j < syms->size (); j += 1)
	    {
	      if (i != j
		  && (*syms)[j].symbol->linkage_name () != NULL
		  && strcmp ((*syms)[i].symbol->linkage_name (),
			     (*syms)[j].symbol->linkage_name ()) == 0
		  && SYMBOL_CLASS ((*syms)[i].symbol)
		       == SYMBOL_CLASS ((*syms)[j].symbol)
		  && SYMBOL_VALUE_ADDRESS ((*syms)[i].symbol)
		  == SYMBOL_VALUE_ADDRESS ((*syms)[j].symbol))
		remove_p = 1;
	    }
	}
      
      if (remove_p)
	syms->erase (syms->begin () + i);
      else
	i += 1;
    }

  /* If all the remaining symbols are identical enumerals, then
     just keep the first one and discard the rest.

     Unlike what we did previously, we do not discard any entry
     unless they are ALL identical.  This is because the symbol
     comparison is not a strict comparison, but rather a practical
     comparison.  If all symbols are considered identical, then
     we can just go ahead and use the first one and discard the rest.
     But if we cannot reduce the list to a single element, we have
     to ask the user to disambiguate anyways.  And if we have to
     present a multiple-choice menu, it's less confusing if the list
     isn't missing some choices that were identical and yet distinct.  */
  if (symbols_are_identical_enums (*syms))
    syms->resize (1);
}

/* Given a type that corresponds to a renaming entity, use the type name
   to extract the scope (package name or function name, fully qualified,
   and following the GNAT encoding convention) where this renaming has been
   defined.  */

static std::string
xget_renaming_scope (struct type *renaming_type)
{
  /* The renaming types adhere to the following convention:
     <scope>__<rename>___<XR extension>.
     So, to extract the scope, we search for the "___XR" extension,
     and then backtrack until we find the first "__".  */

  const char *name = renaming_type->name ();
  const char *suffix = strstr (name, "___XR");
  const char *last;

  /* Now, backtrack a bit until we find the first "__".  Start looking
     at suffix - 3, as the <rename> part is at least one character long.  */

  for (last = suffix - 3; last > name; last--)
    if (last[0] == '_' && last[1] == '_')
      break;

  /* Make a copy of scope and return it.  */
  return std::string (name, last);
}

/* Return nonzero if NAME corresponds to a package name.  */

static int
is_package_name (const char *name)
{
  /* Here, We take advantage of the fact that no symbols are generated
     for packages, while symbols are generated for each function.
     So the condition for NAME represent a package becomes equivalent
     to NAME not existing in our list of symbols.  There is only one
     small complication with library-level functions (see below).  */

  /* If it is a function that has not been defined at library level,
     then we should be able to look it up in the symbols.  */
  if (standard_lookup (name, NULL, VAR_DOMAIN) != NULL)
    return 0;

  /* Library-level function names start with "_ada_".  See if function
     "_ada_" followed by NAME can be found.  */

  /* Do a quick check that NAME does not contain "__", since library-level
     functions names cannot contain "__" in them.  */
  if (strstr (name, "__") != NULL)
    return 0;

  std::string fun_name = string_printf ("_ada_%s", name);

  return (standard_lookup (fun_name.c_str (), NULL, VAR_DOMAIN) == NULL);
}

/* Return nonzero if SYM corresponds to a renaming entity that is
   not visible from FUNCTION_NAME.  */

static int
old_renaming_is_invisible (const struct symbol *sym, const char *function_name)
{
  if (SYMBOL_CLASS (sym) != LOC_TYPEDEF)
    return 0;

  std::string scope = xget_renaming_scope (SYMBOL_TYPE (sym));

  /* If the rename has been defined in a package, then it is visible.  */
  if (is_package_name (scope.c_str ()))
    return 0;

  /* Check that the rename is in the current function scope by checking
     that its name starts with SCOPE.  */

  /* If the function name starts with "_ada_", it means that it is
     a library-level function.  Strip this prefix before doing the
     comparison, as the encoding for the renaming does not contain
     this prefix.  */
  if (startswith (function_name, "_ada_"))
    function_name += 5;

  return !startswith (function_name, scope.c_str ());
}

/* Remove entries from SYMS that corresponds to a renaming entity that
   is not visible from the function associated with CURRENT_BLOCK or
   that is superfluous due to the presence of more specific renaming
   information.  Places surviving symbols in the initial entries of
   SYMS.

   Rationale:
   First, in cases where an object renaming is implemented as a
   reference variable, GNAT may produce both the actual reference
   variable and the renaming encoding.  In this case, we discard the
   latter.

   Second, GNAT emits a type following a specified encoding for each renaming
   entity.  Unfortunately, STABS currently does not support the definition
   of types that are local to a given lexical block, so all renamings types
   are emitted at library level.  As a consequence, if an application
   contains two renaming entities using the same name, and a user tries to
   print the value of one of these entities, the result of the ada symbol
   lookup will also contain the wrong renaming type.

   This function partially covers for this limitation by attempting to
   remove from the SYMS list renaming symbols that should be visible
   from CURRENT_BLOCK.  However, there does not seem be a 100% reliable
   method with the current information available.  The implementation
   below has a couple of limitations (FIXME: brobecker-2003-05-12):  
   
      - When the user tries to print a rename in a function while there
	is another rename entity defined in a package:  Normally, the
	rename in the function has precedence over the rename in the
	package, so the latter should be removed from the list.  This is
	currently not the case.
	
      - This function will incorrectly remove valid renames if
	the CURRENT_BLOCK corresponds to a function which symbol name
	has been changed by an "Export" pragma.  As a consequence,
	the user will be unable to print such rename entities.  */

static void
remove_irrelevant_renamings (std::vector<struct block_symbol> *syms,
			     const struct block *current_block)
{
  struct symbol *current_function;
  const char *current_function_name;
  int i;
  int is_new_style_renaming;

  /* If there is both a renaming foo___XR... encoded as a variable and
     a simple variable foo in the same block, discard the latter.
     First, zero out such symbols, then compress.  */
  is_new_style_renaming = 0;
  for (i = 0; i < syms->size (); i += 1)
    {
      struct symbol *sym = (*syms)[i].symbol;
      const struct block *block = (*syms)[i].block;
      const char *name;
      const char *suffix;

      if (sym == NULL || SYMBOL_CLASS (sym) == LOC_TYPEDEF)
	continue;
      name = sym->linkage_name ();
      suffix = strstr (name, "___XR");

      if (suffix != NULL)
	{
	  int name_len = suffix - name;
	  int j;

	  is_new_style_renaming = 1;
	  for (j = 0; j < syms->size (); j += 1)
	    if (i != j && (*syms)[j].symbol != NULL
		&& strncmp (name, (*syms)[j].symbol->linkage_name (),
			    name_len) == 0
		&& block == (*syms)[j].block)
	      (*syms)[j].symbol = NULL;
	}
    }
  if (is_new_style_renaming)
    {
      int j, k;

      for (j = k = 0; j < syms->size (); j += 1)
	if ((*syms)[j].symbol != NULL)
	    {
	      (*syms)[k] = (*syms)[j];
	      k += 1;
	    }
      syms->resize (k);
      return;
    }

  /* Extract the function name associated to CURRENT_BLOCK.
     Abort if unable to do so.  */

  if (current_block == NULL)
    return;

  current_function = block_linkage_function (current_block);
  if (current_function == NULL)
    return;

  current_function_name = current_function->linkage_name ();
  if (current_function_name == NULL)
    return;

  /* Check each of the symbols, and remove it from the list if it is
     a type corresponding to a renaming that is out of the scope of
     the current block.  */

  i = 0;
  while (i < syms->size ())
    {
      if (ada_parse_renaming ((*syms)[i].symbol, NULL, NULL, NULL)
	  == ADA_OBJECT_RENAMING
	  && old_renaming_is_invisible ((*syms)[i].symbol,
					current_function_name))
	syms->erase (syms->begin () + i);
      else
	i += 1;
    }
}

/* Add to RESULT all symbols from BLOCK (and its super-blocks)
   whose name and domain match LOOKUP_NAME and DOMAIN respectively.

   Note: This function assumes that RESULT is empty.  */

static void
ada_add_local_symbols (std::vector<struct block_symbol> &result,
		       const lookup_name_info &lookup_name,
		       const struct block *block, domain_enum domain)
{
  while (block != NULL)
    {
      ada_add_block_symbols (result, block, lookup_name, domain, NULL);

      /* If we found a non-function match, assume that's the one.  We
	 only check this when finding a function boundary, so that we
	 can accumulate all results from intervening blocks first.  */
      if (BLOCK_FUNCTION (block) != nullptr && is_nonfunction (result))
	return;

      block = BLOCK_SUPERBLOCK (block);
    }
}

/* An object of this type is used as the callback argument when
   calling the map_matching_symbols method.  */

struct match_data
{
  explicit match_data (std::vector<struct block_symbol> *rp)
    : resultp (rp)
  {
  }
  DISABLE_COPY_AND_ASSIGN (match_data);

  bool operator() (struct block_symbol *bsym);

  struct objfile *objfile = nullptr;
  std::vector<struct block_symbol> *resultp;
  struct symbol *arg_sym = nullptr;
  bool found_sym = false;
};

/* A callback for add_nonlocal_symbols that adds symbol, found in
   BSYM, to a list of symbols.  */

bool
match_data::operator() (struct block_symbol *bsym)
{
  const struct block *block = bsym->block;
  struct symbol *sym = bsym->symbol;

  if (sym == NULL)
    {
      if (!found_sym && arg_sym != NULL)
	add_defn_to_vec (*resultp,
			 fixup_symbol_section (arg_sym, objfile),
			 block);
      found_sym = false;
      arg_sym = NULL;
    }
  else 
    {
      if (SYMBOL_CLASS (sym) == LOC_UNRESOLVED)
	return true;
      else if (SYMBOL_IS_ARGUMENT (sym))
	arg_sym = sym;
      else
	{
	  found_sym = true;
	  add_defn_to_vec (*resultp,
			   fixup_symbol_section (sym, objfile),
			   block);
	}
    }
  return true;
}

/* Helper for add_nonlocal_symbols.  Find symbols in DOMAIN which are
   targeted by renamings matching LOOKUP_NAME in BLOCK.  Add these
   symbols to RESULT.  Return whether we found such symbols.  */

static int
ada_add_block_renamings (std::vector<struct block_symbol> &result,
			 const struct block *block,
			 const lookup_name_info &lookup_name,
			 domain_enum domain)
{
  struct using_direct *renaming;
  int defns_mark = result.size ();

  symbol_name_matcher_ftype *name_match
    = ada_get_symbol_name_matcher (lookup_name);

  for (renaming = block_using (block);
       renaming != NULL;
       renaming = renaming->next)
    {
      const char *r_name;

      /* Avoid infinite recursions: skip this renaming if we are actually
	 already traversing it.

	 Currently, symbol lookup in Ada don't use the namespace machinery from
	 C++/Fortran support: skip namespace imports that use them.  */
      if (renaming->searched
	  || (renaming->import_src != NULL
	      && renaming->import_src[0] != '\0')
	  || (renaming->import_dest != NULL
	      && renaming->import_dest[0] != '\0'))
	continue;
      renaming->searched = 1;

      /* TODO: here, we perform another name-based symbol lookup, which can
	 pull its own multiple overloads.  In theory, we should be able to do
	 better in this case since, in DWARF, DW_AT_import is a DIE reference,
	 not a simple name.  But in order to do this, we would need to enhance
	 the DWARF reader to associate a symbol to this renaming, instead of a
	 name.  So, for now, we do something simpler: re-use the C++/Fortran
	 namespace machinery.  */
      r_name = (renaming->alias != NULL
		? renaming->alias
		: renaming->declaration);
      if (name_match (r_name, lookup_name, NULL))
	{
	  lookup_name_info decl_lookup_name (renaming->declaration,
					     lookup_name.match_type ());
	  ada_add_all_symbols (result, block, decl_lookup_name, domain,
			       1, NULL);
	}
      renaming->searched = 0;
    }
  return result.size () != defns_mark;
}

/* Implements compare_names, but only applying the comparision using
   the given CASING.  */

static int
compare_names_with_case (const char *string1, const char *string2,
			 enum case_sensitivity casing)
{
  while (*string1 != '\0' && *string2 != '\0')
    {
      char c1, c2;

      if (isspace (*string1) || isspace (*string2))
	return strcmp_iw_ordered (string1, string2);

      if (casing == case_sensitive_off)
	{
	  c1 = tolower (*string1);
	  c2 = tolower (*string2);
	}
      else
	{
	  c1 = *string1;
	  c2 = *string2;
	}
      if (c1 != c2)
	break;

      string1 += 1;
      string2 += 1;
    }

  switch (*string1)
    {
    case '(':
      return strcmp_iw_ordered (string1, string2);
    case '_':
      if (*string2 == '\0')
	{
	  if (is_name_suffix (string1))
	    return 0;
	  else
	    return 1;
	}
      /* FALLTHROUGH */
    default:
      if (*string2 == '(')
	return strcmp_iw_ordered (string1, string2);
      else
	{
	  if (casing == case_sensitive_off)
	    return tolower (*string1) - tolower (*string2);
	  else
	    return *string1 - *string2;
	}
    }
}

/* Compare STRING1 to STRING2, with results as for strcmp.
   Compatible with strcmp_iw_ordered in that...

       strcmp_iw_ordered (STRING1, STRING2) <= 0

   ... implies...

       compare_names (STRING1, STRING2) <= 0

   (they may differ as to what symbols compare equal).  */

static int
compare_names (const char *string1, const char *string2)
{
  int result;

  /* Similar to what strcmp_iw_ordered does, we need to perform
     a case-insensitive comparison first, and only resort to
     a second, case-sensitive, comparison if the first one was
     not sufficient to differentiate the two strings.  */

  result = compare_names_with_case (string1, string2, case_sensitive_off);
  if (result == 0)
    result = compare_names_with_case (string1, string2, case_sensitive_on);

  return result;
}

/* Convenience function to get at the Ada encoded lookup name for
   LOOKUP_NAME, as a C string.  */

static const char *
ada_lookup_name (const lookup_name_info &lookup_name)
{
  return lookup_name.ada ().lookup_name ().c_str ();
}

/* A helper for add_nonlocal_symbols.  Call expand_matching_symbols
   for OBJFILE, then walk the objfile's symtabs and update the
   results.  */

static void
map_matching_symbols (struct objfile *objfile,
		      const lookup_name_info &lookup_name,
		      bool is_wild_match,
		      domain_enum domain,
		      int global,
		      match_data &data)
{
  data.objfile = objfile;
  objfile->expand_matching_symbols (lookup_name, domain, global,
				    is_wild_match ? nullptr : compare_names);

  const int block_kind = global ? GLOBAL_BLOCK : STATIC_BLOCK;
  for (compunit_symtab *symtab : objfile->compunits ())
    {
      const struct block *block
	= BLOCKVECTOR_BLOCK (COMPUNIT_BLOCKVECTOR (symtab), block_kind);
      if (!iterate_over_symbols_terminated (block, lookup_name,
					    domain, data))
	break;
    }
}

/* Add to RESULT all non-local symbols whose name and domain match
   LOOKUP_NAME and DOMAIN respectively.  The search is performed on
   GLOBAL_BLOCK symbols if GLOBAL is non-zero, or on STATIC_BLOCK
   symbols otherwise.  */

static void
add_nonlocal_symbols (std::vector<struct block_symbol> &result,
		      const lookup_name_info &lookup_name,
		      domain_enum domain, int global)
{
  struct match_data data (&result);

  bool is_wild_match = lookup_name.ada ().wild_match_p ();

  for (objfile *objfile : current_program_space->objfiles ())
    {
      map_matching_symbols (objfile, lookup_name, is_wild_match, domain,
			    global, data);

      for (compunit_symtab *cu : objfile->compunits ())
	{
	  const struct block *global_block
	    = BLOCKVECTOR_BLOCK (COMPUNIT_BLOCKVECTOR (cu), GLOBAL_BLOCK);

	  if (ada_add_block_renamings (result, global_block, lookup_name,
				       domain))
	    data.found_sym = true;
	}
    }

  if (result.empty () && global && !is_wild_match)
    {
      const char *name = ada_lookup_name (lookup_name);
      std::string bracket_name = std::string ("<_ada_") + name + '>';
      lookup_name_info name1 (bracket_name, symbol_name_match_type::FULL);

      for (objfile *objfile : current_program_space->objfiles ())
	map_matching_symbols (objfile, name1, false, domain, global, data);
    }
}

/* Find symbols in DOMAIN matching LOOKUP_NAME, in BLOCK and, if
   FULL_SEARCH is non-zero, enclosing scope and in global scopes,
   returning the number of matches.  Add these to RESULT.

   When FULL_SEARCH is non-zero, any non-function/non-enumeral
   symbol match within the nest of blocks whose innermost member is BLOCK,
   is the one match returned (no other matches in that or
   enclosing blocks is returned).  If there are any matches in or
   surrounding BLOCK, then these alone are returned.

   Names prefixed with "standard__" are handled specially:
   "standard__" is first stripped off (by the lookup_name
   constructor), and only static and global symbols are searched.

   If MADE_GLOBAL_LOOKUP_P is non-null, set it before return to whether we had
   to lookup global symbols.  */

static void
ada_add_all_symbols (std::vector<struct block_symbol> &result,
		     const struct block *block,
		     const lookup_name_info &lookup_name,
		     domain_enum domain,
		     int full_search,
		     int *made_global_lookup_p)
{
  struct symbol *sym;

  if (made_global_lookup_p)
    *made_global_lookup_p = 0;

  /* Special case: If the user specifies a symbol name inside package
     Standard, do a non-wild matching of the symbol name without
     the "standard__" prefix.  This was primarily introduced in order
     to allow the user to specifically access the standard exceptions
     using, for instance, Standard.Constraint_Error when Constraint_Error
     is ambiguous (due to the user defining its own Constraint_Error
     entity inside its program).  */
  if (lookup_name.ada ().standard_p ())
    block = NULL;

  /* Check the non-global symbols.  If we have ANY match, then we're done.  */

  if (block != NULL)
    {
      if (full_search)
	ada_add_local_symbols (result, lookup_name, block, domain);
      else
	{
	  /* In the !full_search case we're are being called by
	     iterate_over_symbols, and we don't want to search
	     superblocks.  */
	  ada_add_block_symbols (result, block, lookup_name, domain, NULL);
	}
      if (!result.empty () || !full_search)
	return;
    }

  /* No non-global symbols found.  Check our cache to see if we have
     already performed this search before.  If we have, then return
     the same result.  */

  if (lookup_cached_symbol (ada_lookup_name (lookup_name),
			    domain, &sym, &block))
    {
      if (sym != NULL)
	add_defn_to_vec (result, sym, block);
      return;
    }

  if (made_global_lookup_p)
    *made_global_lookup_p = 1;

  /* Search symbols from all global blocks.  */
 
  add_nonlocal_symbols (result, lookup_name, domain, 1);

  /* Now add symbols from all per-file blocks if we've gotten no hits
     (not strictly correct, but perhaps better than an error).  */

  if (result.empty ())
    add_nonlocal_symbols (result, lookup_name, domain, 0);
}

/* Find symbols in DOMAIN matching LOOKUP_NAME, in BLOCK and, if FULL_SEARCH
   is non-zero, enclosing scope and in global scopes.

   Returns (SYM,BLOCK) tuples, indicating the symbols found and the
   blocks and symbol tables (if any) in which they were found.

   When full_search is non-zero, any non-function/non-enumeral
   symbol match within the nest of blocks whose innermost member is BLOCK,
   is the one match returned (no other matches in that or
   enclosing blocks is returned).  If there are any matches in or
   surrounding BLOCK, then these alone are returned.

   Names prefixed with "standard__" are handled specially: "standard__"
   is first stripped off, and only static and global symbols are searched.  */

static std::vector<struct block_symbol>
ada_lookup_symbol_list_worker (const lookup_name_info &lookup_name,
			       const struct block *block,
			       domain_enum domain,
			       int full_search)
{
  int syms_from_global_search;
  std::vector<struct block_symbol> results;

  ada_add_all_symbols (results, block, lookup_name,
		       domain, full_search, &syms_from_global_search);

  remove_extra_symbols (&results);

  if (results.empty () && full_search && syms_from_global_search)
    cache_symbol (ada_lookup_name (lookup_name), domain, NULL, NULL);

  if (results.size () == 1 && full_search && syms_from_global_search)
    cache_symbol (ada_lookup_name (lookup_name), domain,
		  results[0].symbol, results[0].block);

  remove_irrelevant_renamings (&results, block);
  return results;
}

/* Find symbols in DOMAIN matching NAME, in BLOCK and enclosing scope and
   in global scopes, returning (SYM,BLOCK) tuples.

   See ada_lookup_symbol_list_worker for further details.  */

std::vector<struct block_symbol>
ada_lookup_symbol_list (const char *name, const struct block *block,
			domain_enum domain)
{
  symbol_name_match_type name_match_type = name_match_type_from_name (name);
  lookup_name_info lookup_name (name, name_match_type);

  return ada_lookup_symbol_list_worker (lookup_name, block, domain, 1);
}

/* The result is as for ada_lookup_symbol_list with FULL_SEARCH set
   to 1, but choosing the first symbol found if there are multiple
   choices.

   The result is stored in *INFO, which must be non-NULL.
   If no match is found, INFO->SYM is set to NULL.  */

void
ada_lookup_encoded_symbol (const char *name, const struct block *block,
			   domain_enum domain,
			   struct block_symbol *info)
{
  /* Since we already have an encoded name, wrap it in '<>' to force a
     verbatim match.  Otherwise, if the name happens to not look like
     an encoded name (because it doesn't include a "__"),
     ada_lookup_name_info would re-encode/fold it again, and that
     would e.g., incorrectly lowercase object renaming names like
     "R28b" -> "r28b".  */
  std::string verbatim = add_angle_brackets (name);

  gdb_assert (info != NULL);
  *info = ada_lookup_symbol (verbatim.c_str (), block, domain);
}

/* Return a symbol in DOMAIN matching NAME, in BLOCK0 and enclosing
   scope and in global scopes, or NULL if none.  NAME is folded and
   encoded first.  Otherwise, the result is as for ada_lookup_symbol_list,
   choosing the first symbol if there are multiple choices.  */

struct block_symbol
ada_lookup_symbol (const char *name, const struct block *block0,
		   domain_enum domain)
{
  std::vector<struct block_symbol> candidates
    = ada_lookup_symbol_list (name, block0, domain);

  if (candidates.empty ())
    return {};

  block_symbol info = candidates[0];
  info.symbol = fixup_symbol_section (info.symbol, NULL);
  return info;
}


/* True iff STR is a possible encoded suffix of a normal Ada name
   that is to be ignored for matching purposes.  Suffixes of parallel
   names (e.g., XVE) are not included here.  Currently, the possible suffixes
   are given by any of the regular expressions:

   [.$][0-9]+       [nested subprogram suffix, on platforms such as GNU/Linux]
   ___[0-9]+        [nested subprogram suffix, on platforms such as HP/UX]
   TKB              [subprogram suffix for task bodies]
   _E[0-9]+[bs]$    [protected object entry suffixes]
   (X[nb]*)?((\$|__)[0-9](_?[0-9]+)|___(JM|LJM|X([FDBUP].*|R[^T]?)))?$

   Also, any leading "__[0-9]+" sequence is skipped before the suffix
   match is performed.  This sequence is used to differentiate homonyms,
   is an optional part of a valid name suffix.  */

static int
is_name_suffix (const char *str)
{
  int k;
  const char *matching;
  const int len = strlen (str);

  /* Skip optional leading __[0-9]+.  */

  if (len > 3 && str[0] == '_' && str[1] == '_' && isdigit (str[2]))
    {
      str += 3;
      while (isdigit (str[0]))
	str += 1;
    }
  
  /* [.$][0-9]+ */

  if (str[0] == '.' || str[0] == '$')
    {
      matching = str + 1;
      while (isdigit (matching[0]))
	matching += 1;
      if (matching[0] == '\0')
	return 1;
    }

  /* ___[0-9]+ */

  if (len > 3 && str[0] == '_' && str[1] == '_' && str[2] == '_')
    {
      matching = str + 3;
      while (isdigit (matching[0]))
	matching += 1;
      if (matching[0] == '\0')
	return 1;
    }

  /* "TKB" suffixes are used for subprograms implementing task bodies.  */

  if (strcmp (str, "TKB") == 0)
    return 1;

#if 0
  /* FIXME: brobecker/2005-09-23: Protected Object subprograms end
     with a N at the end.  Unfortunately, the compiler uses the same
     convention for other internal types it creates.  So treating
     all entity names that end with an "N" as a name suffix causes
     some regressions.  For instance, consider the case of an enumerated
     type.  To support the 'Image attribute, it creates an array whose
     name ends with N.
     Having a single character like this as a suffix carrying some
     information is a bit risky.  Perhaps we should change the encoding
     to be something like "_N" instead.  In the meantime, do not do
     the following check.  */
  /* Protected Object Subprograms */
  if (len == 1 && str [0] == 'N')
    return 1;
#endif

  /* _E[0-9]+[bs]$ */
  if (len > 3 && str[0] == '_' && str [1] == 'E' && isdigit (str[2]))
    {
      matching = str + 3;
      while (isdigit (matching[0]))
	matching += 1;
      if ((matching[0] == 'b' || matching[0] == 's')
	  && matching [1] == '\0')
	return 1;
    }

  /* ??? We should not modify STR directly, as we are doing below.  This
     is fine in this case, but may become problematic later if we find
     that this alternative did not work, and want to try matching
     another one from the begining of STR.  Since we modified it, we
     won't be able to find the begining of the string anymore!  */
  if (str[0] == 'X')
    {
      str += 1;
      while (str[0] != '_' && str[0] != '\0')
	{
	  if (str[0] != 'n' && str[0] != 'b')
	    return 0;
	  str += 1;
	}
    }

  if (str[0] == '\000')
    return 1;

  if (str[0] == '_')
    {
      if (str[1] != '_' || str[2] == '\000')
	return 0;
      if (str[2] == '_')
	{
	  if (strcmp (str + 3, "JM") == 0)
	    return 1;
	  /* FIXME: brobecker/2004-09-30: GNAT will soon stop using
	     the LJM suffix in favor of the JM one.  But we will
	     still accept LJM as a valid suffix for a reasonable
	     amount of time, just to allow ourselves to debug programs
	     compiled using an older version of GNAT.  */
	  if (strcmp (str + 3, "LJM") == 0)
	    return 1;
	  if (str[3] != 'X')
	    return 0;
	  if (str[4] == 'F' || str[4] == 'D' || str[4] == 'B'
	      || str[4] == 'U' || str[4] == 'P')
	    return 1;
	  if (str[4] == 'R' && str[5] != 'T')
	    return 1;
	  return 0;
	}
      if (!isdigit (str[2]))
	return 0;
      for (k = 3; str[k] != '\0'; k += 1)
	if (!isdigit (str[k]) && str[k] != '_')
	  return 0;
      return 1;
    }
  if (str[0] == '$' && isdigit (str[1]))
    {
      for (k = 2; str[k] != '\0'; k += 1)
	if (!isdigit (str[k]) && str[k] != '_')
	  return 0;
      return 1;
    }
  return 0;
}

/* Return non-zero if the string starting at NAME and ending before
   NAME_END contains no capital letters.  */

static int
is_valid_name_for_wild_match (const char *name0)
{
  std::string decoded_name = ada_decode (name0);
  int i;

  /* If the decoded name starts with an angle bracket, it means that
     NAME0 does not follow the GNAT encoding format.  It should then
     not be allowed as a possible wild match.  */
  if (decoded_name[0] == '<')
    return 0;

  for (i=0; decoded_name[i] != '\0'; i++)
    if (isalpha (decoded_name[i]) && !islower (decoded_name[i]))
      return 0;

  return 1;
}

/* Advance *NAMEP to next occurrence in the string NAME0 of the TARGET0
   character which could start a simple name.  Assumes that *NAMEP points
   somewhere inside the string beginning at NAME0.  */

static int
advance_wild_match (const char **namep, const char *name0, char target0)
{
  const char *name = *namep;

  while (1)
    {
      char t0, t1;

      t0 = *name;
      if (t0 == '_')
	{
	  t1 = name[1];
	  if ((t1 >= 'a' && t1 <= 'z') || (t1 >= '0' && t1 <= '9'))
	    {
	      name += 1;
	      if (name == name0 + 5 && startswith (name0, "_ada"))
		break;
	      else
		name += 1;
	    }
	  else if (t1 == '_' && ((name[2] >= 'a' && name[2] <= 'z')
				 || name[2] == target0))
	    {
	      name += 2;
	      break;
	    }
	  else if (t1 == '_' && name[2] == 'B' && name[3] == '_')
	    {
	      /* Names like "pkg__B_N__name", where N is a number, are
		 block-local.  We can handle these by simply skipping
		 the "B_" here.  */
	      name += 4;
	    }
	  else
	    return 0;
	}
      else if ((t0 >= 'a' && t0 <= 'z') || (t0 >= '0' && t0 <= '9'))
	name += 1;
      else
	return 0;
    }

  *namep = name;
  return 1;
}

/* Return true iff NAME encodes a name of the form prefix.PATN.
   Ignores any informational suffixes of NAME (i.e., for which
   is_name_suffix is true).  Assumes that PATN is a lower-cased Ada
   simple name.  */

static bool
wild_match (const char *name, const char *patn)
{
  const char *p;
  const char *name0 = name;

  while (1)
    {
      const char *match = name;

      if (*name == *patn)
	{
	  for (name += 1, p = patn + 1; *p != '\0'; name += 1, p += 1)
	    if (*p != *name)
	      break;
	  if (*p == '\0' && is_name_suffix (name))
	    return match == name0 || is_valid_name_for_wild_match (name0);

	  if (name[-1] == '_')
	    name -= 1;
	}
      if (!advance_wild_match (&name, name0, *patn))
	return false;
    }
}

/* Add symbols from BLOCK matching LOOKUP_NAME in DOMAIN to RESULT (if
   necessary).  OBJFILE is the section containing BLOCK.  */

static void
ada_add_block_symbols (std::vector<struct block_symbol> &result,
		       const struct block *block,
		       const lookup_name_info &lookup_name,
		       domain_enum domain, struct objfile *objfile)
{
  struct block_iterator iter;
  /* A matching argument symbol, if any.  */
  struct symbol *arg_sym;
  /* Set true when we find a matching non-argument symbol.  */
  bool found_sym;
  struct symbol *sym;

  arg_sym = NULL;
  found_sym = false;
  for (sym = block_iter_match_first (block, lookup_name, &iter);
       sym != NULL;
       sym = block_iter_match_next (lookup_name, &iter))
    {
      if (symbol_matches_domain (sym->language (), SYMBOL_DOMAIN (sym), domain))
	{
	  if (SYMBOL_CLASS (sym) != LOC_UNRESOLVED)
	    {
	      if (SYMBOL_IS_ARGUMENT (sym))
		arg_sym = sym;
	      else
		{
		  found_sym = true;
		  add_defn_to_vec (result,
				   fixup_symbol_section (sym, objfile),
				   block);
		}
	    }
	}
    }

  /* Handle renamings.  */

  if (ada_add_block_renamings (result, block, lookup_name, domain))
    found_sym = true;

  if (!found_sym && arg_sym != NULL)
    {
      add_defn_to_vec (result,
		       fixup_symbol_section (arg_sym, objfile),
		       block);
    }

  if (!lookup_name.ada ().wild_match_p ())
    {
      arg_sym = NULL;
      found_sym = false;
      const std::string &ada_lookup_name = lookup_name.ada ().lookup_name ();
      const char *name = ada_lookup_name.c_str ();
      size_t name_len = ada_lookup_name.size ();

      ALL_BLOCK_SYMBOLS (block, iter, sym)
      {
	if (symbol_matches_domain (sym->language (),
				   SYMBOL_DOMAIN (sym), domain))
	  {
	    int cmp;

	    cmp = (int) '_' - (int) sym->linkage_name ()[0];
	    if (cmp == 0)
	      {
		cmp = !startswith (sym->linkage_name (), "_ada_");
		if (cmp == 0)
		  cmp = strncmp (name, sym->linkage_name () + 5,
				 name_len);
	      }

	    if (cmp == 0
		&& is_name_suffix (sym->linkage_name () + name_len + 5))
	      {
		if (SYMBOL_CLASS (sym) != LOC_UNRESOLVED)
		  {
		    if (SYMBOL_IS_ARGUMENT (sym))
		      arg_sym = sym;
		    else
		      {
			found_sym = true;
			add_defn_to_vec (result,
					 fixup_symbol_section (sym, objfile),
					 block);
		      }
		  }
	      }
	  }
      }

      /* NOTE: This really shouldn't be needed for _ada_ symbols.
	 They aren't parameters, right?  */
      if (!found_sym && arg_sym != NULL)
	{
	  add_defn_to_vec (result,
			   fixup_symbol_section (arg_sym, objfile),
			   block);
	}
    }
}


				/* Symbol Completion */

/* See symtab.h.  */

bool
ada_lookup_name_info::matches
  (const char *sym_name,
   symbol_name_match_type match_type,
   completion_match_result *comp_match_res) const
{
  bool match = false;
  const char *text = m_encoded_name.c_str ();
  size_t text_len = m_encoded_name.size ();

  /* First, test against the fully qualified name of the symbol.  */

  if (strncmp (sym_name, text, text_len) == 0)
    match = true;

  std::string decoded_name = ada_decode (sym_name);
  if (match && !m_encoded_p)
    {
      /* One needed check before declaring a positive match is to verify
	 that iff we are doing a verbatim match, the decoded version
	 of the symbol name starts with '<'.  Otherwise, this symbol name
	 is not a suitable completion.  */

      bool has_angle_bracket = (decoded_name[0] == '<');
      match = (has_angle_bracket == m_verbatim_p);
    }

  if (match && !m_verbatim_p)
    {
      /* When doing non-verbatim match, another check that needs to
	 be done is to verify that the potentially matching symbol name
	 does not include capital letters, because the ada-mode would
	 not be able to understand these symbol names without the
	 angle bracket notation.  */
      const char *tmp;

      for (tmp = sym_name; *tmp != '\0' && !isupper (*tmp); tmp++);
      if (*tmp != '\0')
	match = false;
    }

  /* Second: Try wild matching...  */

  if (!match && m_wild_match_p)
    {
      /* Since we are doing wild matching, this means that TEXT
	 may represent an unqualified symbol name.  We therefore must
	 also compare TEXT against the unqualified name of the symbol.  */
      sym_name = ada_unqualified_name (decoded_name.c_str ());

      if (strncmp (sym_name, text, text_len) == 0)
	match = true;
    }

  /* Finally: If we found a match, prepare the result to return.  */

  if (!match)
    return false;

  if (comp_match_res != NULL)
    {
      std::string &match_str = comp_match_res->match.storage ();

      if (!m_encoded_p)
	match_str = ada_decode (sym_name);
      else
	{
	  if (m_verbatim_p)
	    match_str = add_angle_brackets (sym_name);
	  else
	    match_str = sym_name;

	}

      comp_match_res->set_match (match_str.c_str ());
    }

  return true;
}

				/* Field Access */

/* Return non-zero if TYPE is a pointer to the GNAT dispatch table used
   for tagged types.  */

static int
ada_is_dispatch_table_ptr_type (struct type *type)
{
  const char *name;

  if (type->code () != TYPE_CODE_PTR)
    return 0;

  name = TYPE_TARGET_TYPE (type)->name ();
  if (name == NULL)
    return 0;

  return (strcmp (name, "ada__tags__dispatch_table") == 0);
}

/* Return non-zero if TYPE is an interface tag.  */

static int
ada_is_interface_tag (struct type *type)
{
  const char *name = type->name ();

  if (name == NULL)
    return 0;

  return (strcmp (name, "ada__tags__interface_tag") == 0);
}

/* True if field number FIELD_NUM in struct or union type TYPE is supposed
   to be invisible to users.  */

int
ada_is_ignored_field (struct type *type, int field_num)
{
  if (field_num < 0 || field_num > type->num_fields ())
    return 1;

  /* Check the name of that field.  */
  {
    const char *name = TYPE_FIELD_NAME (type, field_num);

    /* Anonymous field names should not be printed.
       brobecker/2007-02-20: I don't think this can actually happen
       but we don't want to print the value of anonymous fields anyway.  */
    if (name == NULL)
      return 1;

    /* Normally, fields whose name start with an underscore ("_")
       are fields that have been internally generated by the compiler,
       and thus should not be printed.  The "_parent" field is special,
       however: This is a field internally generated by the compiler
       for tagged types, and it contains the components inherited from
       the parent type.  This field should not be printed as is, but
       should not be ignored either.  */
    if (name[0] == '_' && !startswith (name, "_parent"))
      return 1;
  }

  /* If this is the dispatch table of a tagged type or an interface tag,
     then ignore.  */
  if (ada_is_tagged_type (type, 1)
      && (ada_is_dispatch_table_ptr_type (type->field (field_num).type ())
	  || ada_is_interface_tag (type->field (field_num).type ())))
    return 1;

  /* Not a special field, so it should not be ignored.  */
  return 0;
}

/* True iff TYPE has a tag field.  If REFOK, then TYPE may also be a
   pointer or reference type whose ultimate target has a tag field.  */

int
ada_is_tagged_type (struct type *type, int refok)
{
  return (ada_lookup_struct_elt_type (type, "_tag", refok, 1) != NULL);
}

/* True iff TYPE represents the type of X'Tag */

int
ada_is_tag_type (struct type *type)
{
  type = ada_check_typedef (type);

  if (type == NULL || type->code () != TYPE_CODE_PTR)
    return 0;
  else
    {
      const char *name = ada_type_name (TYPE_TARGET_TYPE (type));

      return (name != NULL
	      && strcmp (name, "ada__tags__dispatch_table") == 0);
    }
}

/* The type of the tag on VAL.  */

static struct type *
ada_tag_type (struct value *val)
{
  return ada_lookup_struct_elt_type (value_type (val), "_tag", 1, 0);
}

/* Return 1 if TAG follows the old scheme for Ada tags (used for Ada 95,
   retired at Ada 05).  */

static int
is_ada95_tag (struct value *tag)
{
  return ada_value_struct_elt (tag, "tsd", 1) != NULL;
}

/* The value of the tag on VAL.  */

static struct value *
ada_value_tag (struct value *val)
{
  return ada_value_struct_elt (val, "_tag", 0);
}

/* The value of the tag on the object of type TYPE whose contents are
   saved at VALADDR, if it is non-null, or is at memory address
   ADDRESS.  */

static struct value *
value_tag_from_contents_and_address (struct type *type,
				     const gdb_byte *valaddr,
				     CORE_ADDR address)
{
  int tag_byte_offset;
  struct type *tag_type;

  if (find_struct_field ("_tag", type, 0, &tag_type, &tag_byte_offset,
			 NULL, NULL, NULL))
    {
      const gdb_byte *valaddr1 = ((valaddr == NULL)
				  ? NULL
				  : valaddr + tag_byte_offset);
      CORE_ADDR address1 = (address == 0) ? 0 : address + tag_byte_offset;

      return value_from_contents_and_address (tag_type, valaddr1, address1);
    }
  return NULL;
}

static struct type *
type_from_tag (struct value *tag)
{
  gdb::unique_xmalloc_ptr<char> type_name = ada_tag_name (tag);

  if (type_name != NULL)
    return ada_find_any_type (ada_encode (type_name.get ()).c_str ());
  return NULL;
}

/* Given a value OBJ of a tagged type, return a value of this
   type at the base address of the object.  The base address, as
   defined in Ada.Tags, it is the address of the primary tag of
   the object, and therefore where the field values of its full
   view can be fetched.  */

struct value *
ada_tag_value_at_base_address (struct value *obj)
{
  struct value *val;
  LONGEST offset_to_top = 0;
  struct type *ptr_type, *obj_type;
  struct value *tag;
  CORE_ADDR base_address;

  obj_type = value_type (obj);

  /* It is the responsability of the caller to deref pointers.  */

  if (obj_type->code () == TYPE_CODE_PTR || obj_type->code () == TYPE_CODE_REF)
    return obj;

  tag = ada_value_tag (obj);
  if (!tag)
    return obj;

  /* Base addresses only appeared with Ada 05 and multiple inheritance.  */

  if (is_ada95_tag (tag))
    return obj;

  ptr_type = language_lookup_primitive_type
    (language_def (language_ada), target_gdbarch(), "storage_offset");
  ptr_type = lookup_pointer_type (ptr_type);
  val = value_cast (ptr_type, tag);
  if (!val)
    return obj;

  /* It is perfectly possible that an exception be raised while
     trying to determine the base address, just like for the tag;
     see ada_tag_name for more details.  We do not print the error
     message for the same reason.  */

  try
    {
      offset_to_top = value_as_long (value_ind (value_ptradd (val, -2)));
    }

  catch (const gdb_exception_error &e)
    {
      return obj;
    }

  /* If offset is null, nothing to do.  */

  if (offset_to_top == 0)
    return obj;

  /* -1 is a special case in Ada.Tags; however, what should be done
     is not quite clear from the documentation.  So do nothing for
     now.  */

  if (offset_to_top == -1)
    return obj;

  /* OFFSET_TO_TOP used to be a positive value to be subtracted
     from the base address.  This was however incompatible with
     C++ dispatch table: C++ uses a *negative* value to *add*
     to the base address.  Ada's convention has therefore been
     changed in GNAT 19.0w 20171023: since then, C++ and Ada
     use the same convention.  Here, we support both cases by
     checking the sign of OFFSET_TO_TOP.  */

  if (offset_to_top > 0)
    offset_to_top = -offset_to_top;

  base_address = value_address (obj) + offset_to_top;
  tag = value_tag_from_contents_and_address (obj_type, NULL, base_address);

  /* Make sure that we have a proper tag at the new address.
     Otherwise, offset_to_top is bogus (which can happen when
     the object is not initialized yet).  */

  if (!tag)
    return obj;

  obj_type = type_from_tag (tag);

  if (!obj_type)
    return obj;

  return value_from_contents_and_address (obj_type, NULL, base_address);
}

/* Return the "ada__tags__type_specific_data" type.  */

static struct type *
ada_get_tsd_type (struct inferior *inf)
{
  struct ada_inferior_data *data = get_ada_inferior_data (inf);

  if (data->tsd_type == 0)
    data->tsd_type = ada_find_any_type ("ada__tags__type_specific_data");
  return data->tsd_type;
}

/* Return the TSD (type-specific data) associated to the given TAG.
   TAG is assumed to be the tag of a tagged-type entity.

   May return NULL if we are unable to get the TSD.  */

static struct value *
ada_get_tsd_from_tag (struct value *tag)
{
  struct value *val;
  struct type *type;

  /* First option: The TSD is simply stored as a field of our TAG.
     Only older versions of GNAT would use this format, but we have
     to test it first, because there are no visible markers for
     the current approach except the absence of that field.  */

  val = ada_value_struct_elt (tag, "tsd", 1);
  if (val)
    return val;

  /* Try the second representation for the dispatch table (in which
     there is no explicit 'tsd' field in the referent of the tag pointer,
     and instead the tsd pointer is stored just before the dispatch
     table.  */

  type = ada_get_tsd_type (current_inferior());
  if (type == NULL)
    return NULL;
  type = lookup_pointer_type (lookup_pointer_type (type));
  val = value_cast (type, tag);
  if (val == NULL)
    return NULL;
  return value_ind (value_ptradd (val, -1));
}

/* Given the TSD of a tag (type-specific data), return a string
   containing the name of the associated type.

   May return NULL if we are unable to determine the tag name.  */

static gdb::unique_xmalloc_ptr<char>
ada_tag_name_from_tsd (struct value *tsd)
{
  char *p;
  struct value *val;

  val = ada_value_struct_elt (tsd, "expanded_name", 1);
  if (val == NULL)
    return NULL;
  gdb::unique_xmalloc_ptr<char> buffer
    = target_read_string (value_as_address (val), INT_MAX);
  if (buffer == nullptr)
    return nullptr;

  for (p = buffer.get (); *p != '\0'; ++p)
    {
      if (isalpha (*p))
	*p = tolower (*p);
    }

  return buffer;
}

/* The type name of the dynamic type denoted by the 'tag value TAG, as
   a C string.

   Return NULL if the TAG is not an Ada tag, or if we were unable to
   determine the name of that tag.  */

gdb::unique_xmalloc_ptr<char>
ada_tag_name (struct value *tag)
{
  gdb::unique_xmalloc_ptr<char> name;

  if (!ada_is_tag_type (value_type (tag)))
    return NULL;

  /* It is perfectly possible that an exception be raised while trying
     to determine the TAG's name, even under normal circumstances:
     The associated variable may be uninitialized or corrupted, for
     instance. We do not let any exception propagate past this point.
     instead we return NULL.

     We also do not print the error message either (which often is very
     low-level (Eg: "Cannot read memory at 0x[...]"), but instead let
     the caller print a more meaningful message if necessary.  */
  try
    {
      struct value *tsd = ada_get_tsd_from_tag (tag);

      if (tsd != NULL)
	name = ada_tag_name_from_tsd (tsd);
    }
  catch (const gdb_exception_error &e)
    {
    }

  return name;
}

/* The parent type of TYPE, or NULL if none.  */

struct type *
ada_parent_type (struct type *type)
{
  int i;

  type = ada_check_typedef (type);

  if (type == NULL || type->code () != TYPE_CODE_STRUCT)
    return NULL;

  for (i = 0; i < type->num_fields (); i += 1)
    if (ada_is_parent_field (type, i))
      {
	struct type *parent_type = type->field (i).type ();

	/* If the _parent field is a pointer, then dereference it.  */
	if (parent_type->code () == TYPE_CODE_PTR)
	  parent_type = TYPE_TARGET_TYPE (parent_type);
	/* If there is a parallel XVS type, get the actual base type.  */
	parent_type = ada_get_base_type (parent_type);

	return ada_check_typedef (parent_type);
      }

  return NULL;
}

/* True iff field number FIELD_NUM of structure type TYPE contains the
   parent-type (inherited) fields of a derived type.  Assumes TYPE is
   a structure type with at least FIELD_NUM+1 fields.  */

int
ada_is_parent_field (struct type *type, int field_num)
{
  const char *name = TYPE_FIELD_NAME (ada_check_typedef (type), field_num);

  return (name != NULL
	  && (startswith (name, "PARENT")
	      || startswith (name, "_parent")));
}

/* True iff field number FIELD_NUM of structure type TYPE is a
   transparent wrapper field (which should be silently traversed when doing
   field selection and flattened when printing).  Assumes TYPE is a
   structure type with at least FIELD_NUM+1 fields.  Such fields are always
   structures.  */

int
ada_is_wrapper_field (struct type *type, int field_num)
{
  const char *name = TYPE_FIELD_NAME (type, field_num);

  if (name != NULL && strcmp (name, "RETVAL") == 0)
    {
      /* This happens in functions with "out" or "in out" parameters
	 which are passed by copy.  For such functions, GNAT describes
	 the function's return type as being a struct where the return
	 value is in a field called RETVAL, and where the other "out"
	 or "in out" parameters are fields of that struct.  This is not
	 a wrapper.  */
      return 0;
    }

  return (name != NULL
	  && (startswith (name, "PARENT")
	      || strcmp (name, "REP") == 0
	      || startswith (name, "_parent")
	      || name[0] == 'S' || name[0] == 'R' || name[0] == 'O'));
}

/* True iff field number FIELD_NUM of structure or union type TYPE
   is a variant wrapper.  Assumes TYPE is a structure type with at least
   FIELD_NUM+1 fields.  */

int
ada_is_variant_part (struct type *type, int field_num)
{
  /* Only Ada types are eligible.  */
  if (!ADA_TYPE_P (type))
    return 0;

  struct type *field_type = type->field (field_num).type ();

  return (field_type->code () == TYPE_CODE_UNION
	  || (is_dynamic_field (type, field_num)
	      && (TYPE_TARGET_TYPE (field_type)->code ()
		  == TYPE_CODE_UNION)));
}

/* Assuming that VAR_TYPE is a variant wrapper (type of the variant part)
   whose discriminants are contained in the record type OUTER_TYPE,
   returns the type of the controlling discriminant for the variant.
   May return NULL if the type could not be found.  */

struct type *
ada_variant_discrim_type (struct type *var_type, struct type *outer_type)
{
  const char *name = ada_variant_discrim_name (var_type);

  return ada_lookup_struct_elt_type (outer_type, name, 1, 1);
}

/* Assuming that TYPE is the type of a variant wrapper, and FIELD_NUM is a
   valid field number within it, returns 1 iff field FIELD_NUM of TYPE
   represents a 'when others' clause; otherwise 0.  */

static int
ada_is_others_clause (struct type *type, int field_num)
{
  const char *name = TYPE_FIELD_NAME (type, field_num);

  return (name != NULL && name[0] == 'O');
}

/* Assuming that TYPE0 is the type of the variant part of a record,
   returns the name of the discriminant controlling the variant.
   The value is valid until the next call to ada_variant_discrim_name.  */

const char *
ada_variant_discrim_name (struct type *type0)
{
  static std::string result;
  struct type *type;
  const char *name;
  const char *discrim_end;
  const char *discrim_start;

  if (type0->code () == TYPE_CODE_PTR)
    type = TYPE_TARGET_TYPE (type0);
  else
    type = type0;

  name = ada_type_name (type);

  if (name == NULL || name[0] == '\000')
    return "";

  for (discrim_end = name + strlen (name) - 6; discrim_end != name;
       discrim_end -= 1)
    {
      if (startswith (discrim_end, "___XVN"))
	break;
    }
  if (discrim_end == name)
    return "";

  for (discrim_start = discrim_end; discrim_start != name + 3;
       discrim_start -= 1)
    {
      if (discrim_start == name + 1)
	return "";
      if ((discrim_start > name + 3
	   && startswith (discrim_start - 3, "___"))
	  || discrim_start[-1] == '.')
	break;
    }

  result = std::string (discrim_start, discrim_end - discrim_start);
  return result.c_str ();
}

/* Scan STR for a subtype-encoded number, beginning at position K.
   Put the position of the character just past the number scanned in
   *NEW_K, if NEW_K!=NULL.  Put the scanned number in *R, if R!=NULL.
   Return 1 if there was a valid number at the given position, and 0
   otherwise.  A "subtype-encoded" number consists of the absolute value
   in decimal, followed by the letter 'm' to indicate a negative number.
   Assumes 0m does not occur.  */

int
ada_scan_number (const char str[], int k, LONGEST * R, int *new_k)
{
  ULONGEST RU;

  if (!isdigit (str[k]))
    return 0;

  /* Do it the hard way so as not to make any assumption about
     the relationship of unsigned long (%lu scan format code) and
     LONGEST.  */
  RU = 0;
  while (isdigit (str[k]))
    {
      RU = RU * 10 + (str[k] - '0');
      k += 1;
    }

  if (str[k] == 'm')
    {
      if (R != NULL)
	*R = (-(LONGEST) (RU - 1)) - 1;
      k += 1;
    }
  else if (R != NULL)
    *R = (LONGEST) RU;

  /* NOTE on the above: Technically, C does not say what the results of
     - (LONGEST) RU or (LONGEST) -RU are for RU == largest positive
     number representable as a LONGEST (although either would probably work
     in most implementations).  When RU>0, the locution in the then branch
     above is always equivalent to the negative of RU.  */

  if (new_k != NULL)
    *new_k = k;
  return 1;
}

/* Assuming that TYPE is a variant part wrapper type (a VARIANTS field),
   and FIELD_NUM is a valid field number within it, returns 1 iff VAL is
   in the range encoded by field FIELD_NUM of TYPE; otherwise 0.  */

static int
ada_in_variant (LONGEST val, struct type *type, int field_num)
{
  const char *name = TYPE_FIELD_NAME (type, field_num);
  int p;

  p = 0;
  while (1)
    {
      switch (name[p])
	{
	case '\0':
	  return 0;
	case 'S':
	  {
	    LONGEST W;

	    if (!ada_scan_number (name, p + 1, &W, &p))
	      return 0;
	    if (val == W)
	      return 1;
	    break;
	  }
	case 'R':
	  {
	    LONGEST L, U;

	    if (!ada_scan_number (name, p + 1, &L, &p)
		|| name[p] != 'T' || !ada_scan_number (name, p + 1, &U, &p))
	      return 0;
	    if (val >= L && val <= U)
	      return 1;
	    break;
	  }
	case 'O':
	  return 1;
	default:
	  return 0;
	}
    }
}

/* FIXME: Lots of redundancy below.  Try to consolidate.  */

/* Given a value ARG1 (offset by OFFSET bytes) of a struct or union type
   ARG_TYPE, extract and return the value of one of its (non-static)
   fields.  FIELDNO says which field.   Differs from value_primitive_field
   only in that it can handle packed values of arbitrary type.  */

struct value *
ada_value_primitive_field (struct value *arg1, int offset, int fieldno,
			   struct type *arg_type)
{
  struct type *type;

  arg_type = ada_check_typedef (arg_type);
  type = arg_type->field (fieldno).type ();

  /* Handle packed fields.  It might be that the field is not packed
     relative to its containing structure, but the structure itself is
     packed; in this case we must take the bit-field path.  */
  if (TYPE_FIELD_BITSIZE (arg_type, fieldno) != 0 || value_bitpos (arg1) != 0)
    {
      int bit_pos = TYPE_FIELD_BITPOS (arg_type, fieldno);
      int bit_size = TYPE_FIELD_BITSIZE (arg_type, fieldno);

      return ada_value_primitive_packed_val (arg1, value_contents (arg1),
					     offset + bit_pos / 8,
					     bit_pos % 8, bit_size, type);
    }
  else
    return value_primitive_field (arg1, offset, fieldno, arg_type);
}

/* Find field with name NAME in object of type TYPE.  If found, 
   set the following for each argument that is non-null:
    - *FIELD_TYPE_P to the field's type; 
    - *BYTE_OFFSET_P to OFFSET + the byte offset of the field within 
      an object of that type;
    - *BIT_OFFSET_P to the bit offset modulo byte size of the field; 
    - *BIT_SIZE_P to its size in bits if the field is packed, and 
      0 otherwise;
   If INDEX_P is non-null, increment *INDEX_P by the number of source-visible
   fields up to but not including the desired field, or by the total
   number of fields if not found.   A NULL value of NAME never
   matches; the function just counts visible fields in this case.
   
   Notice that we need to handle when a tagged record hierarchy
   has some components with the same name, like in this scenario:

      type Top_T is tagged record
	 N : Integer := 1;
	 U : Integer := 974;
	 A : Integer := 48;
      end record;

      type Middle_T is new Top.Top_T with record
	 N : Character := 'a';
	 C : Integer := 3;
      end record;

     type Bottom_T is new Middle.Middle_T with record
	N : Float := 4.0;
	C : Character := '5';
	X : Integer := 6;
	A : Character := 'J';
     end record;

   Let's say we now have a variable declared and initialized as follow:

     TC : Top_A := new Bottom_T;

   And then we use this variable to call this function

     procedure Assign (Obj: in out Top_T; TV : Integer);

   as follow:

      Assign (Top_T (B), 12);

   Now, we're in the debugger, and we're inside that procedure
   then and we want to print the value of obj.c:

   Usually, the tagged record or one of the parent type owns the
   component to print and there's no issue but in this particular
   case, what does it mean to ask for Obj.C? Since the actual
   type for object is type Bottom_T, it could mean two things: type
   component C from the Middle_T view, but also component C from
   Bottom_T.  So in that "undefined" case, when the component is
   not found in the non-resolved type (which includes all the
   components of the parent type), then resolve it and see if we
   get better luck once expanded.

   In the case of homonyms in the derived tagged type, we don't
   guaranty anything, and pick the one that's easiest for us
   to program.

   Returns 1 if found, 0 otherwise.  */

static int
find_struct_field (const char *name, struct type *type, int offset,
		   struct type **field_type_p,
		   int *byte_offset_p, int *bit_offset_p, int *bit_size_p,
		   int *index_p)
{
  int i;
  int parent_offset = -1;

  type = ada_check_typedef (type);

  if (field_type_p != NULL)
    *field_type_p = NULL;
  if (byte_offset_p != NULL)
    *byte_offset_p = 0;
  if (bit_offset_p != NULL)
    *bit_offset_p = 0;
  if (bit_size_p != NULL)
    *bit_size_p = 0;

  for (i = 0; i < type->num_fields (); i += 1)
    {
      int bit_pos = TYPE_FIELD_BITPOS (type, i);
      int fld_offset = offset + bit_pos / 8;
      const char *t_field_name = TYPE_FIELD_NAME (type, i);

      if (t_field_name == NULL)
	continue;

      else if (ada_is_parent_field (type, i))
	{
	  /* This is a field pointing us to the parent type of a tagged
	     type.  As hinted in this function's documentation, we give
	     preference to fields in the current record first, so what
	     we do here is just record the index of this field before
	     we skip it.  If it turns out we couldn't find our field
	     in the current record, then we'll get back to it and search
	     inside it whether the field might exist in the parent.  */

	  parent_offset = i;
	  continue;
	}

      else if (name != NULL && field_name_match (t_field_name, name))
	{
	  int bit_size = TYPE_FIELD_BITSIZE (type, i);

	  if (field_type_p != NULL)
	    *field_type_p = type->field (i).type ();
	  if (byte_offset_p != NULL)
	    *byte_offset_p = fld_offset;
	  if (bit_offset_p != NULL)
	    *bit_offset_p = bit_pos % 8;
	  if (bit_size_p != NULL)
	    *bit_size_p = bit_size;
	  return 1;
	}
      else if (ada_is_wrapper_field (type, i))
	{
	  if (find_struct_field (name, type->field (i).type (), fld_offset,
				 field_type_p, byte_offset_p, bit_offset_p,
				 bit_size_p, index_p))
	    return 1;
	}
      else if (ada_is_variant_part (type, i))
	{
	  /* PNH: Wait.  Do we ever execute this section, or is ARG always of 
	     fixed type?? */
	  int j;
	  struct type *field_type
	    = ada_check_typedef (type->field (i).type ());

	  for (j = 0; j < field_type->num_fields (); j += 1)
	    {
	      if (find_struct_field (name, field_type->field (j).type (),
				     fld_offset
				     + TYPE_FIELD_BITPOS (field_type, j) / 8,
				     field_type_p, byte_offset_p,
				     bit_offset_p, bit_size_p, index_p))
		return 1;
	    }
	}
      else if (index_p != NULL)
	*index_p += 1;
    }

  /* Field not found so far.  If this is a tagged type which
     has a parent, try finding that field in the parent now.  */

  if (parent_offset != -1)
    {
      int bit_pos = TYPE_FIELD_BITPOS (type, parent_offset);
      int fld_offset = offset + bit_pos / 8;

      if (find_struct_field (name, type->field (parent_offset).type (),
			     fld_offset, field_type_p, byte_offset_p,
			     bit_offset_p, bit_size_p, index_p))
	return 1;
    }

  return 0;
}

/* Number of user-visible fields in record type TYPE.  */

static int
num_visible_fields (struct type *type)
{
  int n;

  n = 0;
  find_struct_field (NULL, type, 0, NULL, NULL, NULL, NULL, &n);
  return n;
}

/* Look for a field NAME in ARG.  Adjust the address of ARG by OFFSET bytes,
   and search in it assuming it has (class) type TYPE.
   If found, return value, else return NULL.

   Searches recursively through wrapper fields (e.g., '_parent').

   In the case of homonyms in the tagged types, please refer to the
   long explanation in find_struct_field's function documentation.  */

static struct value *
ada_search_struct_field (const char *name, struct value *arg, int offset,
			 struct type *type)
{
  int i;
  int parent_offset = -1;

  type = ada_check_typedef (type);
  for (i = 0; i < type->num_fields (); i += 1)
    {
      const char *t_field_name = TYPE_FIELD_NAME (type, i);

      if (t_field_name == NULL)
	continue;

      else if (ada_is_parent_field (type, i))
	{
	  /* This is a field pointing us to the parent type of a tagged
	     type.  As hinted in this function's documentation, we give
	     preference to fields in the current record first, so what
	     we do here is just record the index of this field before
	     we skip it.  If it turns out we couldn't find our field
	     in the current record, then we'll get back to it and search
	     inside it whether the field might exist in the parent.  */

	  parent_offset = i;
	  continue;
	}

      else if (field_name_match (t_field_name, name))
	return ada_value_primitive_field (arg, offset, i, type);

      else if (ada_is_wrapper_field (type, i))
	{
	  struct value *v =     /* Do not let indent join lines here.  */
	    ada_search_struct_field (name, arg,
				     offset + TYPE_FIELD_BITPOS (type, i) / 8,
				     type->field (i).type ());

	  if (v != NULL)
	    return v;
	}

      else if (ada_is_variant_part (type, i))
	{
	  /* PNH: Do we ever get here?  See find_struct_field.  */
	  int j;
	  struct type *field_type = ada_check_typedef (type->field (i).type ());
	  int var_offset = offset + TYPE_FIELD_BITPOS (type, i) / 8;

	  for (j = 0; j < field_type->num_fields (); j += 1)
	    {
	      struct value *v = ada_search_struct_field /* Force line
							   break.  */
		(name, arg,
		 var_offset + TYPE_FIELD_BITPOS (field_type, j) / 8,
		 field_type->field (j).type ());

	      if (v != NULL)
		return v;
	    }
	}
    }

  /* Field not found so far.  If this is a tagged type which
     has a parent, try finding that field in the parent now.  */

  if (parent_offset != -1)
    {
      struct value *v = ada_search_struct_field (
	name, arg, offset + TYPE_FIELD_BITPOS (type, parent_offset) / 8,
	type->field (parent_offset).type ());

      if (v != NULL)
	return v;
    }

  return NULL;
}

static struct value *ada_index_struct_field_1 (int *, struct value *,
					       int, struct type *);


/* Return field #INDEX in ARG, where the index is that returned by
 * find_struct_field through its INDEX_P argument.  Adjust the address
 * of ARG by OFFSET bytes, and search in it assuming it has (class) type TYPE.
 * If found, return value, else return NULL.  */

static struct value *
ada_index_struct_field (int index, struct value *arg, int offset,
			struct type *type)
{
  return ada_index_struct_field_1 (&index, arg, offset, type);
}


/* Auxiliary function for ada_index_struct_field.  Like
 * ada_index_struct_field, but takes index from *INDEX_P and modifies
 * *INDEX_P.  */

static struct value *
ada_index_struct_field_1 (int *index_p, struct value *arg, int offset,
			  struct type *type)
{
  int i;
  type = ada_check_typedef (type);

  for (i = 0; i < type->num_fields (); i += 1)
    {
      if (TYPE_FIELD_NAME (type, i) == NULL)
	continue;
      else if (ada_is_wrapper_field (type, i))
	{
	  struct value *v =     /* Do not let indent join lines here.  */
	    ada_index_struct_field_1 (index_p, arg,
				      offset + TYPE_FIELD_BITPOS (type, i) / 8,
				      type->field (i).type ());

	  if (v != NULL)
	    return v;
	}

      else if (ada_is_variant_part (type, i))
	{
	  /* PNH: Do we ever get here?  See ada_search_struct_field,
	     find_struct_field.  */
	  error (_("Cannot assign this kind of variant record"));
	}
      else if (*index_p == 0)
	return ada_value_primitive_field (arg, offset, i, type);
      else
	*index_p -= 1;
    }
  return NULL;
}

/* Return a string representation of type TYPE.  */

static std::string
type_as_string (struct type *type)
{
  string_file tmp_stream;

  type_print (type, "", &tmp_stream, -1);

  return std::move (tmp_stream.string ());
}

/* Given a type TYPE, look up the type of the component of type named NAME.
   If DISPP is non-null, add its byte displacement from the beginning of a
   structure (pointed to by a value) of type TYPE to *DISPP (does not
   work for packed fields).

   Matches any field whose name has NAME as a prefix, possibly
   followed by "___".

   TYPE can be either a struct or union.  If REFOK, TYPE may also 
   be a (pointer or reference)+ to a struct or union, and the
   ultimate target type will be searched.

   Looks recursively into variant clauses and parent types.

   In the case of homonyms in the tagged types, please refer to the
   long explanation in find_struct_field's function documentation.

   If NOERR is nonzero, return NULL if NAME is not suitably defined or
   TYPE is not a type of the right kind.  */

static struct type *
ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
			    int noerr)
{
  int i;
  int parent_offset = -1;

  if (name == NULL)
    goto BadName;

  if (refok && type != NULL)
    while (1)
      {
	type = ada_check_typedef (type);
	if (type->code () != TYPE_CODE_PTR && type->code () != TYPE_CODE_REF)
	  break;
	type = TYPE_TARGET_TYPE (type);
      }

  if (type == NULL
      || (type->code () != TYPE_CODE_STRUCT
	  && type->code () != TYPE_CODE_UNION))
    {
      if (noerr)
	return NULL;

      error (_("Type %s is not a structure or union type"),
	     type != NULL ? type_as_string (type).c_str () : _("(null)"));
    }

  type = to_static_fixed_type (type);

  for (i = 0; i < type->num_fields (); i += 1)
    {
      const char *t_field_name = TYPE_FIELD_NAME (type, i);
      struct type *t;

      if (t_field_name == NULL)
	continue;

      else if (ada_is_parent_field (type, i))
	{
	  /* This is a field pointing us to the parent type of a tagged
	     type.  As hinted in this function's documentation, we give
	     preference to fields in the current record first, so what
	     we do here is just record the index of this field before
	     we skip it.  If it turns out we couldn't find our field
	     in the current record, then we'll get back to it and search
	     inside it whether the field might exist in the parent.  */

	  parent_offset = i;
	  continue;
	}

      else if (field_name_match (t_field_name, name))
	return type->field (i).type ();

      else if (ada_is_wrapper_field (type, i))
	{
	  t = ada_lookup_struct_elt_type (type->field (i).type (), name,
					  0, 1);
	  if (t != NULL)
	    return t;
	}

      else if (ada_is_variant_part (type, i))
	{
	  int j;
	  struct type *field_type = ada_check_typedef (type->field (i).type ());

	  for (j = field_type->num_fields () - 1; j >= 0; j -= 1)
	    {
	      /* FIXME pnh 2008/01/26: We check for a field that is
		 NOT wrapped in a struct, since the compiler sometimes
		 generates these for unchecked variant types.  Revisit
		 if the compiler changes this practice.  */
	      const char *v_field_name = TYPE_FIELD_NAME (field_type, j);

	      if (v_field_name != NULL 
		  && field_name_match (v_field_name, name))
		t = field_type->field (j).type ();
	      else
		t = ada_lookup_struct_elt_type (field_type->field (j).type (),
						name, 0, 1);

	      if (t != NULL)
		return t;
	    }
	}

    }

    /* Field not found so far.  If this is a tagged type which
       has a parent, try finding that field in the parent now.  */

    if (parent_offset != -1)
      {
	struct type *t;

	t = ada_lookup_struct_elt_type (type->field (parent_offset).type (),
					name, 0, 1);
	if (t != NULL)
	  return t;
      }

BadName:
  if (!noerr)
    {
      const char *name_str = name != NULL ? name : _("<null>");

      error (_("Type %s has no component named %s"),
	     type_as_string (type).c_str (), name_str);
    }

  return NULL;
}

/* Assuming that VAR_TYPE is the type of a variant part of a record (a union),
   within a value of type OUTER_TYPE, return true iff VAR_TYPE
   represents an unchecked union (that is, the variant part of a
   record that is named in an Unchecked_Union pragma).  */

static int
is_unchecked_variant (struct type *var_type, struct type *outer_type)
{
  const char *discrim_name = ada_variant_discrim_name (var_type);

  return (ada_lookup_struct_elt_type (outer_type, discrim_name, 0, 1) == NULL);
}


/* Assuming that VAR_TYPE is the type of a variant part of a record (a union),
   within OUTER, determine which variant clause (field number in VAR_TYPE,
   numbering from 0) is applicable.  Returns -1 if none are.  */

int
ada_which_variant_applies (struct type *var_type, struct value *outer)
{
  int others_clause;
  int i;
  const char *discrim_name = ada_variant_discrim_name (var_type);
  struct value *discrim;
  LONGEST discrim_val;

  /* Using plain value_from_contents_and_address here causes problems
     because we will end up trying to resolve a type that is currently
     being constructed.  */
  discrim = ada_value_struct_elt (outer, discrim_name, 1);
  if (discrim == NULL)
    return -1;
  discrim_val = value_as_long (discrim);

  others_clause = -1;
  for (i = 0; i < var_type->num_fields (); i += 1)
    {
      if (ada_is_others_clause (var_type, i))
	others_clause = i;
      else if (ada_in_variant (discrim_val, var_type, i))
	return i;
    }

  return others_clause;
}



				/* Dynamic-Sized Records */

/* Strategy: The type ostensibly attached to a value with dynamic size
   (i.e., a size that is not statically recorded in the debugging
   data) does not accurately reflect the size or layout of the value.
   Our strategy is to convert these values to values with accurate,
   conventional types that are constructed on the fly.  */

/* There is a subtle and tricky problem here.  In general, we cannot
   determine the size of dynamic records without its data.  However,
   the 'struct value' data structure, which GDB uses to represent
   quantities in the inferior process (the target), requires the size
   of the type at the time of its allocation in order to reserve space
   for GDB's internal copy of the data.  That's why the
   'to_fixed_xxx_type' routines take (target) addresses as parameters,
   rather than struct value*s.

   However, GDB's internal history variables ($1, $2, etc.) are
   struct value*s containing internal copies of the data that are not, in
   general, the same as the data at their corresponding addresses in
   the target.  Fortunately, the types we give to these values are all
   conventional, fixed-size types (as per the strategy described
   above), so that we don't usually have to perform the
   'to_fixed_xxx_type' conversions to look at their values.
   Unfortunately, there is one exception: if one of the internal
   history variables is an array whose elements are unconstrained
   records, then we will need to create distinct fixed types for each
   element selected.  */

/* The upshot of all of this is that many routines take a (type, host
   address, target address) triple as arguments to represent a value.
   The host address, if non-null, is supposed to contain an internal
   copy of the relevant data; otherwise, the program is to consult the
   target at the target address.  */

/* Assuming that VAL0 represents a pointer value, the result of
   dereferencing it.  Differs from value_ind in its treatment of
   dynamic-sized types.  */

struct value *
ada_value_ind (struct value *val0)
{
  struct value *val = value_ind (val0);

  if (ada_is_tagged_type (value_type (val), 0))
    val = ada_tag_value_at_base_address (val);

  return ada_to_fixed_value (val);
}

/* The value resulting from dereferencing any "reference to"
   qualifiers on VAL0.  */

static struct value *
ada_coerce_ref (struct value *val0)
{
  if (value_type (val0)->code () == TYPE_CODE_REF)
    {
      struct value *val = val0;

      val = coerce_ref (val);

      if (ada_is_tagged_type (value_type (val), 0))
	val = ada_tag_value_at_base_address (val);

      return ada_to_fixed_value (val);
    }
  else
    return val0;
}

/* Return the bit alignment required for field #F of template type TYPE.  */

static unsigned int
field_alignment (struct type *type, int f)
{
  const char *name = TYPE_FIELD_NAME (type, f);
  int len;
  int align_offset;

  /* The field name should never be null, unless the debugging information
     is somehow malformed.  In this case, we assume the field does not
     require any alignment.  */
  if (name == NULL)
    return 1;

  len = strlen (name);

  if (!isdigit (name[len - 1]))
    return 1;

  if (isdigit (name[len - 2]))
    align_offset = len - 2;
  else
    align_offset = len - 1;

  if (align_offset < 7 || !startswith (name + align_offset - 6, "___XV"))
    return TARGET_CHAR_BIT;

  return atoi (name + align_offset) * TARGET_CHAR_BIT;
}

/* Find a typedef or tag symbol named NAME.  Ignores ambiguity.  */

static struct symbol *
ada_find_any_type_symbol (const char *name)
{
  struct symbol *sym;

  sym = standard_lookup (name, get_selected_block (NULL), VAR_DOMAIN);
  if (sym != NULL && SYMBOL_CLASS (sym) == LOC_TYPEDEF)
    return sym;

  sym = standard_lookup (name, NULL, STRUCT_DOMAIN);
  return sym;
}

/* Find a type named NAME.  Ignores ambiguity.  This routine will look
   solely for types defined by debug info, it will not search the GDB
   primitive types.  */

static struct type *
ada_find_any_type (const char *name)
{
  struct symbol *sym = ada_find_any_type_symbol (name);

  if (sym != NULL)
    return SYMBOL_TYPE (sym);

  return NULL;
}

/* Given NAME_SYM and an associated BLOCK, find a "renaming" symbol
   associated with NAME_SYM's name.  NAME_SYM may itself be a renaming
   symbol, in which case it is returned.  Otherwise, this looks for
   symbols whose name is that of NAME_SYM suffixed with  "___XR".
   Return symbol if found, and NULL otherwise.  */

static bool
ada_is_renaming_symbol (struct symbol *name_sym)
{
  const char *name = name_sym->linkage_name ();
  return strstr (name, "___XR") != NULL;
}

/* Because of GNAT encoding conventions, several GDB symbols may match a
   given type name.  If the type denoted by TYPE0 is to be preferred to
   that of TYPE1 for purposes of type printing, return non-zero;
   otherwise return 0.  */

int
ada_prefer_type (struct type *type0, struct type *type1)
{
  if (type1 == NULL)
    return 1;
  else if (type0 == NULL)
    return 0;
  else if (type1->code () == TYPE_CODE_VOID)
    return 1;
  else if (type0->code () == TYPE_CODE_VOID)
    return 0;
  else if (type1->name () == NULL && type0->name () != NULL)
    return 1;
  else if (ada_is_constrained_packed_array_type (type0))
    return 1;
  else if (ada_is_array_descriptor_type (type0)
	   && !ada_is_array_descriptor_type (type1))
    return 1;
  else
    {
      const char *type0_name = type0->name ();
      const char *type1_name = type1->name ();

      if (type0_name != NULL && strstr (type0_name, "___XR") != NULL
	  && (type1_name == NULL || strstr (type1_name, "___XR") == NULL))
	return 1;
    }
  return 0;
}

/* The name of TYPE, which is its TYPE_NAME.  Null if TYPE is
   null.  */

const char *
ada_type_name (struct type *type)
{
  if (type == NULL)
    return NULL;
  return type->name ();
}

/* Search the list of "descriptive" types associated to TYPE for a type
   whose name is NAME.  */

static struct type *
find_parallel_type_by_descriptive_type (struct type *type, const char *name)
{
  struct type *result, *tmp;

  if (ada_ignore_descriptive_types_p)
    return NULL;

  /* If there no descriptive-type info, then there is no parallel type
     to be found.  */
  if (!HAVE_GNAT_AUX_INFO (type))
    return NULL;

  result = TYPE_DESCRIPTIVE_TYPE (type);
  while (result != NULL)
    {
      const char *result_name = ada_type_name (result);

      if (result_name == NULL)
	{
	  warning (_("unexpected null name on descriptive type"));
	  return NULL;
	}

      /* If the names match, stop.  */
      if (strcmp (result_name, name) == 0)
	break;

      /* Otherwise, look at the next item on the list, if any.  */
      if (HAVE_GNAT_AUX_INFO (result))
	tmp = TYPE_DESCRIPTIVE_TYPE (result);
      else
	tmp = NULL;

      /* If not found either, try after having resolved the typedef.  */
      if (tmp != NULL)
	result = tmp;
      else
	{
	  result = check_typedef (result);
	  if (HAVE_GNAT_AUX_INFO (result))
	    result = TYPE_DESCRIPTIVE_TYPE (result);
	  else
	    result = NULL;
	}
    }

  /* If we didn't find a match, see whether this is a packed array.  With
     older compilers, the descriptive type information is either absent or
     irrelevant when it comes to packed arrays so the above lookup fails.
     Fall back to using a parallel lookup by name in this case.  */
  if (result == NULL && ada_is_constrained_packed_array_type (type))
    return ada_find_any_type (name);

  return result;
}

/* Find a parallel type to TYPE with the specified NAME, using the
   descriptive type taken from the debugging information, if available,
   and otherwise using the (slower) name-based method.  */

static struct type *
ada_find_parallel_type_with_name (struct type *type, const char *name)
{
  struct type *result = NULL;

  if (HAVE_GNAT_AUX_INFO (type))
    result = find_parallel_type_by_descriptive_type (type, name);
  else
    result = ada_find_any_type (name);

  return result;
}

/* Same as above, but specify the name of the parallel type by appending
   SUFFIX to the name of TYPE.  */

struct type *
ada_find_parallel_type (struct type *type, const char *suffix)
{
  char *name;
  const char *type_name = ada_type_name (type);
  int len;

  if (type_name == NULL)
    return NULL;

  len = strlen (type_name);

  name = (char *) alloca (len + strlen (suffix) + 1);

  strcpy (name, type_name);
  strcpy (name + len, suffix);

  return ada_find_parallel_type_with_name (type, name);
}

/* If TYPE is a variable-size record type, return the corresponding template
   type describing its fields.  Otherwise, return NULL.  */

static struct type *
dynamic_template_type (struct type *type)
{
  type = ada_check_typedef (type);

  if (type == NULL || type->code () != TYPE_CODE_STRUCT
      || ada_type_name (type) == NULL)
    return NULL;
  else
    {
      int len = strlen (ada_type_name (type));

      if (len > 6 && strcmp (ada_type_name (type) + len - 6, "___XVE") == 0)
	return type;
      else
	return ada_find_parallel_type (type, "___XVE");
    }
}

/* Assuming that TEMPL_TYPE is a union or struct type, returns
   non-zero iff field FIELD_NUM of TEMPL_TYPE has dynamic size.  */

static int
is_dynamic_field (struct type *templ_type, int field_num)
{
  const char *name = TYPE_FIELD_NAME (templ_type, field_num);

  return name != NULL
    && templ_type->field (field_num).type ()->code () == TYPE_CODE_PTR
    && strstr (name, "___XVL") != NULL;
}

/* The index of the variant field of TYPE, or -1 if TYPE does not
   represent a variant record type.  */

static int
variant_field_index (struct type *type)
{
  int f;

  if (type == NULL || type->code () != TYPE_CODE_STRUCT)
    return -1;

  for (f = 0; f < type->num_fields (); f += 1)
    {
      if (ada_is_variant_part (type, f))
	return f;
    }
  return -1;
}

/* A record type with no fields.  */

static struct type *
empty_record (struct type *templ)
{
  struct type *type = alloc_type_copy (templ);

  type->set_code (TYPE_CODE_STRUCT);
  INIT_NONE_SPECIFIC (type);
  type->set_name ("<empty>");
  TYPE_LENGTH (type) = 0;
  return type;
}

/* An ordinary record type (with fixed-length fields) that describes
   the value of type TYPE at VALADDR or ADDRESS (see comments at
   the beginning of this section) VAL according to GNAT conventions.
   DVAL0 should describe the (portion of a) record that contains any
   necessary discriminants.  It should be NULL if value_type (VAL) is
   an outer-level type (i.e., as opposed to a branch of a variant.)  A
   variant field (unless unchecked) is replaced by a particular branch
   of the variant.

   If not KEEP_DYNAMIC_FIELDS, then all fields whose position or
   length are not statically known are discarded.  As a consequence,
   VALADDR, ADDRESS and DVAL0 are ignored.

   NOTE: Limitations: For now, we assume that dynamic fields and
   variants occupy whole numbers of bytes.  However, they need not be
   byte-aligned.  */

struct type *
ada_template_to_fixed_record_type_1 (struct type *type,
				     const gdb_byte *valaddr,
				     CORE_ADDR address, struct value *dval0,
				     int keep_dynamic_fields)
{
  struct value *mark = value_mark ();
  struct value *dval;
  struct type *rtype;
  int nfields, bit_len;
  int variant_field;
  long off;
  int fld_bit_len;
  int f;

  /* Compute the number of fields in this record type that are going
     to be processed: unless keep_dynamic_fields, this includes only
     fields whose position and length are static will be processed.  */
  if (keep_dynamic_fields)
    nfields = type->num_fields ();
  else
    {
      nfields = 0;
      while (nfields < type->num_fields ()
	     && !ada_is_variant_part (type, nfields)
	     && !is_dynamic_field (type, nfields))
	nfields++;
    }

  rtype = alloc_type_copy (type);
  rtype->set_code (TYPE_CODE_STRUCT);
  INIT_NONE_SPECIFIC (rtype);
  rtype->set_num_fields (nfields);
  rtype->set_fields
   ((struct field *) TYPE_ZALLOC (rtype, nfields * sizeof (struct field)));
  rtype->set_name (ada_type_name (type));
  rtype->set_is_fixed_instance (true);

  off = 0;
  bit_len = 0;
  variant_field = -1;

  for (f = 0; f < nfields; f += 1)
    {
      off = align_up (off, field_alignment (type, f))
	+ TYPE_FIELD_BITPOS (type, f);
      SET_FIELD_BITPOS (rtype->field (f), off);
      TYPE_FIELD_BITSIZE (rtype, f) = 0;

      if (ada_is_variant_part (type, f))
	{
	  variant_field = f;
	  fld_bit_len = 0;
	}
      else if (is_dynamic_field (type, f))
	{
	  const gdb_byte *field_valaddr = valaddr;
	  CORE_ADDR field_address = address;
	  struct type *field_type =
	    TYPE_TARGET_TYPE (type->field (f).type ());

	  if (dval0 == NULL)
	    {
	      /* rtype's length is computed based on the run-time
		 value of discriminants.  If the discriminants are not
		 initialized, the type size may be completely bogus and
		 GDB may fail to allocate a value for it.  So check the
		 size first before creating the value.  */
	      ada_ensure_varsize_limit (rtype);
	      /* Using plain value_from_contents_and_address here
		 causes problems because we will end up trying to
		 resolve a type that is currently being
		 constructed.  */
	      dval = value_from_contents_and_address_unresolved (rtype,
								 valaddr,
								 address);
	      rtype = value_type (dval);
	    }
	  else
	    dval = dval0;

	  /* If the type referenced by this field is an aligner type, we need
	     to unwrap that aligner type, because its size might not be set.
	     Keeping the aligner type would cause us to compute the wrong
	     size for this field, impacting the offset of the all the fields
	     that follow this one.  */
	  if (ada_is_aligner_type (field_type))
	    {
	      long field_offset = TYPE_FIELD_BITPOS (field_type, f);

	      field_valaddr = cond_offset_host (field_valaddr, field_offset);
	      field_address = cond_offset_target (field_address, field_offset);
	      field_type = ada_aligned_type (field_type);
	    }

	  field_valaddr = cond_offset_host (field_valaddr,
					    off / TARGET_CHAR_BIT);
	  field_address = cond_offset_target (field_address,
					      off / TARGET_CHAR_BIT);

	  /* Get the fixed type of the field.  Note that, in this case,
	     we do not want to get the real type out of the tag: if
	     the current field is the parent part of a tagged record,
	     we will get the tag of the object.  Clearly wrong: the real
	     type of the parent is not the real type of the child.  We
	     would end up in an infinite loop.	*/
	  field_type = ada_get_base_type (field_type);
	  field_type = ada_to_fixed_type (field_type, field_valaddr,
					  field_address, dval, 0);
	  /* If the field size is already larger than the maximum
	     object size, then the record itself will necessarily
	     be larger than the maximum object size.  We need to make
	     this check now, because the size might be so ridiculously
	     large (due to an uninitialized variable in the inferior)
	     that it would cause an overflow when adding it to the
	     record size.  */
	  ada_ensure_varsize_limit (field_type);

	  rtype->field (f).set_type (field_type);
	  TYPE_FIELD_NAME (rtype, f) = TYPE_FIELD_NAME (type, f);
	  /* The multiplication can potentially overflow.  But because
	     the field length has been size-checked just above, and
	     assuming that the maximum size is a reasonable value,
	     an overflow should not happen in practice.  So rather than
	     adding overflow recovery code to this already complex code,
	     we just assume that it's not going to happen.  */
	  fld_bit_len =
	    TYPE_LENGTH (rtype->field (f).type ()) * TARGET_CHAR_BIT;
	}
      else
	{
	  /* Note: If this field's type is a typedef, it is important
	     to preserve the typedef layer.

	     Otherwise, we might be transforming a typedef to a fat
	     pointer (encoding a pointer to an unconstrained array),
	     into a basic fat pointer (encoding an unconstrained
	     array).  As both types are implemented using the same
	     structure, the typedef is the only clue which allows us
	     to distinguish between the two options.  Stripping it
	     would prevent us from printing this field appropriately.  */
	  rtype->field (f).set_type (type->field (f).type ());
	  TYPE_FIELD_NAME (rtype, f) = TYPE_FIELD_NAME (type, f);
	  if (TYPE_FIELD_BITSIZE (type, f) > 0)
	    fld_bit_len =
	      TYPE_FIELD_BITSIZE (rtype, f) = TYPE_FIELD_BITSIZE (type, f);
	  else
	    {
	      struct type *field_type = type->field (f).type ();

	      /* We need to be careful of typedefs when computing
		 the length of our field.  If this is a typedef,
		 get the length of the target type, not the length
		 of the typedef.  */
	      if (field_type->code () == TYPE_CODE_TYPEDEF)
		field_type = ada_typedef_target_type (field_type);

	      fld_bit_len =
		TYPE_LENGTH (ada_check_typedef (field_type)) * TARGET_CHAR_BIT;
	    }
	}
      if (off + fld_bit_len > bit_len)
	bit_len = off + fld_bit_len;
      off += fld_bit_len;
      TYPE_LENGTH (rtype) =
	align_up (bit_len, TARGET_CHAR_BIT) / TARGET_CHAR_BIT;
    }

  /* We handle the variant part, if any, at the end because of certain
     odd cases in which it is re-ordered so as NOT to be the last field of
     the record.  This can happen in the presence of representation
     clauses.  */
  if (variant_field >= 0)
    {
      struct type *branch_type;

      off = TYPE_FIELD_BITPOS (rtype, variant_field);

      if (dval0 == NULL)
	{
	  /* Using plain value_from_contents_and_address here causes
	     problems because we will end up trying to resolve a type
	     that is currently being constructed.  */
	  dval = value_from_contents_and_address_unresolved (rtype, valaddr,
							     address);
	  rtype = value_type (dval);
	}
      else
	dval = dval0;

      branch_type =
	to_fixed_variant_branch_type
	(type->field (variant_field).type (),
	 cond_offset_host (valaddr, off / TARGET_CHAR_BIT),
	 cond_offset_target (address, off / TARGET_CHAR_BIT), dval);
      if (branch_type == NULL)
	{
	  for (f = variant_field + 1; f < rtype->num_fields (); f += 1)
	    rtype->field (f - 1) = rtype->field (f);
	  rtype->set_num_fields (rtype->num_fields () - 1);
	}
      else
	{
	  rtype->field (variant_field).set_type (branch_type);
	  TYPE_FIELD_NAME (rtype, variant_field) = "S";
	  fld_bit_len =
	    TYPE_LENGTH (rtype->field (variant_field).type ()) *
	    TARGET_CHAR_BIT;
	  if (off + fld_bit_len > bit_len)
	    bit_len = off + fld_bit_len;
	  TYPE_LENGTH (rtype) =
	    align_up (bit_len, TARGET_CHAR_BIT) / TARGET_CHAR_BIT;
	}
    }

  /* According to exp_dbug.ads, the size of TYPE for variable-size records
     should contain the alignment of that record, which should be a strictly
     positive value.  If null or negative, then something is wrong, most
     probably in the debug info.  In that case, we don't round up the size
     of the resulting type.  If this record is not part of another structure,
     the current RTYPE length might be good enough for our purposes.  */
  if (TYPE_LENGTH (type) <= 0)
    {
      if (rtype->name ())
	warning (_("Invalid type size for `%s' detected: %s."),
		 rtype->name (), pulongest (TYPE_LENGTH (type)));
      else
	warning (_("Invalid type size for <unnamed> detected: %s."),
		 pulongest (TYPE_LENGTH (type)));
    }
  else
    {
      TYPE_LENGTH (rtype) = align_up (TYPE_LENGTH (rtype),
				      TYPE_LENGTH (type));
    }

  value_free_to_mark (mark);
  if (TYPE_LENGTH (rtype) > varsize_limit)
    error (_("record type with dynamic size is larger than varsize-limit"));
  return rtype;
}

/* As for ada_template_to_fixed_record_type_1 with KEEP_DYNAMIC_FIELDS
   of 1.  */

static struct type *
template_to_fixed_record_type (struct type *type, const gdb_byte *valaddr,
			       CORE_ADDR address, struct value *dval0)
{
  return ada_template_to_fixed_record_type_1 (type, valaddr,
					      address, dval0, 1);
}

/* An ordinary record type in which ___XVL-convention fields and
   ___XVU- and ___XVN-convention field types in TYPE0 are replaced with
   static approximations, containing all possible fields.  Uses
   no runtime values.  Useless for use in values, but that's OK,
   since the results are used only for type determinations.   Works on both
   structs and unions.  Representation note: to save space, we memorize
   the result of this function in the TYPE_TARGET_TYPE of the
   template type.  */

static struct type *
template_to_static_fixed_type (struct type *type0)
{
  struct type *type;
  int nfields;
  int f;

  /* No need no do anything if the input type is already fixed.  */
  if (type0->is_fixed_instance ())
    return type0;

  /* Likewise if we already have computed the static approximation.  */
  if (TYPE_TARGET_TYPE (type0) != NULL)
    return TYPE_TARGET_TYPE (type0);

  /* Don't clone TYPE0 until we are sure we are going to need a copy.  */
  type = type0;
  nfields = type0->num_fields ();

  /* Whether or not we cloned TYPE0, cache the result so that we don't do
     recompute all over next time.  */
  TYPE_TARGET_TYPE (type0) = type;

  for (f = 0; f < nfields; f += 1)
    {
      struct type *field_type = type0->field (f).type ();
      struct type *new_type;

      if (is_dynamic_field (type0, f))
	{
	  field_type = ada_check_typedef (field_type);
	  new_type = to_static_fixed_type (TYPE_TARGET_TYPE (field_type));
	}
      else
	new_type = static_unwrap_type (field_type);

      if (new_type != field_type)
	{
	  /* Clone TYPE0 only the first time we get a new field type.  */
	  if (type == type0)
	    {
	      TYPE_TARGET_TYPE (type0) = type = alloc_type_copy (type0);
	      type->set_code (type0->code ());
	      INIT_NONE_SPECIFIC (type);
	      type->set_num_fields (nfields);

	      field *fields =
		((struct field *)
		 TYPE_ALLOC (type, nfields * sizeof (struct field)));
	      memcpy (fields, type0->fields (),
		      sizeof (struct field) * nfields);
	      type->set_fields (fields);

	      type->set_name (ada_type_name (type0));
	      type->set_is_fixed_instance (true);
	      TYPE_LENGTH (type) = 0;
	    }
	  type->field (f).set_type (new_type);
	  TYPE_FIELD_NAME (type, f) = TYPE_FIELD_NAME (type0, f);
	}
    }

  return type;
}

/* Given an object of type TYPE whose contents are at VALADDR and
   whose address in memory is ADDRESS, returns a revision of TYPE,
   which should be a non-dynamic-sized record, in which the variant
   part, if any, is replaced with the appropriate branch.  Looks
   for discriminant values in DVAL0, which can be NULL if the record
   contains the necessary discriminant values.  */

static struct type *
to_record_with_fixed_variant_part (struct type *type, const gdb_byte *valaddr,
				   CORE_ADDR address, struct value *dval0)
{
  struct value *mark = value_mark ();
  struct value *dval;
  struct type *rtype;
  struct type *branch_type;
  int nfields = type->num_fields ();
  int variant_field = variant_field_index (type);

  if (variant_field == -1)
    return type;

  if (dval0 == NULL)
    {
      dval = value_from_contents_and_address (type, valaddr, address);
      type = value_type (dval);
    }
  else
    dval = dval0;

  rtype = alloc_type_copy (type);
  rtype->set_code (TYPE_CODE_STRUCT);
  INIT_NONE_SPECIFIC (rtype);
  rtype->set_num_fields (nfields);

  field *fields =
    (struct field *) TYPE_ALLOC (rtype, nfields * sizeof (struct field));
  memcpy (fields, type->fields (), sizeof (struct field) * nfields);
  rtype->set_fields (fields);

  rtype->set_name (ada_type_name (type));
  rtype->set_is_fixed_instance (true);
  TYPE_LENGTH (rtype) = TYPE_LENGTH (type);

  branch_type = to_fixed_variant_branch_type
    (type->field (variant_field).type (),
     cond_offset_host (valaddr,
		       TYPE_FIELD_BITPOS (type, variant_field)
		       / TARGET_CHAR_BIT),
     cond_offset_target (address,
			 TYPE_FIELD_BITPOS (type, variant_field)
			 / TARGET_CHAR_BIT), dval);
  if (branch_type == NULL)
    {
      int f;

      for (f = variant_field + 1; f < nfields; f += 1)
	rtype->field (f - 1) = rtype->field (f);
      rtype->set_num_fields (rtype->num_fields () - 1);
    }
  else
    {
      rtype->field (variant_field).set_type (branch_type);
      TYPE_FIELD_NAME (rtype, variant_field) = "S";
      TYPE_FIELD_BITSIZE (rtype, variant_field) = 0;
      TYPE_LENGTH (rtype) += TYPE_LENGTH (branch_type);
    }
  TYPE_LENGTH (rtype) -= TYPE_LENGTH (type->field (variant_field).type ());

  value_free_to_mark (mark);
  return rtype;
}

/* An ordinary record type (with fixed-length fields) that describes
   the value at (TYPE0, VALADDR, ADDRESS) [see explanation at
   beginning of this section].   Any necessary discriminants' values
   should be in DVAL, a record value; it may be NULL if the object
   at ADDR itself contains any necessary discriminant values.
   Additionally, VALADDR and ADDRESS may also be NULL if no discriminant
   values from the record are needed.  Except in the case that DVAL,
   VALADDR, and ADDRESS are all 0 or NULL, a variant field (unless
   unchecked) is replaced by a particular branch of the variant.

   NOTE: the case in which DVAL and VALADDR are NULL and ADDRESS is 0
   is questionable and may be removed.  It can arise during the
   processing of an unconstrained-array-of-record type where all the
   variant branches have exactly the same size.  This is because in
   such cases, the compiler does not bother to use the XVS convention
   when encoding the record.  I am currently dubious of this
   shortcut and suspect the compiler should be altered.  FIXME.  */

static struct type *
to_fixed_record_type (struct type *type0, const gdb_byte *valaddr,
		      CORE_ADDR address, struct value *dval)
{
  struct type *templ_type;

  if (type0->is_fixed_instance ())
    return type0;

  templ_type = dynamic_template_type (type0);

  if (templ_type != NULL)
    return template_to_fixed_record_type (templ_type, valaddr, address, dval);
  else if (variant_field_index (type0) >= 0)
    {
      if (dval == NULL && valaddr == NULL && address == 0)
	return type0;
      return to_record_with_fixed_variant_part (type0, valaddr, address,
						dval);
    }
  else
    {
      type0->set_is_fixed_instance (true);
      return type0;
    }

}

/* An ordinary record type (with fixed-length fields) that describes
   the value at (VAR_TYPE0, VALADDR, ADDRESS), where VAR_TYPE0 is a
   union type.  Any necessary discriminants' values should be in DVAL,
   a record value.  That is, this routine selects the appropriate
   branch of the union at ADDR according to the discriminant value
   indicated in the union's type name.  Returns VAR_TYPE0 itself if
   it represents a variant subject to a pragma Unchecked_Union.  */

static struct type *
to_fixed_variant_branch_type (struct type *var_type0, const gdb_byte *valaddr,
			      CORE_ADDR address, struct value *dval)
{
  int which;
  struct type *templ_type;
  struct type *var_type;

  if (var_type0->code () == TYPE_CODE_PTR)
    var_type = TYPE_TARGET_TYPE (var_type0);
  else
    var_type = var_type0;

  templ_type = ada_find_parallel_type (var_type, "___XVU");

  if (templ_type != NULL)
    var_type = templ_type;

  if (is_unchecked_variant (var_type, value_type (dval)))
      return var_type0;
  which = ada_which_variant_applies (var_type, dval);

  if (which < 0)
    return empty_record (var_type);
  else if (is_dynamic_field (var_type, which))
    return to_fixed_record_type
      (TYPE_TARGET_TYPE (var_type->field (which).type ()),
       valaddr, address, dval);
  else if (variant_field_index (var_type->field (which).type ()) >= 0)
    return
      to_fixed_record_type
      (var_type->field (which).type (), valaddr, address, dval);
  else
    return var_type->field (which).type ();
}

/* Assuming RANGE_TYPE is a TYPE_CODE_RANGE, return nonzero if
   ENCODING_TYPE, a type following the GNAT conventions for discrete
   type encodings, only carries redundant information.  */

static int
ada_is_redundant_range_encoding (struct type *range_type,
				 struct type *encoding_type)
{
  const char *bounds_str;
  int n;
  LONGEST lo, hi;

  gdb_assert (range_type->code () == TYPE_CODE_RANGE);

  if (get_base_type (range_type)->code ()
      != get_base_type (encoding_type)->code ())
    {
      /* The compiler probably used a simple base type to describe
	 the range type instead of the range's actual base type,
	 expecting us to get the real base type from the encoding
	 anyway.  In this situation, the encoding cannot be ignored
	 as redundant.  */
      return 0;
    }

  if (is_dynamic_type (range_type))
    return 0;

  if (encoding_type->name () == NULL)
    return 0;

  bounds_str = strstr (encoding_type->name (), "___XDLU_");
  if (bounds_str == NULL)
    return 0;

  n = 8; /* Skip "___XDLU_".  */
  if (!ada_scan_number (bounds_str, n, &lo, &n))
    return 0;
  if (range_type->bounds ()->low.const_val () != lo)
    return 0;

  n += 2; /* Skip the "__" separator between the two bounds.  */
  if (!ada_scan_number (bounds_str, n, &hi, &n))
    return 0;
  if (range_type->bounds ()->high.const_val () != hi)
    return 0;

  return 1;
}

/* Given the array type ARRAY_TYPE, return nonzero if DESC_TYPE,
   a type following the GNAT encoding for describing array type
   indices, only carries redundant information.  */

static int
ada_is_redundant_index_type_desc (struct type *array_type,
				  struct type *desc_type)
{
  struct type *this_layer = check_typedef (array_type);
  int i;

  for (i = 0; i < desc_type->num_fields (); i++)
    {
      if (!ada_is_redundant_range_encoding (this_layer->index_type (),
					    desc_type->field (i).type ()))
	return 0;
      this_layer = check_typedef (TYPE_TARGET_TYPE (this_layer));
    }

  return 1;
}

/* Assuming that TYPE0 is an array type describing the type of a value
   at ADDR, and that DVAL describes a record containing any
   discriminants used in TYPE0, returns a type for the value that
   contains no dynamic components (that is, no components whose sizes
   are determined by run-time quantities).  Unless IGNORE_TOO_BIG is
   true, gives an error message if the resulting type's size is over
   varsize_limit.  */

static struct type *
to_fixed_array_type (struct type *type0, struct value *dval,
		     int ignore_too_big)
{
  struct type *index_type_desc;
  struct type *result;
  int constrained_packed_array_p;
  static const char *xa_suffix = "___XA";

  type0 = ada_check_typedef (type0);
  if (type0->is_fixed_instance ())
    return type0;

  constrained_packed_array_p = ada_is_constrained_packed_array_type (type0);
  if (constrained_packed_array_p)
    {
      type0 = decode_constrained_packed_array_type (type0);
      if (type0 == nullptr)
	error (_("could not decode constrained packed array type"));
    }

  index_type_desc = ada_find_parallel_type (type0, xa_suffix);

  /* As mentioned in exp_dbug.ads, for non bit-packed arrays an
     encoding suffixed with 'P' may still be generated.  If so,
     it should be used to find the XA type.  */

  if (index_type_desc == NULL)
    {
      const char *type_name = ada_type_name (type0);

      if (type_name != NULL)
	{
	  const int len = strlen (type_name);
	  char *name = (char *) alloca (len + strlen (xa_suffix));

	  if (type_name[len - 1] == 'P')
	    {
	      strcpy (name, type_name);
	      strcpy (name + len - 1, xa_suffix);
	      index_type_desc = ada_find_parallel_type_with_name (type0, name);
	    }
	}
    }

  ada_fixup_array_indexes_type (index_type_desc);
  if (index_type_desc != NULL
      && ada_is_redundant_index_type_desc (type0, index_type_desc))
    {
      /* Ignore this ___XA parallel type, as it does not bring any
	 useful information.  This allows us to avoid creating fixed
	 versions of the array's index types, which would be identical
	 to the original ones.  This, in turn, can also help avoid
	 the creation of fixed versions of the array itself.  */
      index_type_desc = NULL;
    }

  if (index_type_desc == NULL)
    {
      struct type *elt_type0 = ada_check_typedef (TYPE_TARGET_TYPE (type0));

      /* NOTE: elt_type---the fixed version of elt_type0---should never
	 depend on the contents of the array in properly constructed
	 debugging data.  */
      /* Create a fixed version of the array element type.
	 We're not providing the address of an element here,
	 and thus the actual object value cannot be inspected to do
	 the conversion.  This should not be a problem, since arrays of
	 unconstrained objects are not allowed.  In particular, all
	 the elements of an array of a tagged type should all be of
	 the same type specified in the debugging info.  No need to
	 consult the object tag.  */
      struct type *elt_type = ada_to_fixed_type (elt_type0, 0, 0, dval, 1);

      /* Make sure we always create a new array type when dealing with
	 packed array types, since we're going to fix-up the array
	 type length and element bitsize a little further down.  */
      if (elt_type0 == elt_type && !constrained_packed_array_p)
	result = type0;
      else
	result = create_array_type (alloc_type_copy (type0),
				    elt_type, type0->index_type ());
    }
  else
    {
      int i;
      struct type *elt_type0;

      elt_type0 = type0;
      for (i = index_type_desc->num_fields (); i > 0; i -= 1)
	elt_type0 = TYPE_TARGET_TYPE (elt_type0);

      /* NOTE: result---the fixed version of elt_type0---should never
	 depend on the contents of the array in properly constructed
	 debugging data.  */
      /* Create a fixed version of the array element type.
	 We're not providing the address of an element here,
	 and thus the actual object value cannot be inspected to do
	 the conversion.  This should not be a problem, since arrays of
	 unconstrained objects are not allowed.  In particular, all
	 the elements of an array of a tagged type should all be of
	 the same type specified in the debugging info.  No need to
	 consult the object tag.  */
      result =
	ada_to_fixed_type (ada_check_typedef (elt_type0), 0, 0, dval, 1);

      elt_type0 = type0;
      for (i = index_type_desc->num_fields () - 1; i >= 0; i -= 1)
	{
	  struct type *range_type =
	    to_fixed_range_type (index_type_desc->field (i).type (), dval);

	  result = create_array_type (alloc_type_copy (elt_type0),
				      result, range_type);
	  elt_type0 = TYPE_TARGET_TYPE (elt_type0);
	}
      if (!ignore_too_big && TYPE_LENGTH (result) > varsize_limit)
	error (_("array type with dynamic size is larger than varsize-limit"));
    }

  /* We want to preserve the type name.  This can be useful when
     trying to get the type name of a value that has already been
     printed (for instance, if the user did "print VAR; whatis $".  */
  result->set_name (type0->name ());

  if (constrained_packed_array_p)
    {
      /* So far, the resulting type has been created as if the original
	 type was a regular (non-packed) array type.  As a result, the
	 bitsize of the array elements needs to be set again, and the array
	 length needs to be recomputed based on that bitsize.  */
      int len = TYPE_LENGTH (result) / TYPE_LENGTH (TYPE_TARGET_TYPE (result));
      int elt_bitsize = TYPE_FIELD_BITSIZE (type0, 0);

      TYPE_FIELD_BITSIZE (result, 0) = TYPE_FIELD_BITSIZE (type0, 0);
      TYPE_LENGTH (result) = len * elt_bitsize / HOST_CHAR_BIT;
      if (TYPE_LENGTH (result) * HOST_CHAR_BIT < len * elt_bitsize)
	TYPE_LENGTH (result)++;
    }

  result->set_is_fixed_instance (true);
  return result;
}


/* A standard type (containing no dynamically sized components)
   corresponding to TYPE for the value (TYPE, VALADDR, ADDRESS)
   DVAL describes a record containing any discriminants used in TYPE0,
   and may be NULL if there are none, or if the object of type TYPE at
   ADDRESS or in VALADDR contains these discriminants.
   
   If CHECK_TAG is not null, in the case of tagged types, this function
   attempts to locate the object's tag and use it to compute the actual
   type.  However, when ADDRESS is null, we cannot use it to determine the
   location of the tag, and therefore compute the tagged type's actual type.
   So we return the tagged type without consulting the tag.  */
   
static struct type *
ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
		   CORE_ADDR address, struct value *dval, int check_tag)
{
  type = ada_check_typedef (type);

  /* Only un-fixed types need to be handled here.  */
  if (!HAVE_GNAT_AUX_INFO (type))
    return type;

  switch (type->code ())
    {
    default:
      return type;
    case TYPE_CODE_STRUCT:
      {
	struct type *static_type = to_static_fixed_type (type);
	struct type *fixed_record_type =
	  to_fixed_record_type (type, valaddr, address, NULL);

	/* If STATIC_TYPE is a tagged type and we know the object's address,
	   then we can determine its tag, and compute the object's actual
	   type from there.  Note that we have to use the fixed record
	   type (the parent part of the record may have dynamic fields
	   and the way the location of _tag is expressed may depend on
	   them).  */

	if (check_tag && address != 0 && ada_is_tagged_type (static_type, 0))
	  {
	    struct value *tag =
	      value_tag_from_contents_and_address
	      (fixed_record_type,
	       valaddr,
	       address);
	    struct type *real_type = type_from_tag (tag);
	    struct value *obj =
	      value_from_contents_and_address (fixed_record_type,
					       valaddr,
					       address);
	    fixed_record_type = value_type (obj);
	    if (real_type != NULL)
	      return to_fixed_record_type
		(real_type, NULL,
		 value_address (ada_tag_value_at_base_address (obj)), NULL);
	  }

	/* Check to see if there is a parallel ___XVZ variable.
	   If there is, then it provides the actual size of our type.  */
	else if (ada_type_name (fixed_record_type) != NULL)
	  {
	    const char *name = ada_type_name (fixed_record_type);
	    char *xvz_name
	      = (char *) alloca (strlen (name) + 7 /* "___XVZ\0" */);
	    bool xvz_found = false;
	    LONGEST size;

	    xsnprintf (xvz_name, strlen (name) + 7, "%s___XVZ", name);
	    try
	      {
		xvz_found = get_int_var_value (xvz_name, size);
	      }
	    catch (const gdb_exception_error &except)
	      {
		/* We found the variable, but somehow failed to read
		   its value.  Rethrow the same error, but with a little
		   bit more information, to help the user understand
		   what went wrong (Eg: the variable might have been
		   optimized out).  */
		throw_error (except.error,
			     _("unable to read value of %s (%s)"),
			     xvz_name, except.what ());
	      }

	    if (xvz_found && TYPE_LENGTH (fixed_record_type) != size)
	      {
		fixed_record_type = copy_type (fixed_record_type);
		TYPE_LENGTH (fixed_record_type) = size;

		/* The FIXED_RECORD_TYPE may have be a stub.  We have
		   observed this when the debugging info is STABS, and
		   apparently it is something that is hard to fix.

		   In practice, we don't need the actual type definition
		   at all, because the presence of the XVZ variable allows us
		   to assume that there must be a XVS type as well, which we
		   should be able to use later, when we need the actual type
		   definition.

		   In the meantime, pretend that the "fixed" type we are
		   returning is NOT a stub, because this can cause trouble
		   when using this type to create new types targeting it.
		   Indeed, the associated creation routines often check
		   whether the target type is a stub and will try to replace
		   it, thus using a type with the wrong size.  This, in turn,
		   might cause the new type to have the wrong size too.
		   Consider the case of an array, for instance, where the size
		   of the array is computed from the number of elements in
		   our array multiplied by the size of its element.  */
		fixed_record_type->set_is_stub (false);
	      }
	  }
	return fixed_record_type;
      }
    case TYPE_CODE_ARRAY:
      return to_fixed_array_type (type, dval, 1);
    case TYPE_CODE_UNION:
      if (dval == NULL)
	return type;
      else
	return to_fixed_variant_branch_type (type, valaddr, address, dval);
    }
}

/* The same as ada_to_fixed_type_1, except that it preserves the type
   if it is a TYPE_CODE_TYPEDEF of a type that is already fixed.

   The typedef layer needs be preserved in order to differentiate between
   arrays and array pointers when both types are implemented using the same
   fat pointer.  In the array pointer case, the pointer is encoded as
   a typedef of the pointer type.  For instance, considering:

	  type String_Access is access String;
	  S1 : String_Access := null;

   To the debugger, S1 is defined as a typedef of type String.  But
   to the user, it is a pointer.  So if the user tries to print S1,
   we should not dereference the array, but print the array address
   instead.

   If we didn't preserve the typedef layer, we would lose the fact that
   the type is to be presented as a pointer (needs de-reference before
   being printed).  And we would also use the source-level type name.  */

struct type *
ada_to_fixed_type (struct type *type, const gdb_byte *valaddr,
		   CORE_ADDR address, struct value *dval, int check_tag)

{
  struct type *fixed_type =
    ada_to_fixed_type_1 (type, valaddr, address, dval, check_tag);

  /*  If TYPE is a typedef and its target type is the same as the FIXED_TYPE,
      then preserve the typedef layer.

      Implementation note: We can only check the main-type portion of
      the TYPE and FIXED_TYPE, because eliminating the typedef layer
      from TYPE now returns a type that has the same instance flags
      as TYPE.  For instance, if TYPE is a "typedef const", and its
      target type is a "struct", then the typedef elimination will return
      a "const" version of the target type.  See check_typedef for more
      details about how the typedef layer elimination is done.

      brobecker/2010-11-19: It seems to me that the only case where it is
      useful to preserve the typedef layer is when dealing with fat pointers.
      Perhaps, we could add a check for that and preserve the typedef layer
      only in that situation.  But this seems unnecessary so far, probably
      because we call check_typedef/ada_check_typedef pretty much everywhere.
      */
  if (type->code () == TYPE_CODE_TYPEDEF
      && (TYPE_MAIN_TYPE (ada_typedef_target_type (type))
	  == TYPE_MAIN_TYPE (fixed_type)))
    return type;

  return fixed_type;
}

/* A standard (static-sized) type corresponding as well as possible to
   TYPE0, but based on no runtime data.  */

static struct type *
to_static_fixed_type (struct type *type0)
{
  struct type *type;

  if (type0 == NULL)
    return NULL;

  if (type0->is_fixed_instance ())
    return type0;

  type0 = ada_check_typedef (type0);

  switch (type0->code ())
    {
    default:
      return type0;
    case TYPE_CODE_STRUCT:
      type = dynamic_template_type (type0);
      if (type != NULL)
	return template_to_static_fixed_type (type);
      else
	return template_to_static_fixed_type (type0);
    case TYPE_CODE_UNION:
      type = ada_find_parallel_type (type0, "___XVU");
      if (type != NULL)
	return template_to_static_fixed_type (type);
      else
	return template_to_static_fixed_type (type0);
    }
}

/* A static approximation of TYPE with all type wrappers removed.  */

static struct type *
static_unwrap_type (struct type *type)
{
  if (ada_is_aligner_type (type))
    {
      struct type *type1 = ada_check_typedef (type)->field (0).type ();
      if (ada_type_name (type1) == NULL)
	type1->set_name (ada_type_name (type));

      return static_unwrap_type (type1);
    }
  else
    {
      struct type *raw_real_type = ada_get_base_type (type);

      if (raw_real_type == type)
	return type;
      else
	return to_static_fixed_type (raw_real_type);
    }
}

/* In some cases, incomplete and private types require
   cross-references that are not resolved as records (for example,
      type Foo;
      type FooP is access Foo;
      V: FooP;
      type Foo is array ...;
   ).  In these cases, since there is no mechanism for producing
   cross-references to such types, we instead substitute for FooP a
   stub enumeration type that is nowhere resolved, and whose tag is
   the name of the actual type.  Call these types "non-record stubs".  */

/* A type equivalent to TYPE that is not a non-record stub, if one
   exists, otherwise TYPE.  */

struct type *
ada_check_typedef (struct type *type)
{
  if (type == NULL)
    return NULL;

  /* If our type is an access to an unconstrained array, which is encoded
     as a TYPE_CODE_TYPEDEF of a fat pointer, then we're done.
     We don't want to strip the TYPE_CODE_TYPDEF layer, because this is
     what allows us to distinguish between fat pointers that represent
     array types, and fat pointers that represent array access types
     (in both cases, the compiler implements them as fat pointers).  */
  if (ada_is_access_to_unconstrained_array (type))
    return type;

  type = check_typedef (type);
  if (type == NULL || type->code () != TYPE_CODE_ENUM
      || !type->is_stub ()
      || type->name () == NULL)
    return type;
  else
    {
      const char *name = type->name ();
      struct type *type1 = ada_find_any_type (name);

      if (type1 == NULL)
	return type;

      /* TYPE1 might itself be a TYPE_CODE_TYPEDEF (this can happen with
	 stubs pointing to arrays, as we don't create symbols for array
	 types, only for the typedef-to-array types).  If that's the case,
	 strip the typedef layer.  */
      if (type1->code () == TYPE_CODE_TYPEDEF)
	type1 = ada_check_typedef (type1);

      return type1;
    }
}

/* A value representing the data at VALADDR/ADDRESS as described by
   type TYPE0, but with a standard (static-sized) type that correctly
   describes it.  If VAL0 is not NULL and TYPE0 already is a standard
   type, then return VAL0 [this feature is simply to avoid redundant
   creation of struct values].  */

static struct value *
ada_to_fixed_value_create (struct type *type0, CORE_ADDR address,
			   struct value *val0)
{
  struct type *type = ada_to_fixed_type (type0, 0, address, NULL, 1);

  if (type == type0 && val0 != NULL)
    return val0;

  if (VALUE_LVAL (val0) != lval_memory)
    {
      /* Our value does not live in memory; it could be a convenience
	 variable, for instance.  Create a not_lval value using val0's
	 contents.  */
      return value_from_contents (type, value_contents (val0));
    }

  return value_from_contents_and_address (type, 0, address);
}

/* A value representing VAL, but with a standard (static-sized) type
   that correctly describes it.  Does not necessarily create a new
   value.  */

struct value *
ada_to_fixed_value (struct value *val)
{
  val = unwrap_value (val);
  val = ada_to_fixed_value_create (value_type (val), value_address (val), val);
  return val;
}


/* Attributes */

/* Table mapping attribute numbers to names.
   NOTE: Keep up to date with enum ada_attribute definition in ada-lang.h.  */

static const char * const attribute_names[] = {
  "<?>",

  "first",
  "last",
  "length",
  "image",
  "max",
  "min",
  "modulus",
  "pos",
  "size",
  "tag",
  "val",
  0
};

static const char *
ada_attribute_name (enum exp_opcode n)
{
  if (n >= OP_ATR_FIRST && n <= (int) OP_ATR_VAL)
    return attribute_names[n - OP_ATR_FIRST + 1];
  else
    return attribute_names[0];
}

/* Evaluate the 'POS attribute applied to ARG.  */

static LONGEST
pos_atr (struct value *arg)
{
  struct value *val = coerce_ref (arg);
  struct type *type = value_type (val);

  if (!discrete_type_p (type))
    error (_("'POS only defined on discrete types"));

  gdb::optional<LONGEST> result = discrete_position (type, value_as_long (val));
  if (!result.has_value ())
    error (_("enumeration value is invalid: can't find 'POS"));

  return *result;
}

struct value *
ada_pos_atr (struct type *expect_type,
	     struct expression *exp,
	     enum noside noside, enum exp_opcode op,
	     struct value *arg)
{
  struct type *type = builtin_type (exp->gdbarch)->builtin_int;
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (type, not_lval);
  return value_from_longest (type, pos_atr (arg));
}

/* Evaluate the TYPE'VAL attribute applied to ARG.  */

static struct value *
val_atr (struct type *type, LONGEST val)
{
  gdb_assert (discrete_type_p (type));
  if (type->code () == TYPE_CODE_RANGE)
    type = TYPE_TARGET_TYPE (type);
  if (type->code () == TYPE_CODE_ENUM)
    {
      if (val < 0 || val >= type->num_fields ())
	error (_("argument to 'VAL out of range"));
      val = TYPE_FIELD_ENUMVAL (type, val);
    }
  return value_from_longest (type, val);
}

struct value *
ada_val_atr (enum noside noside, struct type *type, struct value *arg)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (type, not_lval);

  if (!discrete_type_p (type))
    error (_("'VAL only defined on discrete types"));
  if (!integer_type_p (value_type (arg)))
    error (_("'VAL requires integral argument"));

  return val_atr (type, value_as_long (arg));
}


				/* Evaluation */

/* True if TYPE appears to be an Ada character type.
   [At the moment, this is true only for Character and Wide_Character;
   It is a heuristic test that could stand improvement].  */

bool
ada_is_character_type (struct type *type)
{
  const char *name;

  /* If the type code says it's a character, then assume it really is,
     and don't check any further.  */
  if (type->code () == TYPE_CODE_CHAR)
    return true;
  
  /* Otherwise, assume it's a character type iff it is a discrete type
     with a known character type name.  */
  name = ada_type_name (type);
  return (name != NULL
	  && (type->code () == TYPE_CODE_INT
	      || type->code () == TYPE_CODE_RANGE)
	  && (strcmp (name, "character") == 0
	      || strcmp (name, "wide_character") == 0
	      || strcmp (name, "wide_wide_character") == 0
	      || strcmp (name, "unsigned char") == 0));
}

/* True if TYPE appears to be an Ada string type.  */

bool
ada_is_string_type (struct type *type)
{
  type = ada_check_typedef (type);
  if (type != NULL
      && type->code () != TYPE_CODE_PTR
      && (ada_is_simple_array_type (type)
	  || ada_is_array_descriptor_type (type))
      && ada_array_arity (type) == 1)
    {
      struct type *elttype = ada_array_element_type (type, 1);

      return ada_is_character_type (elttype);
    }
  else
    return false;
}

/* The compiler sometimes provides a parallel XVS type for a given
   PAD type.  Normally, it is safe to follow the PAD type directly,
   but older versions of the compiler have a bug that causes the offset
   of its "F" field to be wrong.  Following that field in that case
   would lead to incorrect results, but this can be worked around
   by ignoring the PAD type and using the associated XVS type instead.

   Set to True if the debugger should trust the contents of PAD types.
   Otherwise, ignore the PAD type if there is a parallel XVS type.  */
static bool trust_pad_over_xvs = true;

/* True if TYPE is a struct type introduced by the compiler to force the
   alignment of a value.  Such types have a single field with a
   distinctive name.  */

int
ada_is_aligner_type (struct type *type)
{
  type = ada_check_typedef (type);

  if (!trust_pad_over_xvs && ada_find_parallel_type (type, "___XVS") != NULL)
    return 0;

  return (type->code () == TYPE_CODE_STRUCT
	  && type->num_fields () == 1
	  && strcmp (TYPE_FIELD_NAME (type, 0), "F") == 0);
}

/* If there is an ___XVS-convention type parallel to SUBTYPE, return
   the parallel type.  */

struct type *
ada_get_base_type (struct type *raw_type)
{
  struct type *real_type_namer;
  struct type *raw_real_type;

  if (raw_type == NULL || raw_type->code () != TYPE_CODE_STRUCT)
    return raw_type;

  if (ada_is_aligner_type (raw_type))
    /* The encoding specifies that we should always use the aligner type.
       So, even if this aligner type has an associated XVS type, we should
       simply ignore it.

       According to the compiler gurus, an XVS type parallel to an aligner
       type may exist because of a stabs limitation.  In stabs, aligner
       types are empty because the field has a variable-sized type, and
       thus cannot actually be used as an aligner type.  As a result,
       we need the associated parallel XVS type to decode the type.
       Since the policy in the compiler is to not change the internal
       representation based on the debugging info format, we sometimes
       end up having a redundant XVS type parallel to the aligner type.  */
    return raw_type;

  real_type_namer = ada_find_parallel_type (raw_type, "___XVS");
  if (real_type_namer == NULL
      || real_type_namer->code () != TYPE_CODE_STRUCT
      || real_type_namer->num_fields () != 1)
    return raw_type;

  if (real_type_namer->field (0).type ()->code () != TYPE_CODE_REF)
    {
      /* This is an older encoding form where the base type needs to be
	 looked up by name.  We prefer the newer encoding because it is
	 more efficient.  */
      raw_real_type = ada_find_any_type (TYPE_FIELD_NAME (real_type_namer, 0));
      if (raw_real_type == NULL)
	return raw_type;
      else
	return raw_real_type;
    }

  /* The field in our XVS type is a reference to the base type.  */
  return TYPE_TARGET_TYPE (real_type_namer->field (0).type ());
}

/* The type of value designated by TYPE, with all aligners removed.  */

struct type *
ada_aligned_type (struct type *type)
{
  if (ada_is_aligner_type (type))
    return ada_aligned_type (type->field (0).type ());
  else
    return ada_get_base_type (type);
}


/* The address of the aligned value in an object at address VALADDR
   having type TYPE.  Assumes ada_is_aligner_type (TYPE).  */

const gdb_byte *
ada_aligned_value_addr (struct type *type, const gdb_byte *valaddr)
{
  if (ada_is_aligner_type (type))
    return ada_aligned_value_addr (type->field (0).type (),
				   valaddr +
				   TYPE_FIELD_BITPOS (type,
						      0) / TARGET_CHAR_BIT);
  else
    return valaddr;
}



/* The printed representation of an enumeration literal with encoded
   name NAME.  The value is good to the next call of ada_enum_name.  */
const char *
ada_enum_name (const char *name)
{
  static std::string storage;
  const char *tmp;

  /* First, unqualify the enumeration name:
     1. Search for the last '.' character.  If we find one, then skip
     all the preceding characters, the unqualified name starts
     right after that dot.
     2. Otherwise, we may be debugging on a target where the compiler
     translates dots into "__".  Search forward for double underscores,
     but stop searching when we hit an overloading suffix, which is
     of the form "__" followed by digits.  */

  tmp = strrchr (name, '.');
  if (tmp != NULL)
    name = tmp + 1;
  else
    {
      while ((tmp = strstr (name, "__")) != NULL)
	{
	  if (isdigit (tmp[2]))
	    break;
	  else
	    name = tmp + 2;
	}
    }

  if (name[0] == 'Q')
    {
      int v;

      if (name[1] == 'U' || name[1] == 'W')
	{
	  if (sscanf (name + 2, "%x", &v) != 1)
	    return name;
	}
      else if (((name[1] >= '0' && name[1] <= '9')
		|| (name[1] >= 'a' && name[1] <= 'z'))
	       && name[2] == '\0')
	{
	  storage = string_printf ("'%c'", name[1]);
	  return storage.c_str ();
	}
      else
	return name;

      if (isascii (v) && isprint (v))
	storage = string_printf ("'%c'", v);
      else if (name[1] == 'U')
	storage = string_printf ("[\"%02x\"]", v);
      else
	storage = string_printf ("[\"%04x\"]", v);

      return storage.c_str ();
    }
  else
    {
      tmp = strstr (name, "__");
      if (tmp == NULL)
	tmp = strstr (name, "$");
      if (tmp != NULL)
	{
	  storage = std::string (name, tmp - name);
	  return storage.c_str ();
	}

      return name;
    }
}

/* If VAL is wrapped in an aligner or subtype wrapper, return the
   value it wraps.  */

static struct value *
unwrap_value (struct value *val)
{
  struct type *type = ada_check_typedef (value_type (val));

  if (ada_is_aligner_type (type))
    {
      struct value *v = ada_value_struct_elt (val, "F", 0);
      struct type *val_type = ada_check_typedef (value_type (v));

      if (ada_type_name (val_type) == NULL)
	val_type->set_name (ada_type_name (type));

      return unwrap_value (v);
    }
  else
    {
      struct type *raw_real_type =
	ada_check_typedef (ada_get_base_type (type));

      /* If there is no parallel XVS or XVE type, then the value is
	 already unwrapped.  Return it without further modification.  */
      if ((type == raw_real_type)
	  && ada_find_parallel_type (type, "___XVE") == NULL)
	return val;

      return
	coerce_unspec_val_to_type
	(val, ada_to_fixed_type (raw_real_type, 0,
				 value_address (val),
				 NULL, 1));
    }
}

/* Given two array types T1 and T2, return nonzero iff both arrays
   contain the same number of elements.  */

static int
ada_same_array_size_p (struct type *t1, struct type *t2)
{
  LONGEST lo1, hi1, lo2, hi2;

  /* Get the array bounds in order to verify that the size of
     the two arrays match.  */
  if (!get_array_bounds (t1, &lo1, &hi1)
      || !get_array_bounds (t2, &lo2, &hi2))
    error (_("unable to determine array bounds"));

  /* To make things easier for size comparison, normalize a bit
     the case of empty arrays by making sure that the difference
     between upper bound and lower bound is always -1.  */
  if (lo1 > hi1)
    hi1 = lo1 - 1;
  if (lo2 > hi2)
    hi2 = lo2 - 1;

  return (hi1 - lo1 == hi2 - lo2);
}

/* Assuming that VAL is an array of integrals, and TYPE represents
   an array with the same number of elements, but with wider integral
   elements, return an array "casted" to TYPE.  In practice, this
   means that the returned array is built by casting each element
   of the original array into TYPE's (wider) element type.  */

static struct value *
ada_promote_array_of_integrals (struct type *type, struct value *val)
{
  struct type *elt_type = TYPE_TARGET_TYPE (type);
  LONGEST lo, hi;
  struct value *res;
  LONGEST i;

  /* Verify that both val and type are arrays of scalars, and
     that the size of val's elements is smaller than the size
     of type's element.  */
  gdb_assert (type->code () == TYPE_CODE_ARRAY);
  gdb_assert (is_integral_type (TYPE_TARGET_TYPE (type)));
  gdb_assert (value_type (val)->code () == TYPE_CODE_ARRAY);
  gdb_assert (is_integral_type (TYPE_TARGET_TYPE (value_type (val))));
  gdb_assert (TYPE_LENGTH (TYPE_TARGET_TYPE (type))
	      > TYPE_LENGTH (TYPE_TARGET_TYPE (value_type (val))));

  if (!get_array_bounds (type, &lo, &hi))
    error (_("unable to determine array bounds"));

  res = allocate_value (type);

  /* Promote each array element.  */
  for (i = 0; i < hi - lo + 1; i++)
    {
      struct value *elt = value_cast (elt_type, value_subscript (val, lo + i));

      memcpy (value_contents_writeable (res) + (i * TYPE_LENGTH (elt_type)),
	      value_contents_all (elt), TYPE_LENGTH (elt_type));
    }

  return res;
}

/* Coerce VAL as necessary for assignment to an lval of type TYPE, and
   return the converted value.  */

static struct value *
coerce_for_assign (struct type *type, struct value *val)
{
  struct type *type2 = value_type (val);

  if (type == type2)
    return val;

  type2 = ada_check_typedef (type2);
  type = ada_check_typedef (type);

  if (type2->code () == TYPE_CODE_PTR
      && type->code () == TYPE_CODE_ARRAY)
    {
      val = ada_value_ind (val);
      type2 = value_type (val);
    }

  if (type2->code () == TYPE_CODE_ARRAY
      && type->code () == TYPE_CODE_ARRAY)
    {
      if (!ada_same_array_size_p (type, type2))
	error (_("cannot assign arrays of different length"));

      if (is_integral_type (TYPE_TARGET_TYPE (type))
	  && is_integral_type (TYPE_TARGET_TYPE (type2))
	  && TYPE_LENGTH (TYPE_TARGET_TYPE (type2))
	       < TYPE_LENGTH (TYPE_TARGET_TYPE (type)))
	{
	  /* Allow implicit promotion of the array elements to
	     a wider type.  */
	  return ada_promote_array_of_integrals (type, val);
	}

      if (TYPE_LENGTH (TYPE_TARGET_TYPE (type2))
	  != TYPE_LENGTH (TYPE_TARGET_TYPE (type)))
	error (_("Incompatible types in assignment"));
      deprecated_set_value_type (val, type);
    }
  return val;
}

static struct value *
ada_value_binop (struct value *arg1, struct value *arg2, enum exp_opcode op)
{
  struct value *val;
  struct type *type1, *type2;
  LONGEST v, v1, v2;

  arg1 = coerce_ref (arg1);
  arg2 = coerce_ref (arg2);
  type1 = get_base_type (ada_check_typedef (value_type (arg1)));
  type2 = get_base_type (ada_check_typedef (value_type (arg2)));

  if (type1->code () != TYPE_CODE_INT
      || type2->code () != TYPE_CODE_INT)
    return value_binop (arg1, arg2, op);

  switch (op)
    {
    case BINOP_MOD:
    case BINOP_DIV:
    case BINOP_REM:
      break;
    default:
      return value_binop (arg1, arg2, op);
    }

  v2 = value_as_long (arg2);
  if (v2 == 0)
    {
      const char *name;
      if (op == BINOP_MOD)
	name = "mod";
      else if (op == BINOP_DIV)
	name = "/";
      else
	{
	  gdb_assert (op == BINOP_REM);
	  name = "rem";
	}

      error (_("second operand of %s must not be zero."), name);
    }

  if (type1->is_unsigned () || op == BINOP_MOD)
    return value_binop (arg1, arg2, op);

  v1 = value_as_long (arg1);
  switch (op)
    {
    case BINOP_DIV:
      v = v1 / v2;
      if (!TRUNCATION_TOWARDS_ZERO && v1 * (v1 % v2) < 0)
	v += v > 0 ? -1 : 1;
      break;
    case BINOP_REM:
      v = v1 % v2;
      if (v * v1 < 0)
	v -= v2;
      break;
    default:
      /* Should not reach this point.  */
      v = 0;
    }

  val = allocate_value (type1);
  store_unsigned_integer (value_contents_raw (val),
			  TYPE_LENGTH (value_type (val)),
			  type_byte_order (type1), v);
  return val;
}

static int
ada_value_equal (struct value *arg1, struct value *arg2)
{
  if (ada_is_direct_array_type (value_type (arg1))
      || ada_is_direct_array_type (value_type (arg2)))
    {
      struct type *arg1_type, *arg2_type;

      /* Automatically dereference any array reference before
	 we attempt to perform the comparison.  */
      arg1 = ada_coerce_ref (arg1);
      arg2 = ada_coerce_ref (arg2);

      arg1 = ada_coerce_to_simple_array (arg1);
      arg2 = ada_coerce_to_simple_array (arg2);

      arg1_type = ada_check_typedef (value_type (arg1));
      arg2_type = ada_check_typedef (value_type (arg2));

      if (arg1_type->code () != TYPE_CODE_ARRAY
	  || arg2_type->code () != TYPE_CODE_ARRAY)
	error (_("Attempt to compare array with non-array"));
      /* FIXME: The following works only for types whose
	 representations use all bits (no padding or undefined bits)
	 and do not have user-defined equality.  */
      return (TYPE_LENGTH (arg1_type) == TYPE_LENGTH (arg2_type)
	      && memcmp (value_contents (arg1), value_contents (arg2),
			 TYPE_LENGTH (arg1_type)) == 0);
    }
  return value_equal (arg1, arg2);
}

namespace expr
{

bool
check_objfile (const std::unique_ptr<ada_component> &comp,
	       struct objfile *objfile)
{
  return comp->uses_objfile (objfile);
}

/* Assign the result of evaluating ARG starting at *POS to the INDEXth
   component of LHS (a simple array or a record).  Does not modify the
   inferior's memory, nor does it modify LHS (unless LHS ==
   CONTAINER).  */

static void
assign_component (struct value *container, struct value *lhs, LONGEST index,
		  struct expression *exp, operation_up &arg)
{
  scoped_value_mark mark;

  struct value *elt;
  struct type *lhs_type = check_typedef (value_type (lhs));

  if (lhs_type->code () == TYPE_CODE_ARRAY)
    {
      struct type *index_type = builtin_type (exp->gdbarch)->builtin_int;
      struct value *index_val = value_from_longest (index_type, index);

      elt = unwrap_value (ada_value_subscript (lhs, 1, &index_val));
    }
  else
    {
      elt = ada_index_struct_field (index, lhs, 0, value_type (lhs));
      elt = ada_to_fixed_value (elt);
    }

  ada_aggregate_operation *ag_op
    = dynamic_cast<ada_aggregate_operation *> (arg.get ());
  if (ag_op != nullptr)
    ag_op->assign_aggregate (container, elt, exp);
  else
    value_assign_to_component (container, elt,
			       arg->evaluate (nullptr, exp,
					      EVAL_NORMAL));
}

bool
ada_aggregate_component::uses_objfile (struct objfile *objfile)
{
  for (const auto &item : m_components)
    if (item->uses_objfile (objfile))
      return true;
  return false;
}

void
ada_aggregate_component::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sAggregate\n"), depth, "");
  for (const auto &item : m_components)
    item->dump (stream, depth + 1);
}

void
ada_aggregate_component::assign (struct value *container,
				 struct value *lhs, struct expression *exp,
				 std::vector<LONGEST> &indices,
				 LONGEST low, LONGEST high)
{
  for (auto &item : m_components)
    item->assign (container, lhs, exp, indices, low, high);
}

/* See ada-exp.h.  */

value *
ada_aggregate_operation::assign_aggregate (struct value *container,
					   struct value *lhs,
					   struct expression *exp)
{
  struct type *lhs_type;
  LONGEST low_index, high_index;

  container = ada_coerce_ref (container);
  if (ada_is_direct_array_type (value_type (container)))
    container = ada_coerce_to_simple_array (container);
  lhs = ada_coerce_ref (lhs);
  if (!deprecated_value_modifiable (lhs))
    error (_("Left operand of assignment is not a modifiable lvalue."));

  lhs_type = check_typedef (value_type (lhs));
  if (ada_is_direct_array_type (lhs_type))
    {
      lhs = ada_coerce_to_simple_array (lhs);
      lhs_type = check_typedef (value_type (lhs));
      low_index = lhs_type->bounds ()->low.const_val ();
      high_index = lhs_type->bounds ()->high.const_val ();
    }
  else if (lhs_type->code () == TYPE_CODE_STRUCT)
    {
      low_index = 0;
      high_index = num_visible_fields (lhs_type) - 1;
    }
  else
    error (_("Left-hand side must be array or record."));

  std::vector<LONGEST> indices (4);
  indices[0] = indices[1] = low_index - 1;
  indices[2] = indices[3] = high_index + 1;

  std::get<0> (m_storage)->assign (container, lhs, exp, indices,
				   low_index, high_index);

  return container;
}

bool
ada_positional_component::uses_objfile (struct objfile *objfile)
{
  return m_op->uses_objfile (objfile);
}

void
ada_positional_component::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sPositional, index = %d\n"),
		    depth, "", m_index);
  m_op->dump (stream, depth + 1);
}

/* Assign into the component of LHS indexed by the OP_POSITIONAL
   construct, given that the positions are relative to lower bound
   LOW, where HIGH is the upper bound.  Record the position in
   INDICES.  CONTAINER is as for assign_aggregate.  */
void
ada_positional_component::assign (struct value *container,
				  struct value *lhs, struct expression *exp,
				  std::vector<LONGEST> &indices,
				  LONGEST low, LONGEST high)
{
  LONGEST ind = m_index + low;

  if (ind - 1 == high)
    warning (_("Extra components in aggregate ignored."));
  if (ind <= high)
    {
      add_component_interval (ind, ind, indices);
      assign_component (container, lhs, ind, exp, m_op);
    }
}

bool
ada_discrete_range_association::uses_objfile (struct objfile *objfile)
{
  return m_low->uses_objfile (objfile) || m_high->uses_objfile (objfile);
}

void
ada_discrete_range_association::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sDiscrete range:\n"), depth, "");
  m_low->dump (stream, depth + 1);
  m_high->dump (stream, depth + 1);
}

void
ada_discrete_range_association::assign (struct value *container,
					struct value *lhs,
					struct expression *exp,
					std::vector<LONGEST> &indices,
					LONGEST low, LONGEST high,
					operation_up &op)
{
  LONGEST lower = value_as_long (m_low->evaluate (nullptr, exp, EVAL_NORMAL));
  LONGEST upper = value_as_long (m_high->evaluate (nullptr, exp, EVAL_NORMAL));

  if (lower <= upper && (lower < low || upper > high))
    error (_("Index in component association out of bounds."));

  add_component_interval (lower, upper, indices);
  while (lower <= upper)
    {
      assign_component (container, lhs, lower, exp, op);
      lower += 1;
    }
}

bool
ada_name_association::uses_objfile (struct objfile *objfile)
{
  return m_val->uses_objfile (objfile);
}

void
ada_name_association::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sName:\n"), depth, "");
  m_val->dump (stream, depth + 1);
}

void
ada_name_association::assign (struct value *container,
			      struct value *lhs,
			      struct expression *exp,
			      std::vector<LONGEST> &indices,
			      LONGEST low, LONGEST high,
			      operation_up &op)
{
  int index;

  if (ada_is_direct_array_type (value_type (lhs)))
    index = longest_to_int (value_as_long (m_val->evaluate (nullptr, exp,
							    EVAL_NORMAL)));
  else
    {
      ada_string_operation *strop
	= dynamic_cast<ada_string_operation *> (m_val.get ());

      const char *name;
      if (strop != nullptr)
	name = strop->get_name ();
      else
	{
	  ada_var_value_operation *vvo
	    = dynamic_cast<ada_var_value_operation *> (m_val.get ());
	  if (vvo != nullptr)
	    error (_("Invalid record component association."));
	  name = vvo->get_symbol ()->natural_name ();
	}

      index = 0;
      if (! find_struct_field (name, value_type (lhs), 0,
			       NULL, NULL, NULL, NULL, &index))
	error (_("Unknown component name: %s."), name);
    }

  add_component_interval (index, index, indices);
  assign_component (container, lhs, index, exp, op);
}

bool
ada_choices_component::uses_objfile (struct objfile *objfile)
{
  if (m_op->uses_objfile (objfile))
    return true;
  for (const auto &item : m_assocs)
    if (item->uses_objfile (objfile))
      return true;
  return false;
}

void
ada_choices_component::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sChoices:\n"), depth, "");
  m_op->dump (stream, depth + 1);
  for (const auto &item : m_assocs)
    item->dump (stream, depth + 1);
}

/* Assign into the components of LHS indexed by the OP_CHOICES
   construct at *POS, updating *POS past the construct, given that
   the allowable indices are LOW..HIGH.  Record the indices assigned
   to in INDICES.  CONTAINER is as for assign_aggregate.  */
void
ada_choices_component::assign (struct value *container,
			       struct value *lhs, struct expression *exp,
			       std::vector<LONGEST> &indices,
			       LONGEST low, LONGEST high)
{
  for (auto &item : m_assocs)
    item->assign (container, lhs, exp, indices, low, high, m_op);
}

bool
ada_others_component::uses_objfile (struct objfile *objfile)
{
  return m_op->uses_objfile (objfile);
}

void
ada_others_component::dump (ui_file *stream, int depth)
{
  fprintf_filtered (stream, _("%*sOthers:\n"), depth, "");
  m_op->dump (stream, depth + 1);
}

/* Assign the value of the expression in the OP_OTHERS construct in
   EXP at *POS into the components of LHS indexed from LOW .. HIGH that
   have not been previously assigned.  The index intervals already assigned
   are in INDICES.  CONTAINER is as for assign_aggregate.  */
void
ada_others_component::assign (struct value *container,
			      struct value *lhs, struct expression *exp,
			      std::vector<LONGEST> &indices,
			      LONGEST low, LONGEST high)
{
  int num_indices = indices.size ();
  for (int i = 0; i < num_indices - 2; i += 2)
    {
      for (LONGEST ind = indices[i + 1] + 1; ind < indices[i + 2]; ind += 1)
	assign_component (container, lhs, ind, exp, m_op);
    }
}

struct value *
ada_assign_operation::evaluate (struct type *expect_type,
				struct expression *exp,
				enum noside noside)
{
  value *arg1 = std::get<0> (m_storage)->evaluate (nullptr, exp, noside);

  ada_aggregate_operation *ag_op
    = dynamic_cast<ada_aggregate_operation *> (std::get<1> (m_storage).get ());
  if (ag_op != nullptr)
    {
      if (noside != EVAL_NORMAL)
	return arg1;

      arg1 = ag_op->assign_aggregate (arg1, arg1, exp);
      return ada_value_assign (arg1, arg1);
    }
  /* Force the evaluation of the rhs ARG2 to the type of the lhs ARG1,
     except if the lhs of our assignment is a convenience variable.
     In the case of assigning to a convenience variable, the lhs
     should be exactly the result of the evaluation of the rhs.  */
  struct type *type = value_type (arg1);
  if (VALUE_LVAL (arg1) == lval_internalvar)
    type = NULL;
  value *arg2 = std::get<1> (m_storage)->evaluate (type, exp, noside);
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return arg1;
  if (VALUE_LVAL (arg1) == lval_internalvar)
    {
      /* Nothing.  */
    }
  else
    arg2 = coerce_for_assign (value_type (arg1), arg2);
  return ada_value_assign (arg1, arg2);
}

} /* namespace expr */

/* Add the interval [LOW .. HIGH] to the sorted set of intervals
   [ INDICES[0] .. INDICES[1] ],...  The resulting intervals do not
   overlap.  */
static void
add_component_interval (LONGEST low, LONGEST high, 
			std::vector<LONGEST> &indices)
{
  int i, j;

  int size = indices.size ();
  for (i = 0; i < size; i += 2) {
    if (high >= indices[i] && low <= indices[i + 1])
      {
	int kh;

	for (kh = i + 2; kh < size; kh += 2)
	  if (high < indices[kh])
	    break;
	if (low < indices[i])
	  indices[i] = low;
	indices[i + 1] = indices[kh - 1];
	if (high > indices[i + 1])
	  indices[i + 1] = high;
	memcpy (indices.data () + i + 2, indices.data () + kh, size - kh);
	indices.resize (kh - i - 2);
	return;
      }
    else if (high < indices[i])
      break;
  }
	
  indices.resize (indices.size () + 2);
  for (j = indices.size () - 1; j >= i + 2; j -= 1)
    indices[j] = indices[j - 2];
  indices[i] = low;
  indices[i + 1] = high;
}

/* Perform and Ada cast of ARG2 to type TYPE if the type of ARG2
   is different.  */

static struct value *
ada_value_cast (struct type *type, struct value *arg2)
{
  if (type == ada_check_typedef (value_type (arg2)))
    return arg2;

  return value_cast (type, arg2);
}

/*  Evaluating Ada expressions, and printing their result.
    ------------------------------------------------------

    1. Introduction:
    ----------------

    We usually evaluate an Ada expression in order to print its value.
    We also evaluate an expression in order to print its type, which
    happens during the EVAL_AVOID_SIDE_EFFECTS phase of the evaluation,
    but we'll focus mostly on the EVAL_NORMAL phase.  In practice, the
    EVAL_AVOID_SIDE_EFFECTS phase allows us to simplify certain aspects of
    the evaluation compared to the EVAL_NORMAL, but is otherwise very
    similar.

    Evaluating expressions is a little more complicated for Ada entities
    than it is for entities in languages such as C.  The main reason for
    this is that Ada provides types whose definition might be dynamic.
    One example of such types is variant records.  Or another example
    would be an array whose bounds can only be known at run time.

    The following description is a general guide as to what should be
    done (and what should NOT be done) in order to evaluate an expression
    involving such types, and when.  This does not cover how the semantic
    information is encoded by GNAT as this is covered separatly.  For the
    document used as the reference for the GNAT encoding, see exp_dbug.ads
    in the GNAT sources.

    Ideally, we should embed each part of this description next to its
    associated code.  Unfortunately, the amount of code is so vast right
    now that it's hard to see whether the code handling a particular
    situation might be duplicated or not.  One day, when the code is
    cleaned up, this guide might become redundant with the comments
    inserted in the code, and we might want to remove it.

    2. ``Fixing'' an Entity, the Simple Case:
    -----------------------------------------

    When evaluating Ada expressions, the tricky issue is that they may
    reference entities whose type contents and size are not statically
    known.  Consider for instance a variant record:

       type Rec (Empty : Boolean := True) is record
	  case Empty is
	     when True => null;
	     when False => Value : Integer;
	  end case;
       end record;
       Yes : Rec := (Empty => False, Value => 1);
       No  : Rec := (empty => True);

    The size and contents of that record depends on the value of the
    descriminant (Rec.Empty).  At this point, neither the debugging
    information nor the associated type structure in GDB are able to
    express such dynamic types.  So what the debugger does is to create
    "fixed" versions of the type that applies to the specific object.
    We also informally refer to this operation as "fixing" an object,
    which means creating its associated fixed type.

    Example: when printing the value of variable "Yes" above, its fixed
    type would look like this:

       type Rec is record
	  Empty : Boolean;
	  Value : Integer;
       end record;

    On the other hand, if we printed the value of "No", its fixed type
    would become:

       type Rec is record
	  Empty : Boolean;
       end record;

    Things become a little more complicated when trying to fix an entity
    with a dynamic type that directly contains another dynamic type,
    such as an array of variant records, for instance.  There are
    two possible cases: Arrays, and records.

    3. ``Fixing'' Arrays:
    ---------------------

    The type structure in GDB describes an array in terms of its bounds,
    and the type of its elements.  By design, all elements in the array
    have the same type and we cannot represent an array of variant elements
    using the current type structure in GDB.  When fixing an array,
    we cannot fix the array element, as we would potentially need one
    fixed type per element of the array.  As a result, the best we can do
    when fixing an array is to produce an array whose bounds and size
    are correct (allowing us to read it from memory), but without having
    touched its element type.  Fixing each element will be done later,
    when (if) necessary.

    Arrays are a little simpler to handle than records, because the same
    amount of memory is allocated for each element of the array, even if
    the amount of space actually used by each element differs from element
    to element.  Consider for instance the following array of type Rec:

       type Rec_Array is array (1 .. 2) of Rec;

    The actual amount of memory occupied by each element might be different
    from element to element, depending on the value of their discriminant.
    But the amount of space reserved for each element in the array remains
    fixed regardless.  So we simply need to compute that size using
    the debugging information available, from which we can then determine
    the array size (we multiply the number of elements of the array by
    the size of each element).

    The simplest case is when we have an array of a constrained element
    type. For instance, consider the following type declarations:

	type Bounded_String (Max_Size : Integer) is
	   Length : Integer;
	   Buffer : String (1 .. Max_Size);
	end record;
	type Bounded_String_Array is array (1 ..2) of Bounded_String (80);

    In this case, the compiler describes the array as an array of
    variable-size elements (identified by its XVS suffix) for which
    the size can be read in the parallel XVZ variable.

    In the case of an array of an unconstrained element type, the compiler
    wraps the array element inside a private PAD type.  This type should not
    be shown to the user, and must be "unwrap"'ed before printing.  Note
    that we also use the adjective "aligner" in our code to designate
    these wrapper types.

    In some cases, the size allocated for each element is statically
    known.  In that case, the PAD type already has the correct size,
    and the array element should remain unfixed.

    But there are cases when this size is not statically known.
    For instance, assuming that "Five" is an integer variable:

	type Dynamic is array (1 .. Five) of Integer;
	type Wrapper (Has_Length : Boolean := False) is record
	   Data : Dynamic;
	   case Has_Length is
	      when True => Length : Integer;
	      when False => null;
	   end case;
	end record;
	type Wrapper_Array is array (1 .. 2) of Wrapper;

	Hello : Wrapper_Array := (others => (Has_Length => True,
					     Data => (others => 17),
					     Length => 1));


    The debugging info would describe variable Hello as being an
    array of a PAD type.  The size of that PAD type is not statically
    known, but can be determined using a parallel XVZ variable.
    In that case, a copy of the PAD type with the correct size should
    be used for the fixed array.

    3. ``Fixing'' record type objects:
    ----------------------------------

    Things are slightly different from arrays in the case of dynamic
    record types.  In this case, in order to compute the associated
    fixed type, we need to determine the size and offset of each of
    its components.  This, in turn, requires us to compute the fixed
    type of each of these components.

    Consider for instance the example:

	type Bounded_String (Max_Size : Natural) is record
	   Str : String (1 .. Max_Size);
	   Length : Natural;
	end record;
	My_String : Bounded_String (Max_Size => 10);

    In that case, the position of field "Length" depends on the size
    of field Str, which itself depends on the value of the Max_Size
    discriminant.  In order to fix the type of variable My_String,
    we need to fix the type of field Str.  Therefore, fixing a variant
    record requires us to fix each of its components.

    However, if a component does not have a dynamic size, the component
    should not be fixed.  In particular, fields that use a PAD type
    should not fixed.  Here is an example where this might happen
    (assuming type Rec above):

       type Container (Big : Boolean) is record
	  First : Rec;
	  After : Integer;
	  case Big is
	     when True => Another : Integer;
	     when False => null;
	  end case;
       end record;
       My_Container : Container := (Big => False,
				    First => (Empty => True),
				    After => 42);

    In that example, the compiler creates a PAD type for component First,
    whose size is constant, and then positions the component After just
    right after it.  The offset of component After is therefore constant
    in this case.

    The debugger computes the position of each field based on an algorithm
    that uses, among other things, the actual position and size of the field
    preceding it.  Let's now imagine that the user is trying to print
    the value of My_Container.  If the type fixing was recursive, we would
    end up computing the offset of field After based on the size of the
    fixed version of field First.  And since in our example First has
    only one actual field, the size of the fixed type is actually smaller
    than the amount of space allocated to that field, and thus we would
    compute the wrong offset of field After.

    To make things more complicated, we need to watch out for dynamic
    components of variant records (identified by the ___XVL suffix in
    the component name).  Even if the target type is a PAD type, the size
    of that type might not be statically known.  So the PAD type needs
    to be unwrapped and the resulting type needs to be fixed.  Otherwise,
    we might end up with the wrong size for our component.  This can be
    observed with the following type declarations:

	type Octal is new Integer range 0 .. 7;
	type Octal_Array is array (Positive range <>) of Octal;
	pragma Pack (Octal_Array);

	type Octal_Buffer (Size : Positive) is record
	   Buffer : Octal_Array (1 .. Size);
	   Length : Integer;
	end record;

    In that case, Buffer is a PAD type whose size is unset and needs
    to be computed by fixing the unwrapped type.

    4. When to ``Fix'' un-``Fixed'' sub-elements of an entity:
    ----------------------------------------------------------

    Lastly, when should the sub-elements of an entity that remained unfixed
    thus far, be actually fixed?

    The answer is: Only when referencing that element.  For instance
    when selecting one component of a record, this specific component
    should be fixed at that point in time.  Or when printing the value
    of a record, each component should be fixed before its value gets
    printed.  Similarly for arrays, the element of the array should be
    fixed when printing each element of the array, or when extracting
    one element out of that array.  On the other hand, fixing should
    not be performed on the elements when taking a slice of an array!

    Note that one of the side effects of miscomputing the offset and
    size of each field is that we end up also miscomputing the size
    of the containing type.  This can have adverse results when computing
    the value of an entity.  GDB fetches the value of an entity based
    on the size of its type, and thus a wrong size causes GDB to fetch
    the wrong amount of memory.  In the case where the computed size is
    too small, GDB fetches too little data to print the value of our
    entity.  Results in this case are unpredictable, as we usually read
    past the buffer containing the data =:-o.  */

/* A helper function for TERNOP_IN_RANGE.  */

static value *
eval_ternop_in_range (struct type *expect_type, struct expression *exp,
		      enum noside noside,
		      value *arg1, value *arg2, value *arg3)
{
  binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
  binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg3);
  struct type *type = language_bool_type (exp->language_defn, exp->gdbarch);
  return
    value_from_longest (type,
			(value_less (arg1, arg3)
			 || value_equal (arg1, arg3))
			&& (value_less (arg2, arg1)
			    || value_equal (arg2, arg1)));
}

/* A helper function for UNOP_NEG.  */

value *
ada_unop_neg (struct type *expect_type,
	      struct expression *exp,
	      enum noside noside, enum exp_opcode op,
	      struct value *arg1)
{
  unop_promote (exp->language_defn, exp->gdbarch, &arg1);
  return value_neg (arg1);
}

/* A helper function for UNOP_IN_RANGE.  */

value *
ada_unop_in_range (struct type *expect_type,
		   struct expression *exp,
		   enum noside noside, enum exp_opcode op,
		   struct value *arg1, struct type *type)
{
  struct value *arg2, *arg3;
  switch (type->code ())
    {
    default:
      lim_warning (_("Membership test incompletely implemented; "
		     "always returns true"));
      type = language_bool_type (exp->language_defn, exp->gdbarch);
      return value_from_longest (type, (LONGEST) 1);

    case TYPE_CODE_RANGE:
      arg2 = value_from_longest (type,
				 type->bounds ()->low.const_val ());
      arg3 = value_from_longest (type,
				 type->bounds ()->high.const_val ());
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg3);
      type = language_bool_type (exp->language_defn, exp->gdbarch);
      return
	value_from_longest (type,
			    (value_less (arg1, arg3)
			     || value_equal (arg1, arg3))
			    && (value_less (arg2, arg1)
				|| value_equal (arg2, arg1)));
    }
}

/* A helper function for OP_ATR_TAG.  */

value *
ada_atr_tag (struct type *expect_type,
	     struct expression *exp,
	     enum noside noside, enum exp_opcode op,
	     struct value *arg1)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (ada_tag_type (arg1), not_lval);

  return ada_value_tag (arg1);
}

/* A helper function for OP_ATR_SIZE.  */

value *
ada_atr_size (struct type *expect_type,
	      struct expression *exp,
	      enum noside noside, enum exp_opcode op,
	      struct value *arg1)
{
  struct type *type = value_type (arg1);

  /* If the argument is a reference, then dereference its type, since
     the user is really asking for the size of the actual object,
     not the size of the pointer.  */
  if (type->code () == TYPE_CODE_REF)
    type = TYPE_TARGET_TYPE (type);

  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (builtin_type (exp->gdbarch)->builtin_int, not_lval);
  else
    return value_from_longest (builtin_type (exp->gdbarch)->builtin_int,
			       TARGET_CHAR_BIT * TYPE_LENGTH (type));
}

/* A helper function for UNOP_ABS.  */

value *
ada_abs (struct type *expect_type,
	 struct expression *exp,
	 enum noside noside, enum exp_opcode op,
	 struct value *arg1)
{
  unop_promote (exp->language_defn, exp->gdbarch, &arg1);
  if (value_less (arg1, value_zero (value_type (arg1), not_lval)))
    return value_neg (arg1);
  else
    return arg1;
}

/* A helper function for BINOP_MUL.  */

value *
ada_mult_binop (struct type *expect_type,
		struct expression *exp,
		enum noside noside, enum exp_opcode op,
		struct value *arg1, struct value *arg2)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
      return value_zero (value_type (arg1), not_lval);
    }
  else
    {
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
      return ada_value_binop (arg1, arg2, op);
    }
}

/* A helper function for BINOP_EQUAL and BINOP_NOTEQUAL.  */

value *
ada_equal_binop (struct type *expect_type,
		 struct expression *exp,
		 enum noside noside, enum exp_opcode op,
		 struct value *arg1, struct value *arg2)
{
  int tem;
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    tem = 0;
  else
    {
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
      tem = ada_value_equal (arg1, arg2);
    }
  if (op == BINOP_NOTEQUAL)
    tem = !tem;
  struct type *type = language_bool_type (exp->language_defn, exp->gdbarch);
  return value_from_longest (type, (LONGEST) tem);
}

/* A helper function for TERNOP_SLICE.  */

value *
ada_ternop_slice (struct expression *exp,
		  enum noside noside,
		  struct value *array, struct value *low_bound_val,
		  struct value *high_bound_val)
{
  LONGEST low_bound;
  LONGEST high_bound;

  low_bound_val = coerce_ref (low_bound_val);
  high_bound_val = coerce_ref (high_bound_val);
  low_bound = value_as_long (low_bound_val);
  high_bound = value_as_long (high_bound_val);

  /* If this is a reference to an aligner type, then remove all
     the aligners.  */
  if (value_type (array)->code () == TYPE_CODE_REF
      && ada_is_aligner_type (TYPE_TARGET_TYPE (value_type (array))))
    TYPE_TARGET_TYPE (value_type (array)) =
      ada_aligned_type (TYPE_TARGET_TYPE (value_type (array)));

  if (ada_is_any_packed_array_type (value_type (array)))
    error (_("cannot slice a packed array"));

  /* If this is a reference to an array or an array lvalue,
     convert to a pointer.  */
  if (value_type (array)->code () == TYPE_CODE_REF
      || (value_type (array)->code () == TYPE_CODE_ARRAY
	  && VALUE_LVAL (array) == lval_memory))
    array = value_addr (array);

  if (noside == EVAL_AVOID_SIDE_EFFECTS
      && ada_is_array_descriptor_type (ada_check_typedef
				       (value_type (array))))
    return empty_array (ada_type_of_array (array, 0), low_bound,
			high_bound);

  array = ada_coerce_to_simple_array_ptr (array);

  /* If we have more than one level of pointer indirection,
     dereference the value until we get only one level.  */
  while (value_type (array)->code () == TYPE_CODE_PTR
	 && (TYPE_TARGET_TYPE (value_type (array))->code ()
	     == TYPE_CODE_PTR))
    array = value_ind (array);

  /* Make sure we really do have an array type before going further,
     to avoid a SEGV when trying to get the index type or the target
     type later down the road if the debug info generated by
     the compiler is incorrect or incomplete.  */
  if (!ada_is_simple_array_type (value_type (array)))
    error (_("cannot take slice of non-array"));

  if (ada_check_typedef (value_type (array))->code ()
      == TYPE_CODE_PTR)
    {
      struct type *type0 = ada_check_typedef (value_type (array));

      if (high_bound < low_bound || noside == EVAL_AVOID_SIDE_EFFECTS)
	return empty_array (TYPE_TARGET_TYPE (type0), low_bound, high_bound);
      else
	{
	  struct type *arr_type0 =
	    to_fixed_array_type (TYPE_TARGET_TYPE (type0), NULL, 1);

	  return ada_value_slice_from_ptr (array, arr_type0,
					   longest_to_int (low_bound),
					   longest_to_int (high_bound));
	}
    }
  else if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return array;
  else if (high_bound < low_bound)
    return empty_array (value_type (array), low_bound, high_bound);
  else
    return ada_value_slice (array, longest_to_int (low_bound),
			    longest_to_int (high_bound));
}

/* A helper function for BINOP_IN_BOUNDS.  */

value *
ada_binop_in_bounds (struct expression *exp, enum noside noside,
		     struct value *arg1, struct value *arg2, int n)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      struct type *type = language_bool_type (exp->language_defn,
					      exp->gdbarch);
      return value_zero (type, not_lval);
    }

  struct type *type = ada_index_type (value_type (arg2), n, "range");
  if (!type)
    type = value_type (arg1);

  value *arg3 = value_from_longest (type, ada_array_bound (arg2, n, 1));
  arg2 = value_from_longest (type, ada_array_bound (arg2, n, 0));

  binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
  binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg3);
  type = language_bool_type (exp->language_defn, exp->gdbarch);
  return value_from_longest (type,
			     (value_less (arg1, arg3)
			      || value_equal (arg1, arg3))
			     && (value_less (arg2, arg1)
				 || value_equal (arg2, arg1)));
}

/* A helper function for some attribute operations.  */

static value *
ada_unop_atr (struct expression *exp, enum noside noside, enum exp_opcode op,
	      struct value *arg1, struct type *type_arg, int tem)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      if (type_arg == NULL)
	type_arg = value_type (arg1);

      if (ada_is_constrained_packed_array_type (type_arg))
	type_arg = decode_constrained_packed_array_type (type_arg);

      if (!discrete_type_p (type_arg))
	{
	  switch (op)
	    {
	    default:          /* Should never happen.  */
	      error (_("unexpected attribute encountered"));
	    case OP_ATR_FIRST:
	    case OP_ATR_LAST:
	      type_arg = ada_index_type (type_arg, tem,
					 ada_attribute_name (op));
	      break;
	    case OP_ATR_LENGTH:
	      type_arg = builtin_type (exp->gdbarch)->builtin_int;
	      break;
	    }
	}

      return value_zero (type_arg, not_lval);
    }
  else if (type_arg == NULL)
    {
      arg1 = ada_coerce_ref (arg1);

      if (ada_is_constrained_packed_array_type (value_type (arg1)))
	arg1 = ada_coerce_to_simple_array (arg1);

      struct type *type;
      if (op == OP_ATR_LENGTH)
	type = builtin_type (exp->gdbarch)->builtin_int;
      else
	{
	  type = ada_index_type (value_type (arg1), tem,
				 ada_attribute_name (op));
	  if (type == NULL)
	    type = builtin_type (exp->gdbarch)->builtin_int;
	}

      switch (op)
	{
	default:          /* Should never happen.  */
	  error (_("unexpected attribute encountered"));
	case OP_ATR_FIRST:
	  return value_from_longest
	    (type, ada_array_bound (arg1, tem, 0));
	case OP_ATR_LAST:
	  return value_from_longest
	    (type, ada_array_bound (arg1, tem, 1));
	case OP_ATR_LENGTH:
	  return value_from_longest
	    (type, ada_array_length (arg1, tem));
	}
    }
  else if (discrete_type_p (type_arg))
    {
      struct type *range_type;
      const char *name = ada_type_name (type_arg);

      range_type = NULL;
      if (name != NULL && type_arg->code () != TYPE_CODE_ENUM)
	range_type = to_fixed_range_type (type_arg, NULL);
      if (range_type == NULL)
	range_type = type_arg;
      switch (op)
	{
	default:
	  error (_("unexpected attribute encountered"));
	case OP_ATR_FIRST:
	  return value_from_longest 
	    (range_type, ada_discrete_type_low_bound (range_type));
	case OP_ATR_LAST:
	  return value_from_longest
	    (range_type, ada_discrete_type_high_bound (range_type));
	case OP_ATR_LENGTH:
	  error (_("the 'length attribute applies only to array types"));
	}
    }
  else if (type_arg->code () == TYPE_CODE_FLT)
    error (_("unimplemented type attribute"));
  else
    {
      LONGEST low, high;

      if (ada_is_constrained_packed_array_type (type_arg))
	type_arg = decode_constrained_packed_array_type (type_arg);

      struct type *type;
      if (op == OP_ATR_LENGTH)
	type = builtin_type (exp->gdbarch)->builtin_int;
      else
	{
	  type = ada_index_type (type_arg, tem, ada_attribute_name (op));
	  if (type == NULL)
	    type = builtin_type (exp->gdbarch)->builtin_int;
	}

      switch (op)
	{
	default:
	  error (_("unexpected attribute encountered"));
	case OP_ATR_FIRST:
	  low = ada_array_bound_from_type (type_arg, tem, 0);
	  return value_from_longest (type, low);
	case OP_ATR_LAST:
	  high = ada_array_bound_from_type (type_arg, tem, 1);
	  return value_from_longest (type, high);
	case OP_ATR_LENGTH:
	  low = ada_array_bound_from_type (type_arg, tem, 0);
	  high = ada_array_bound_from_type (type_arg, tem, 1);
	  return value_from_longest (type, high - low + 1);
	}
    }
}

/* A helper function for OP_ATR_MIN and OP_ATR_MAX.  */

struct value *
ada_binop_minmax (struct type *expect_type,
		  struct expression *exp,
		  enum noside noside, enum exp_opcode op,
		  struct value *arg1, struct value *arg2)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (value_type (arg1), not_lval);
  else
    {
      binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
      return value_binop (arg1, arg2, op);
    }
}

/* A helper function for BINOP_EXP.  */

struct value *
ada_binop_exp (struct type *expect_type,
	       struct expression *exp,
	       enum noside noside, enum exp_opcode op,
	       struct value *arg1, struct value *arg2)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (value_type (arg1), not_lval);
  else
    {
      /* For integer exponentiation operations,
	 only promote the first argument.  */
      if (is_integral_type (value_type (arg2)))
	unop_promote (exp->language_defn, exp->gdbarch, &arg1);
      else
	binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);

      return value_binop (arg1, arg2, op);
    }
}

namespace expr
{

/* See ada-exp.h.  */

operation_up
ada_resolvable::replace (operation_up &&owner,
			 struct expression *exp,
			 bool deprocedure_p,
			 bool parse_completion,
			 innermost_block_tracker *tracker,
			 struct type *context_type)
{
  if (resolve (exp, deprocedure_p, parse_completion, tracker, context_type))
    return (make_operation<ada_funcall_operation>
	    (std::move (owner),
	     std::vector<operation_up> ()));
  return std::move (owner);
}

/* Convert the character literal whose ASCII value would be VAL to the
   appropriate value of type TYPE, if there is a translation.
   Otherwise return VAL.  Hence, in an enumeration type ('A', 'B'),
   the literal 'A' (VAL == 65), returns 0.  */

static LONGEST
convert_char_literal (struct type *type, LONGEST val)
{
  char name[7];
  int f;

  if (type == NULL)
    return val;
  type = check_typedef (type);
  if (type->code () != TYPE_CODE_ENUM)
    return val;

  if ((val >= 'a' && val <= 'z') || (val >= '0' && val <= '9'))
    xsnprintf (name, sizeof (name), "Q%c", (int) val);
  else
    xsnprintf (name, sizeof (name), "QU%02x", (int) val);
  size_t len = strlen (name);
  for (f = 0; f < type->num_fields (); f += 1)
    {
      /* Check the suffix because an enum constant in a package will
	 have a name like "pkg__QUxx".  This is safe enough because we
	 already have the correct type, and because mangling means
	 there can't be clashes.  */
      const char *ename = TYPE_FIELD_NAME (type, f);
      size_t elen = strlen (ename);

      if (elen >= len && strcmp (name, ename + elen - len) == 0)
	return TYPE_FIELD_ENUMVAL (type, f);
    }
  return val;
}

/* See ada-exp.h.  */

operation_up
ada_char_operation::replace (operation_up &&owner,
			     struct expression *exp,
			     bool deprocedure_p,
			     bool parse_completion,
			     innermost_block_tracker *tracker,
			     struct type *context_type)
{
  operation_up result = std::move (owner);

  if (context_type != nullptr && context_type->code () == TYPE_CODE_ENUM)
    {
      gdb_assert (result.get () == this);
      std::get<0> (m_storage) = context_type;
      std::get<1> (m_storage)
	= convert_char_literal (context_type, std::get<1> (m_storage));
    }

  return make_operation<ada_wrapped_operation> (std::move (result));
}

value *
ada_wrapped_operation::evaluate (struct type *expect_type,
				 struct expression *exp,
				 enum noside noside)
{
  value *result = std::get<0> (m_storage)->evaluate (expect_type, exp, noside);
  if (noside == EVAL_NORMAL)
    result = unwrap_value (result);

  /* If evaluating an OP_FLOAT and an EXPECT_TYPE was provided,
     then we need to perform the conversion manually, because
     evaluate_subexp_standard doesn't do it.  This conversion is
     necessary in Ada because the different kinds of float/fixed
     types in Ada have different representations.

     Similarly, we need to perform the conversion from OP_LONG
     ourselves.  */
  if ((opcode () == OP_FLOAT || opcode () == OP_LONG) && expect_type != NULL)
    result = ada_value_cast (expect_type, result);

  return result;
}

value *
ada_string_operation::evaluate (struct type *expect_type,
				struct expression *exp,
				enum noside noside)
{
  value *result = string_operation::evaluate (expect_type, exp, noside);
  /* The result type will have code OP_STRING, bashed there from 
     OP_ARRAY.  Bash it back.  */
  if (value_type (result)->code () == TYPE_CODE_STRING)
    value_type (result)->set_code (TYPE_CODE_ARRAY);
  return result;
}

value *
ada_qual_operation::evaluate (struct type *expect_type,
			      struct expression *exp,
			      enum noside noside)
{
  struct type *type = std::get<1> (m_storage);
  return std::get<0> (m_storage)->evaluate (type, exp, noside);
}

value *
ada_ternop_range_operation::evaluate (struct type *expect_type,
				      struct expression *exp,
				      enum noside noside)
{
  value *arg0 = std::get<0> (m_storage)->evaluate (nullptr, exp, noside);
  value *arg1 = std::get<1> (m_storage)->evaluate (nullptr, exp, noside);
  value *arg2 = std::get<2> (m_storage)->evaluate (nullptr, exp, noside);
  return eval_ternop_in_range (expect_type, exp, noside, arg0, arg1, arg2);
}

value *
ada_binop_addsub_operation::evaluate (struct type *expect_type,
				      struct expression *exp,
				      enum noside noside)
{
  value *arg1 = std::get<1> (m_storage)->evaluate_with_coercion (exp, noside);
  value *arg2 = std::get<2> (m_storage)->evaluate_with_coercion (exp, noside);

  auto do_op = [=] (LONGEST x, LONGEST y)
    {
      if (std::get<0> (m_storage) == BINOP_ADD)
	return x + y;
      return x - y;
    };

  if (value_type (arg1)->code () == TYPE_CODE_PTR)
    return (value_from_longest
	    (value_type (arg1),
	     do_op (value_as_long (arg1), value_as_long (arg2))));
  if (value_type (arg2)->code () == TYPE_CODE_PTR)
    return (value_from_longest
	    (value_type (arg2),
	     do_op (value_as_long (arg1), value_as_long (arg2))));
  /* Preserve the original type for use by the range case below.
     We cannot cast the result to a reference type, so if ARG1 is
     a reference type, find its underlying type.  */
  struct type *type = value_type (arg1);
  while (type->code () == TYPE_CODE_REF)
    type = TYPE_TARGET_TYPE (type);
  binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
  arg1 = value_binop (arg1, arg2, std::get<0> (m_storage));
  /* We need to special-case the result with a range.
     This is done for the benefit of "ptype".  gdb's Ada support
     historically used the LHS to set the result type here, so
     preserve this behavior.  */
  if (type->code () == TYPE_CODE_RANGE)
    arg1 = value_cast (type, arg1);
  return arg1;
}

value *
ada_unop_atr_operation::evaluate (struct type *expect_type,
				  struct expression *exp,
				  enum noside noside)
{
  struct type *type_arg = nullptr;
  value *val = nullptr;

  if (std::get<0> (m_storage)->opcode () == OP_TYPE)
    {
      value *tem = std::get<0> (m_storage)->evaluate (nullptr, exp,
						      EVAL_AVOID_SIDE_EFFECTS);
      type_arg = value_type (tem);
    }
  else
    val = std::get<0> (m_storage)->evaluate (nullptr, exp, noside);

  return ada_unop_atr (exp, noside, std::get<1> (m_storage),
		       val, type_arg, std::get<2> (m_storage));
}

value *
ada_var_msym_value_operation::evaluate_for_cast (struct type *expect_type,
						 struct expression *exp,
						 enum noside noside)
{
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    return value_zero (expect_type, not_lval);

  const bound_minimal_symbol &b = std::get<0> (m_storage);
  value *val = evaluate_var_msym_value (noside, b.objfile, b.minsym);

  val = ada_value_cast (expect_type, val);

  /* Follow the Ada language semantics that do not allow taking
     an address of the result of a cast (view conversion in Ada).  */
  if (VALUE_LVAL (val) == lval_memory)
    {
      if (value_lazy (val))
	value_fetch_lazy (val);
      VALUE_LVAL (val) = not_lval;
    }
  return val;
}

value *
ada_var_value_operation::evaluate_for_cast (struct type *expect_type,
					    struct expression *exp,
					    enum noside noside)
{
  value *val = evaluate_var_value (noside,
				   std::get<0> (m_storage).block,
				   std::get<0> (m_storage).symbol);

  val = ada_value_cast (expect_type, val);

  /* Follow the Ada language semantics that do not allow taking
     an address of the result of a cast (view conversion in Ada).  */
  if (VALUE_LVAL (val) == lval_memory)
    {
      if (value_lazy (val))
	value_fetch_lazy (val);
      VALUE_LVAL (val) = not_lval;
    }
  return val;
}

value *
ada_var_value_operation::evaluate (struct type *expect_type,
				   struct expression *exp,
				   enum noside noside)
{
  symbol *sym = std::get<0> (m_storage).symbol;

  if (SYMBOL_DOMAIN (sym) == UNDEF_DOMAIN)
    /* Only encountered when an unresolved symbol occurs in a
       context other than a function call, in which case, it is
       invalid.  */
    error (_("Unexpected unresolved symbol, %s, during evaluation"),
	   sym->print_name ());

  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      struct type *type = static_unwrap_type (SYMBOL_TYPE (sym));
      /* Check to see if this is a tagged type.  We also need to handle
	 the case where the type is a reference to a tagged type, but
	 we have to be careful to exclude pointers to tagged types.
	 The latter should be shown as usual (as a pointer), whereas
	 a reference should mostly be transparent to the user.  */
      if (ada_is_tagged_type (type, 0)
	  || (type->code () == TYPE_CODE_REF
	      && ada_is_tagged_type (TYPE_TARGET_TYPE (type), 0)))
	{
	  /* Tagged types are a little special in the fact that the real
	     type is dynamic and can only be determined by inspecting the
	     object's tag.  This means that we need to get the object's
	     value first (EVAL_NORMAL) and then extract the actual object
	     type from its tag.

	     Note that we cannot skip the final step where we extract
	     the object type from its tag, because the EVAL_NORMAL phase
	     results in dynamic components being resolved into fixed ones.
	     This can cause problems when trying to print the type
	     description of tagged types whose parent has a dynamic size:
	     We use the type name of the "_parent" component in order
	     to print the name of the ancestor type in the type description.
	     If that component had a dynamic size, the resolution into
	     a fixed type would result in the loss of that type name,
	     thus preventing us from printing the name of the ancestor
	     type in the type description.  */
	  value *arg1 = evaluate (nullptr, exp, EVAL_NORMAL);

	  if (type->code () != TYPE_CODE_REF)
	    {
	      struct type *actual_type;

	      actual_type = type_from_tag (ada_value_tag (arg1));
	      if (actual_type == NULL)
		/* If, for some reason, we were unable to determine
		   the actual type from the tag, then use the static
		   approximation that we just computed as a fallback.
		   This can happen if the debugging information is
		   incomplete, for instance.  */
		actual_type = type;
	      return value_zero (actual_type, not_lval);
	    }
	  else
	    {
	      /* In the case of a ref, ada_coerce_ref takes care
		 of determining the actual type.  But the evaluation
		 should return a ref as it should be valid to ask
		 for its address; so rebuild a ref after coerce.  */
	      arg1 = ada_coerce_ref (arg1);
	      return value_ref (arg1, TYPE_CODE_REF);
	    }
	}

      /* Records and unions for which GNAT encodings have been
	 generated need to be statically fixed as well.
	 Otherwise, non-static fixing produces a type where
	 all dynamic properties are removed, which prevents "ptype"
	 from being able to completely describe the type.
	 For instance, a case statement in a variant record would be
	 replaced by the relevant components based on the actual
	 value of the discriminants.  */
      if ((type->code () == TYPE_CODE_STRUCT
	   && dynamic_template_type (type) != NULL)
	  || (type->code () == TYPE_CODE_UNION
	      && ada_find_parallel_type (type, "___XVU") != NULL))
	return value_zero (to_static_fixed_type (type), not_lval);
    }

  value *arg1 = var_value_operation::evaluate (expect_type, exp, noside);
  return ada_to_fixed_value (arg1);
}

bool
ada_var_value_operation::resolve (struct expression *exp,
				  bool deprocedure_p,
				  bool parse_completion,
				  innermost_block_tracker *tracker,
				  struct type *context_type)
{
  symbol *sym = std::get<0> (m_storage).symbol;
  if (SYMBOL_DOMAIN (sym) == UNDEF_DOMAIN)
    {
      block_symbol resolved
	= ada_resolve_variable (sym, std::get<0> (m_storage).block,
				context_type, parse_completion,
				deprocedure_p, tracker);
      std::get<0> (m_storage) = resolved;
    }

  if (deprocedure_p
      && (SYMBOL_TYPE (std::get<0> (m_storage).symbol)->code ()
	  == TYPE_CODE_FUNC))
    return true;

  return false;
}

value *
ada_atr_val_operation::evaluate (struct type *expect_type,
				 struct expression *exp,
				 enum noside noside)
{
  value *arg = std::get<1> (m_storage)->evaluate (nullptr, exp, noside);
  return ada_val_atr (noside, std::get<0> (m_storage), arg);
}

value *
ada_unop_ind_operation::evaluate (struct type *expect_type,
				  struct expression *exp,
				  enum noside noside)
{
  value *arg1 = std::get<0> (m_storage)->evaluate (expect_type, exp, noside);

  struct type *type = ada_check_typedef (value_type (arg1));
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      if (ada_is_array_descriptor_type (type))
	/* GDB allows dereferencing GNAT array descriptors.  */
	{
	  struct type *arrType = ada_type_of_array (arg1, 0);

	  if (arrType == NULL)
	    error (_("Attempt to dereference null array pointer."));
	  return value_at_lazy (arrType, 0);
	}
      else if (type->code () == TYPE_CODE_PTR
	       || type->code () == TYPE_CODE_REF
	       /* In C you can dereference an array to get the 1st elt.  */
	       || type->code () == TYPE_CODE_ARRAY)
	{
	  /* As mentioned in the OP_VAR_VALUE case, tagged types can
	     only be determined by inspecting the object's tag.
	     This means that we need to evaluate completely the
	     expression in order to get its type.  */

	  if ((type->code () == TYPE_CODE_REF
	       || type->code () == TYPE_CODE_PTR)
	      && ada_is_tagged_type (TYPE_TARGET_TYPE (type), 0))
	    {
	      arg1 = std::get<0> (m_storage)->evaluate (nullptr, exp,
							EVAL_NORMAL);
	      type = value_type (ada_value_ind (arg1));
	    }
	  else
	    {
	      type = to_static_fixed_type
		(ada_aligned_type
		 (ada_check_typedef (TYPE_TARGET_TYPE (type))));
	    }
	  ada_ensure_varsize_limit (type);
	  return value_zero (type, lval_memory);
	}
      else if (type->code () == TYPE_CODE_INT)
	{
	  /* GDB allows dereferencing an int.  */
	  if (expect_type == NULL)
	    return value_zero (builtin_type (exp->gdbarch)->builtin_int,
			       lval_memory);
	  else
	    {
	      expect_type =
		to_static_fixed_type (ada_aligned_type (expect_type));
	      return value_zero (expect_type, lval_memory);
	    }
	}
      else
	error (_("Attempt to take contents of a non-pointer value."));
    }
  arg1 = ada_coerce_ref (arg1);     /* FIXME: What is this for??  */
  type = ada_check_typedef (value_type (arg1));

  if (type->code () == TYPE_CODE_INT)
    /* GDB allows dereferencing an int.  If we were given
       the expect_type, then use that as the target type.
       Otherwise, assume that the target type is an int.  */
    {
      if (expect_type != NULL)
	return ada_value_ind (value_cast (lookup_pointer_type (expect_type),
					  arg1));
      else
	return value_at_lazy (builtin_type (exp->gdbarch)->builtin_int,
			      (CORE_ADDR) value_as_address (arg1));
    }

  struct type *target_type = (to_static_fixed_type
			      (ada_aligned_type
			       (ada_check_typedef (TYPE_TARGET_TYPE (type)))));
  ada_ensure_varsize_limit (target_type);

  if (ada_is_array_descriptor_type (type))
    /* GDB allows dereferencing GNAT array descriptors.  */
    return ada_coerce_to_simple_array (arg1);
  else
    return ada_value_ind (arg1);
}

value *
ada_structop_operation::evaluate (struct type *expect_type,
				  struct expression *exp,
				  enum noside noside)
{
  value *arg1 = std::get<0> (m_storage)->evaluate (nullptr, exp, noside);
  const char *str = std::get<1> (m_storage).c_str ();
  if (noside == EVAL_AVOID_SIDE_EFFECTS)
    {
      struct type *type;
      struct type *type1 = value_type (arg1);

      if (ada_is_tagged_type (type1, 1))
	{
	  type = ada_lookup_struct_elt_type (type1, str, 1, 1);

	  /* If the field is not found, check if it exists in the
	     extension of this object's type. This means that we
	     need to evaluate completely the expression.  */

	  if (type == NULL)
	    {
	      arg1 = std::get<0> (m_storage)->evaluate (nullptr, exp,
							EVAL_NORMAL);
	      arg1 = ada_value_struct_elt (arg1, str, 0);
	      arg1 = unwrap_value (arg1);
	      type = value_type (ada_to_fixed_value (arg1));
	    }
	}
      else
	type = ada_lookup_struct_elt_type (type1, str, 1, 0);

      return value_zero (ada_aligned_type (type), lval_memory);
    }
  else
    {
      arg1 = ada_value_struct_elt (arg1, str, 0);
      arg1 = unwrap_value (arg1);
      return ada_to_fixed_value (arg1);
    }
}

value *
ada_funcall_operation::evaluate (struct type *expect_type,
				 struct expression *exp,
				 enum noside noside)
{
  const std::vector<operation_up> &args_up = std::get<1> (m_storage);
  int nargs = args_up.size ();
  std::vector<value *> argvec (nargs);
  operation_up &callee_op = std::get<0> (m_storage);

  ada_var_value_operation *avv
    = dynamic_cast<ada_var_value_operation *> (callee_op.get ());
  if (avv != nullptr
      && SYMBOL_DOMAIN (avv->get_symbol ()) == UNDEF_DOMAIN)
    error (_("Unexpected unresolved symbol, %s, during evaluation"),
	   avv->get_symbol ()->print_name ());

  value *callee = callee_op->evaluate (nullptr, exp, noside);
  for (int i = 0; i < args_up.size (); ++i)
    argvec[i] = args_up[i]->evaluate (nullptr, exp, noside);

  if (ada_is_constrained_packed_array_type
      (desc_base_type (value_type (callee))))
    callee = ada_coerce_to_simple_array (callee);
  else if (value_type (callee)->code () == TYPE_CODE_ARRAY
	   && TYPE_FIELD_BITSIZE (value_type (callee), 0) != 0)
    /* This is a packed array that has already been fixed, and
       therefore already coerced to a simple array.  Nothing further
       to do.  */
    ;
  else if (value_type (callee)->code () == TYPE_CODE_REF)
    {
      /* Make sure we dereference references so that all the code below
	 feels like it's really handling the referenced value.  Wrapping
	 types (for alignment) may be there, so make sure we strip them as
	 well.  */
      callee = ada_to_fixed_value (coerce_ref (callee));
    }
  else if (value_type (callee)->code () == TYPE_CODE_ARRAY
	   && VALUE_LVAL (callee) == lval_memory)
    callee = value_addr (callee);

  struct type *type = ada_check_typedef (value_type (callee));

  /* Ada allows us to implicitly dereference arrays when subscripting
     them.  So, if this is an array typedef (encoding use for array
     access types encoded as fat pointers), strip it now.  */
  if (type->code () == TYPE_CODE_TYPEDEF)
    type = ada_typedef_target_type (type);

  if (type->code () == TYPE_CODE_PTR)
    {
      switch (ada_check_typedef (TYPE_TARGET_TYPE (type))->code ())
	{
	case TYPE_CODE_FUNC:
	  type = ada_check_typedef (TYPE_TARGET_TYPE (type));
	  break;
	case TYPE_CODE_ARRAY:
	  break;
	case TYPE_CODE_STRUCT:
	  if (noside != EVAL_AVOID_SIDE_EFFECTS)
	    callee = ada_value_ind (callee);
	  type = ada_check_typedef (TYPE_TARGET_TYPE (type));
	  break;
	default:
	  error (_("cannot subscript or call something of type `%s'"),
		 ada_type_name (value_type (callee)));
	  break;
	}
    }

  switch (type->code ())
    {
    case TYPE_CODE_FUNC:
      if (noside == EVAL_AVOID_SIDE_EFFECTS)
	{
	  if (TYPE_TARGET_TYPE (type) == NULL)
	    error_call_unknown_return_type (NULL);
	  return allocate_value (TYPE_TARGET_TYPE (type));
	}
      return call_function_by_hand (callee, NULL, argvec);
    case TYPE_CODE_INTERNAL_FUNCTION:
      if (noside == EVAL_AVOID_SIDE_EFFECTS)
	/* We don't know anything about what the internal
	   function might return, but we have to return
	   something.  */
	return value_zero (builtin_type (exp->gdbarch)->builtin_int,
			   not_lval);
      else
	return call_internal_function (exp->gdbarch, exp->language_defn,
				       callee, nargs,
				       argvec.data ());

    case TYPE_CODE_STRUCT:
      {
	int arity;

	arity = ada_array_arity (type);
	type = ada_array_element_type (type, nargs);
	if (type == NULL)
	  error (_("cannot subscript or call a record"));
	if (arity != nargs)
	  error (_("wrong number of subscripts; expecting %d"), arity);
	if (noside == EVAL_AVOID_SIDE_EFFECTS)
	  return value_zero (ada_aligned_type (type), lval_memory);
	return
	  unwrap_value (ada_value_subscript
			(callee, nargs, argvec.data ()));
      }
    case TYPE_CODE_ARRAY:
      if (noside == EVAL_AVOID_SIDE_EFFECTS)
	{
	  type = ada_array_element_type (type, nargs);
	  if (type == NULL)
	    error (_("element type of array unknown"));
	  else
	    return value_zero (ada_aligned_type (type), lval_memory);
	}
      return
	unwrap_value (ada_value_subscript
		      (ada_coerce_to_simple_array (callee),
		       nargs, argvec.data ()));
    case TYPE_CODE_PTR:     /* Pointer to array */
      if (noside == EVAL_AVOID_SIDE_EFFECTS)
	{
	  type = to_fixed_array_type (TYPE_TARGET_TYPE (type), NULL, 1);
	  type = ada_array_element_type (type, nargs);
	  if (type == NULL)
	    error (_("element type of array unknown"));
	  else
	    return value_zero (ada_aligned_type (type), lval_memory);
	}
      return
	unwrap_value (ada_value_ptr_subscript (callee, nargs,
					       argvec.data ()));

    default:
      error (_("Attempt to index or call something other than an "
	       "array or function"));
    }
}

bool
ada_funcall_operation::resolve (struct expression *exp,
				bool deprocedure_p,
				bool parse_completion,
				innermost_block_tracker *tracker,
				struct type *context_type)
{
  operation_up &callee_op = std::get<0> (m_storage);

  ada_var_value_operation *avv
    = dynamic_cast<ada_var_value_operation *> (callee_op.get ());
  if (avv == nullptr)
    return false;

  symbol *sym = avv->get_symbol ();
  if (SYMBOL_DOMAIN (sym) != UNDEF_DOMAIN)
    return false;

  const std::vector<operation_up> &args_up = std::get<1> (m_storage);
  int nargs = args_up.size ();
  std::vector<value *> argvec (nargs);

  for (int i = 0; i < args_up.size (); ++i)
    argvec[i] = args_up[i]->evaluate (nullptr, exp, EVAL_AVOID_SIDE_EFFECTS);

  const block *block = avv->get_block ();
  block_symbol resolved
    = ada_resolve_funcall (sym, block,
			   context_type, parse_completion,
			   nargs, argvec.data (),
			   tracker);

  std::get<0> (m_storage)
    = make_operation<ada_var_value_operation> (resolved);
  return false;
}

bool
ada_ternop_slice_operation::resolve (struct expression *exp,
				     bool deprocedure_p,
				     bool parse_completion,
				     innermost_block_tracker *tracker,
				     struct type *context_type)
{
  /* Historically this check was done during resolution, so we
     continue that here.  */
  value *v = std::get<0> (m_storage)->evaluate (context_type, exp,
						EVAL_AVOID_SIDE_EFFECTS);
  if (ada_is_any_packed_array_type (value_type (v)))
    error (_("cannot slice a packed array"));
  return false;
}

}



/* Return non-zero iff TYPE represents a System.Address type.  */

int
ada_is_system_address_type (struct type *type)
{
  return (type->name () && strcmp (type->name (), "system__address") == 0);
}



				/* Range types */

/* Scan STR beginning at position K for a discriminant name, and
   return the value of that discriminant field of DVAL in *PX.  If
   PNEW_K is not null, put the position of the character beyond the
   name scanned in *PNEW_K.  Return 1 if successful; return 0 and do
   not alter *PX and *PNEW_K if unsuccessful.  */

static int
scan_discrim_bound (const char *str, int k, struct value *dval, LONGEST * px,
		    int *pnew_k)
{
  static std::string storage;
  const char *pstart, *pend, *bound;
  struct value *bound_val;

  if (dval == NULL || str == NULL || str[k] == '\0')
    return 0;

  pstart = str + k;
  pend = strstr (pstart, "__");
  if (pend == NULL)
    {
      bound = pstart;
      k += strlen (bound);
    }
  else
    {
      int len = pend - pstart;

      /* Strip __ and beyond.  */
      storage = std::string (pstart, len);
      bound = storage.c_str ();
      k = pend - str;
    }

  bound_val = ada_search_struct_field (bound, dval, 0, value_type (dval));
  if (bound_val == NULL)
    return 0;

  *px = value_as_long (bound_val);
  if (pnew_k != NULL)
    *pnew_k = k;
  return 1;
}

/* Value of variable named NAME.  Only exact matches are considered.
   If no such variable found, then if ERR_MSG is null, returns 0, and
   otherwise causes an error with message ERR_MSG.  */

static struct value *
get_var_value (const char *name, const char *err_msg)
{
  std::string quoted_name = add_angle_brackets (name);

  lookup_name_info lookup_name (quoted_name, symbol_name_match_type::FULL);

  std::vector<struct block_symbol> syms
    = ada_lookup_symbol_list_worker (lookup_name,
				     get_selected_block (0),
				     VAR_DOMAIN, 1);

  if (syms.size () != 1)
    {
      if (err_msg == NULL)
	return 0;
      else
	error (("%s"), err_msg);
    }

  return value_of_variable (syms[0].symbol, syms[0].block);
}

/* Value of integer variable named NAME in the current environment.
   If no such variable is found, returns false.  Otherwise, sets VALUE
   to the variable's value and returns true.  */

bool
get_int_var_value (const char *name, LONGEST &value)
{
  struct value *var_val = get_var_value (name, 0);

  if (var_val == 0)
    return false;

  value = value_as_long (var_val);
  return true;
}


/* Return a range type whose base type is that of the range type named
   NAME in the current environment, and whose bounds are calculated
   from NAME according to the GNAT range encoding conventions.
   Extract discriminant values, if needed, from DVAL.  ORIG_TYPE is the
   corresponding range type from debug information; fall back to using it
   if symbol lookup fails.  If a new type must be created, allocate it
   like ORIG_TYPE was.  The bounds information, in general, is encoded
   in NAME, the base type given in the named range type.  */

static struct type *
to_fixed_range_type (struct type *raw_type, struct value *dval)
{
  const char *name;
  struct type *base_type;
  const char *subtype_info;

  gdb_assert (raw_type != NULL);
  gdb_assert (raw_type->name () != NULL);

  if (raw_type->code () == TYPE_CODE_RANGE)
    base_type = TYPE_TARGET_TYPE (raw_type);
  else
    base_type = raw_type;

  name = raw_type->name ();
  subtype_info = strstr (name, "___XD");
  if (subtype_info == NULL)
    {
      LONGEST L = ada_discrete_type_low_bound (raw_type);
      LONGEST U = ada_discrete_type_high_bound (raw_type);

      if (L < INT_MIN || U > INT_MAX)
	return raw_type;
      else
	return create_static_range_type (alloc_type_copy (raw_type), raw_type,
					 L, U);
    }
  else
    {
      int prefix_len = subtype_info - name;
      LONGEST L, U;
      struct type *type;
      const char *bounds_str;
      int n;

      subtype_info += 5;
      bounds_str = strchr (subtype_info, '_');
      n = 1;

      if (*subtype_info == 'L')
	{
	  if (!ada_scan_number (bounds_str, n, &L, &n)
	      && !scan_discrim_bound (bounds_str, n, dval, &L, &n))
	    return raw_type;
	  if (bounds_str[n] == '_')
	    n += 2;
	  else if (bounds_str[n] == '.')     /* FIXME? SGI Workshop kludge.  */
	    n += 1;
	  subtype_info += 1;
	}
      else
	{
	  std::string name_buf = std::string (name, prefix_len) + "___L";
	  if (!get_int_var_value (name_buf.c_str (), L))
	    {
	      lim_warning (_("Unknown lower bound, using 1."));
	      L = 1;
	    }
	}

      if (*subtype_info == 'U')
	{
	  if (!ada_scan_number (bounds_str, n, &U, &n)
	      && !scan_discrim_bound (bounds_str, n, dval, &U, &n))
	    return raw_type;
	}
      else
	{
	  std::string name_buf = std::string (name, prefix_len) + "___U";
	  if (!get_int_var_value (name_buf.c_str (), U))
	    {
	      lim_warning (_("Unknown upper bound, using %ld."), (long) L);
	      U = L;
	    }
	}

      type = create_static_range_type (alloc_type_copy (raw_type),
				       base_type, L, U);
      /* create_static_range_type alters the resulting type's length
	 to match the size of the base_type, which is not what we want.
	 Set it back to the original range type's length.  */
      TYPE_LENGTH (type) = TYPE_LENGTH (raw_type);
      type->set_name (name);
      return type;
    }
}

/* True iff NAME is the name of a range type.  */

int
ada_is_range_type_name (const char *name)
{
  return (name != NULL && strstr (name, "___XD"));
}


				/* Modular types */

/* True iff TYPE is an Ada modular type.  */

int
ada_is_modular_type (struct type *type)
{
  struct type *subranged_type = get_base_type (type);

  return (subranged_type != NULL && type->code () == TYPE_CODE_RANGE
	  && subranged_type->code () == TYPE_CODE_INT
	  && subranged_type->is_unsigned ());
}

/* Assuming ada_is_modular_type (TYPE), the modulus of TYPE.  */

ULONGEST
ada_modulus (struct type *type)
{
  const dynamic_prop &high = type->bounds ()->high;

  if (high.kind () == PROP_CONST)
    return (ULONGEST) high.const_val () + 1;

  /* If TYPE is unresolved, the high bound might be a location list.  Return
     0, for lack of a better value to return.  */
  return 0;
}


/* Ada exception catchpoint support:
   ---------------------------------

   We support 3 kinds of exception catchpoints:
     . catchpoints on Ada exceptions
     . catchpoints on unhandled Ada exceptions
     . catchpoints on failed assertions

   Exceptions raised during failed assertions, or unhandled exceptions
   could perfectly be caught with the general catchpoint on Ada exceptions.
   However, we can easily differentiate these two special cases, and having
   the option to distinguish these two cases from the rest can be useful
   to zero-in on certain situations.

   Exception catchpoints are a specialized form of breakpoint,
   since they rely on inserting breakpoints inside known routines
   of the GNAT runtime.  The implementation therefore uses a standard
   breakpoint structure of the BP_BREAKPOINT type, but with its own set
   of breakpoint_ops.

   Support in the runtime for exception catchpoints have been changed
   a few times already, and these changes affect the implementation
   of these catchpoints.  In order to be able to support several
   variants of the runtime, we use a sniffer that will determine
   the runtime variant used by the program being debugged.  */

/* Ada's standard exceptions.

   The Ada 83 standard also defined Numeric_Error.  But there so many
   situations where it was unclear from the Ada 83 Reference Manual
   (RM) whether Constraint_Error or Numeric_Error should be raised,
   that the ARG (Ada Rapporteur Group) eventually issued a Binding
   Interpretation saying that anytime the RM says that Numeric_Error
   should be raised, the implementation may raise Constraint_Error.
   Ada 95 went one step further and pretty much removed Numeric_Error
   from the list of standard exceptions (it made it a renaming of
   Constraint_Error, to help preserve compatibility when compiling
   an Ada83 compiler). As such, we do not include Numeric_Error from
   this list of standard exceptions.  */

static const char * const standard_exc[] = {
  "constraint_error",
  "program_error",
  "storage_error",
  "tasking_error"
};

typedef CORE_ADDR (ada_unhandled_exception_name_addr_ftype) (void);

/* A structure that describes how to support exception catchpoints
   for a given executable.  */

struct exception_support_info
{
   /* The name of the symbol to break on in order to insert
      a catchpoint on exceptions.  */
   const char *catch_exception_sym;

   /* The name of the symbol to break on in order to insert
      a catchpoint on unhandled exceptions.  */
   const char *catch_exception_unhandled_sym;

   /* The name of the symbol to break on in order to insert
      a catchpoint on failed assertions.  */
   const char *catch_assert_sym;

   /* The name of the symbol to break on in order to insert
      a catchpoint on exception handling.  */
   const char *catch_handlers_sym;

   /* Assuming that the inferior just triggered an unhandled exception
      catchpoint, this function is responsible for returning the address
      in inferior memory where the name of that exception is stored.
      Return zero if the address could not be computed.  */
   ada_unhandled_exception_name_addr_ftype *unhandled_exception_name_addr;
};

static CORE_ADDR ada_unhandled_exception_name_addr (void);
static CORE_ADDR ada_unhandled_exception_name_addr_from_raise (void);

/* The following exception support info structure describes how to
   implement exception catchpoints with the latest version of the
   Ada runtime (as of 2019-08-??).  */

static const struct exception_support_info default_exception_support_info =
{
  "__gnat_debug_raise_exception", /* catch_exception_sym */
  "__gnat_unhandled_exception", /* catch_exception_unhandled_sym */
  "__gnat_debug_raise_assert_failure", /* catch_assert_sym */
  "__gnat_begin_handler_v1", /* catch_handlers_sym */
  ada_unhandled_exception_name_addr
};

/* The following exception support info structure describes how to
   implement exception catchpoints with an earlier version of the
   Ada runtime (as of 2007-03-06) using v0 of the EH ABI.  */

static const struct exception_support_info exception_support_info_v0 =
{
  "__gnat_debug_raise_exception", /* catch_exception_sym */
  "__gnat_unhandled_exception", /* catch_exception_unhandled_sym */
  "__gnat_debug_raise_assert_failure", /* catch_assert_sym */
  "__gnat_begin_handler", /* catch_handlers_sym */
  ada_unhandled_exception_name_addr
};

/* The following exception support info structure describes how to
   implement exception catchpoints with a slightly older version
   of the Ada runtime.  */

static const struct exception_support_info exception_support_info_fallback =
{
  "__gnat_raise_nodefer_with_msg", /* catch_exception_sym */
  "__gnat_unhandled_exception", /* catch_exception_unhandled_sym */
  "system__assertions__raise_assert_failure",  /* catch_assert_sym */
  "__gnat_begin_handler", /* catch_handlers_sym */
  ada_unhandled_exception_name_addr_from_raise
};

/* Return nonzero if we can detect the exception support routines
   described in EINFO.

   This function errors out if an abnormal situation is detected
   (for instance, if we find the exception support routines, but
   that support is found to be incomplete).  */

static int
ada_has_this_exception_support (const struct exception_support_info *einfo)
{
  struct symbol *sym;

  /* The symbol we're looking up is provided by a unit in the GNAT runtime
     that should be compiled with debugging information.  As a result, we
     expect to find that symbol in the symtabs.  */

  sym = standard_lookup (einfo->catch_exception_sym, NULL, VAR_DOMAIN);
  if (sym == NULL)
    {
      /* Perhaps we did not find our symbol because the Ada runtime was
	 compiled without debugging info, or simply stripped of it.
	 It happens on some GNU/Linux distributions for instance, where
	 users have to install a separate debug package in order to get
	 the runtime's debugging info.  In that situation, let the user
	 know why we cannot insert an Ada exception catchpoint.

	 Note: Just for the purpose of inserting our Ada exception
	 catchpoint, we could rely purely on the associated minimal symbol.
	 But we would be operating in degraded mode anyway, since we are
	 still lacking the debugging info needed later on to extract
	 the name of the exception being raised (this name is printed in
	 the catchpoint message, and is also used when trying to catch
	 a specific exception).  We do not handle this case for now.  */
      struct bound_minimal_symbol msym
	= lookup_minimal_symbol (einfo->catch_exception_sym, NULL, NULL);

      if (msym.minsym && MSYMBOL_TYPE (msym.minsym) != mst_solib_trampoline)
	error (_("Your Ada runtime appears to be missing some debugging "
		 "information.\nCannot insert Ada exception catchpoint "
		 "in this configuration."));

      return 0;
    }

  /* Make sure that the symbol we found corresponds to a function.  */

  if (SYMBOL_CLASS (sym) != LOC_BLOCK)
    {
      error (_("Symbol \"%s\" is not a function (class = %d)"),
	     sym->linkage_name (), SYMBOL_CLASS (sym));
      return 0;
    }

  sym = standard_lookup (einfo->catch_handlers_sym, NULL, VAR_DOMAIN);
  if (sym == NULL)
    {
      struct bound_minimal_symbol msym
	= lookup_minimal_symbol (einfo->catch_handlers_sym, NULL, NULL);

      if (msym.minsym && MSYMBOL_TYPE (msym.minsym) != mst_solib_trampoline)
	error (_("Your Ada runtime appears to be missing some debugging "
		 "information.\nCannot insert Ada exception catchpoint "
		 "in this configuration."));

      return 0;
    }

  /* Make sure that the symbol we found corresponds to a function.  */

  if (SYMBOL_CLASS (sym) != LOC_BLOCK)
    {
      error (_("Symbol \"%s\" is not a function (class = %d)"),
	     sym->linkage_name (), SYMBOL_CLASS (sym));
      return 0;
    }

  return 1;
}

/* Inspect the Ada runtime and determine which exception info structure
   should be used to provide support for exception catchpoints.

   This function will always set the per-inferior exception_info,
   or raise an error.  */

static void
ada_exception_support_info_sniffer (void)
{
  struct ada_inferior_data *data = get_ada_inferior_data (current_inferior ());

  /* If the exception info is already known, then no need to recompute it.  */
  if (data->exception_info != NULL)
    return;

  /* Check the latest (default) exception support info.  */
  if (ada_has_this_exception_support (&default_exception_support_info))
    {
      data->exception_info = &default_exception_support_info;
      return;
    }

  /* Try the v0 exception suport info.  */
  if (ada_has_this_exception_support (&exception_support_info_v0))
    {
      data->exception_info = &exception_support_info_v0;
      return;
    }

  /* Try our fallback exception suport info.  */
  if (ada_has_this_exception_support (&exception_support_info_fallback))
    {
      data->exception_info = &exception_support_info_fallback;
      return;
    }

  /* Sometimes, it is normal for us to not be able to find the routine
     we are looking for.  This happens when the program is linked with
     the shared version of the GNAT runtime, and the program has not been
     started yet.  Inform the user of these two possible causes if
     applicable.  */

  if (ada_update_initial_language (language_unknown) != language_ada)
    error (_("Unable to insert catchpoint.  Is this an Ada main program?"));

  /* If the symbol does not exist, then check that the program is
     already started, to make sure that shared libraries have been
     loaded.  If it is not started, this may mean that the symbol is
     in a shared library.  */

  if (inferior_ptid.pid () == 0)
    error (_("Unable to insert catchpoint. Try to start the program first."));

  /* At this point, we know that we are debugging an Ada program and
     that the inferior has been started, but we still are not able to
     find the run-time symbols.  That can mean that we are in
     configurable run time mode, or that a-except as been optimized
     out by the linker...  In any case, at this point it is not worth
     supporting this feature.  */

  error (_("Cannot insert Ada exception catchpoints in this configuration."));
}

/* True iff FRAME is very likely to be that of a function that is
   part of the runtime system.  This is all very heuristic, but is
   intended to be used as advice as to what frames are uninteresting
   to most users.  */

static int
is_known_support_routine (struct frame_info *frame)
{
  enum language func_lang;
  int i;
  const char *fullname;

  /* If this code does not have any debugging information (no symtab),
     This cannot be any user code.  */

  symtab_and_line sal = find_frame_sal (frame);
  if (sal.symtab == NULL)
    return 1;

  /* If there is a symtab, but the associated source file cannot be
     located, then assume this is not user code:  Selecting a frame
     for which we cannot display the code would not be very helpful
     for the user.  This should also take care of case such as VxWorks
     where the kernel has some debugging info provided for a few units.  */

  fullname = symtab_to_fullname (sal.symtab);
  if (access (fullname, R_OK) != 0)
    return 1;

  /* Check the unit filename against the Ada runtime file naming.
     We also check the name of the objfile against the name of some
     known system libraries that sometimes come with debugging info
     too.  */

  for (i = 0; known_runtime_file_name_patterns[i] != NULL; i += 1)
    {
      re_comp (known_runtime_file_name_patterns[i]);
      if (re_exec (lbasename (sal.symtab->filename)))
	return 1;
      if (SYMTAB_OBJFILE (sal.symtab) != NULL
	  && re_exec (objfile_name (SYMTAB_OBJFILE (sal.symtab))))
	return 1;
    }

  /* Check whether the function is a GNAT-generated entity.  */

  gdb::unique_xmalloc_ptr<char> func_name
    = find_frame_funname (frame, &func_lang, NULL);
  if (func_name == NULL)
    return 1;

  for (i = 0; known_auxiliary_function_name_patterns[i] != NULL; i += 1)
    {
      re_comp (known_auxiliary_function_name_patterns[i]);
      if (re_exec (func_name.get ()))
	return 1;
    }

  return 0;
}

/* Find the first frame that contains debugging information and that is not
   part of the Ada run-time, starting from FI and moving upward.  */

void
ada_find_printable_frame (struct frame_info *fi)
{
  for (; fi != NULL; fi = get_prev_frame (fi))
    {
      if (!is_known_support_routine (fi))
	{
	  select_frame (fi);
	  break;
	}
    }

}

/* Assuming that the inferior just triggered an unhandled exception
   catchpoint, return the address in inferior memory where the name
   of the exception is stored.
   
   Return zero if the address could not be computed.  */

static CORE_ADDR
ada_unhandled_exception_name_addr (void)
{
  return parse_and_eval_address ("e.full_name");
}

/* Same as ada_unhandled_exception_name_addr, except that this function
   should be used when the inferior uses an older version of the runtime,
   where the exception name needs to be extracted from a specific frame
   several frames up in the callstack.  */

static CORE_ADDR
ada_unhandled_exception_name_addr_from_raise (void)
{
  int frame_level;
  struct frame_info *fi;
  struct ada_inferior_data *data = get_ada_inferior_data (current_inferior ());

  /* To determine the name of this exception, we need to select
     the frame corresponding to RAISE_SYM_NAME.  This frame is
     at least 3 levels up, so we simply skip the first 3 frames
     without checking the name of their associated function.  */
  fi = get_current_frame ();
  for (frame_level = 0; frame_level < 3; frame_level += 1)
    if (fi != NULL)
      fi = get_prev_frame (fi); 

  while (fi != NULL)
    {
      enum language func_lang;

      gdb::unique_xmalloc_ptr<char> func_name
	= find_frame_funname (fi, &func_lang, NULL);
      if (func_name != NULL)
	{
	  if (strcmp (func_name.get (),
		      data->exception_info->catch_exception_sym) == 0)
	    break; /* We found the frame we were looking for...  */
	}
      fi = get_prev_frame (fi);
    }

  if (fi == NULL)
    return 0;

  select_frame (fi);
  return parse_and_eval_address ("id.full_name");
}

/* Assuming the inferior just triggered an Ada exception catchpoint
   (of any type), return the address in inferior memory where the name
   of the exception is stored, if applicable.

   Assumes the selected frame is the current frame.

   Return zero if the address could not be computed, or if not relevant.  */

static CORE_ADDR
ada_exception_name_addr_1 (enum ada_exception_catchpoint_kind ex,
			   struct breakpoint *b)
{
  struct ada_inferior_data *data = get_ada_inferior_data (current_inferior ());

  switch (ex)
    {
      case ada_catch_exception:
	return (parse_and_eval_address ("e.full_name"));
	break;

      case ada_catch_exception_unhandled:
	return data->exception_info->unhandled_exception_name_addr ();
	break;

      case ada_catch_handlers:
	return 0;  /* The runtimes does not provide access to the exception
		      name.  */
	break;

      case ada_catch_assert:
	return 0;  /* Exception name is not relevant in this case.  */
	break;

      default:
	internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
	break;
    }

  return 0; /* Should never be reached.  */
}

/* Assuming the inferior is stopped at an exception catchpoint,
   return the message which was associated to the exception, if
   available.  Return NULL if the message could not be retrieved.

   Note: The exception message can be associated to an exception
   either through the use of the Raise_Exception function, or
   more simply (Ada 2005 and later), via:

       raise Exception_Name with "exception message";

   */

static gdb::unique_xmalloc_ptr<char>
ada_exception_message_1 (void)
{
  struct value *e_msg_val;
  int e_msg_len;

  /* For runtimes that support this feature, the exception message
     is passed as an unbounded string argument called "message".  */
  e_msg_val = parse_and_eval ("message");
  if (e_msg_val == NULL)
    return NULL; /* Exception message not supported.  */

  e_msg_val = ada_coerce_to_simple_array (e_msg_val);
  gdb_assert (e_msg_val != NULL);
  e_msg_len = TYPE_LENGTH (value_type (e_msg_val));

  /* If the message string is empty, then treat it as if there was
     no exception message.  */
  if (e_msg_len <= 0)
    return NULL;

  gdb::unique_xmalloc_ptr<char> e_msg ((char *) xmalloc (e_msg_len + 1));
  read_memory (value_address (e_msg_val), (gdb_byte *) e_msg.get (),
	       e_msg_len);
  e_msg.get ()[e_msg_len] = '\0';

  return e_msg;
}

/* Same as ada_exception_message_1, except that all exceptions are
   contained here (returning NULL instead).  */

static gdb::unique_xmalloc_ptr<char>
ada_exception_message (void)
{
  gdb::unique_xmalloc_ptr<char> e_msg;

  try
    {
      e_msg = ada_exception_message_1 ();
    }
  catch (const gdb_exception_error &e)
    {
      e_msg.reset (nullptr);
    }

  return e_msg;
}

/* Same as ada_exception_name_addr_1, except that it intercepts and contains
   any error that ada_exception_name_addr_1 might cause to be thrown.
   When an error is intercepted, a warning with the error message is printed,
   and zero is returned.  */

static CORE_ADDR
ada_exception_name_addr (enum ada_exception_catchpoint_kind ex,
			 struct breakpoint *b)
{
  CORE_ADDR result = 0;

  try
    {
      result = ada_exception_name_addr_1 (ex, b);
    }

  catch (const gdb_exception_error &e)
    {
      warning (_("failed to get exception name: %s"), e.what ());
      return 0;
    }

  return result;
}

static std::string ada_exception_catchpoint_cond_string
  (const char *excep_string,
   enum ada_exception_catchpoint_kind ex);

/* Ada catchpoints.

   In the case of catchpoints on Ada exceptions, the catchpoint will
   stop the target on every exception the program throws.  When a user
   specifies the name of a specific exception, we translate this
   request into a condition expression (in text form), and then parse
   it into an expression stored in each of the catchpoint's locations.
   We then use this condition to check whether the exception that was
   raised is the one the user is interested in.  If not, then the
   target is resumed again.  We store the name of the requested
   exception, in order to be able to re-set the condition expression
   when symbols change.  */

/* An instance of this type is used to represent an Ada catchpoint
   breakpoint location.  */

class ada_catchpoint_location : public bp_location
{
public:
  ada_catchpoint_location (breakpoint *owner)
    : bp_location (owner, bp_loc_software_breakpoint)
  {}

  /* The condition that checks whether the exception that was raised
     is the specific exception the user specified on catchpoint
     creation.  */
  expression_up excep_cond_expr;
};

/* An instance of this type is used to represent an Ada catchpoint.  */

struct ada_catchpoint : public breakpoint
{
  explicit ada_catchpoint (enum ada_exception_catchpoint_kind kind)
    : m_kind (kind)
  {
  }

  /* The name of the specific exception the user specified.  */
  std::string excep_string;

  /* What kind of catchpoint this is.  */
  enum ada_exception_catchpoint_kind m_kind;
};

/* Parse the exception condition string in the context of each of the
   catchpoint's locations, and store them for later evaluation.  */

static void
create_excep_cond_exprs (struct ada_catchpoint *c,
			 enum ada_exception_catchpoint_kind ex)
{
  /* Nothing to do if there's no specific exception to catch.  */
  if (c->excep_string.empty ())
    return;

  /* Same if there are no locations... */
  if (c->loc == NULL)
    return;

  /* Compute the condition expression in text form, from the specific
     expection we want to catch.  */
  std::string cond_string
    = ada_exception_catchpoint_cond_string (c->excep_string.c_str (), ex);

  /* Iterate over all the catchpoint's locations, and parse an
     expression for each.  */
  for (bp_location *bl : c->locations ())
    {
      struct ada_catchpoint_location *ada_loc
	= (struct ada_catchpoint_location *) bl;
      expression_up exp;

      if (!bl->shlib_disabled)
	{
	  const char *s;

	  s = cond_string.c_str ();
	  try
	    {
	      exp = parse_exp_1 (&s, bl->address,
				 block_for_pc (bl->address),
				 0);
	    }
	  catch (const gdb_exception_error &e)
	    {
	      warning (_("failed to reevaluate internal exception condition "
			 "for catchpoint %d: %s"),
		       c->number, e.what ());
	    }
	}

      ada_loc->excep_cond_expr = std::move (exp);
    }
}

/* Implement the ALLOCATE_LOCATION method in the breakpoint_ops
   structure for all exception catchpoint kinds.  */

static struct bp_location *
allocate_location_exception (struct breakpoint *self)
{
  return new ada_catchpoint_location (self);
}

/* Implement the RE_SET method in the breakpoint_ops structure for all
   exception catchpoint kinds.  */

static void
re_set_exception (struct breakpoint *b)
{
  struct ada_catchpoint *c = (struct ada_catchpoint *) b;

  /* Call the base class's method.  This updates the catchpoint's
     locations.  */
  bkpt_breakpoint_ops.re_set (b);

  /* Reparse the exception conditional expressions.  One for each
     location.  */
  create_excep_cond_exprs (c, c->m_kind);
}

/* Returns true if we should stop for this breakpoint hit.  If the
   user specified a specific exception, we only want to cause a stop
   if the program thrown that exception.  */

static int
should_stop_exception (const struct bp_location *bl)
{
  struct ada_catchpoint *c = (struct ada_catchpoint *) bl->owner;
  const struct ada_catchpoint_location *ada_loc
    = (const struct ada_catchpoint_location *) bl;
  int stop;

  struct internalvar *var = lookup_internalvar ("_ada_exception");
  if (c->m_kind == ada_catch_assert)
    clear_internalvar (var);
  else
    {
      try
	{
	  const char *expr;

	  if (c->m_kind == ada_catch_handlers)
	    expr = ("GNAT_GCC_exception_Access(gcc_exception)"
		    ".all.occurrence.id");
	  else
	    expr = "e";

	  struct value *exc = parse_and_eval (expr);
	  set_internalvar (var, exc);
	}
      catch (const gdb_exception_error &ex)
	{
	  clear_internalvar (var);
	}
    }

  /* With no specific exception, should always stop.  */
  if (c->excep_string.empty ())
    return 1;

  if (ada_loc->excep_cond_expr == NULL)
    {
      /* We will have a NULL expression if back when we were creating
	 the expressions, this location's had failed to parse.  */
      return 1;
    }

  stop = 1;
  try
    {
      struct value *mark;

      mark = value_mark ();
      stop = value_true (evaluate_expression (ada_loc->excep_cond_expr.get ()));
      value_free_to_mark (mark);
    }
  catch (const gdb_exception &ex)
    {
      exception_fprintf (gdb_stderr, ex,
			 _("Error in testing exception condition:\n"));
    }

  return stop;
}

/* Implement the CHECK_STATUS method in the breakpoint_ops structure
   for all exception catchpoint kinds.  */

static void
check_status_exception (bpstat bs)
{
  bs->stop = should_stop_exception (bs->bp_location_at.get ());
}

/* Implement the PRINT_IT method in the breakpoint_ops structure
   for all exception catchpoint kinds.  */

static enum print_stop_action
print_it_exception (bpstat bs)
{
  struct ui_out *uiout = current_uiout;
  struct breakpoint *b = bs->breakpoint_at;

  annotate_catchpoint (b->number);

  if (uiout->is_mi_like_p ())
    {
      uiout->field_string ("reason",
			   async_reason_lookup (EXEC_ASYNC_BREAKPOINT_HIT));
      uiout->field_string ("disp", bpdisp_text (b->disposition));
    }

  uiout->text (b->disposition == disp_del
	       ? "\nTemporary catchpoint " : "\nCatchpoint ");
  uiout->field_signed ("bkptno", b->number);
  uiout->text (", ");

  /* ada_exception_name_addr relies on the selected frame being the
     current frame.  Need to do this here because this function may be
     called more than once when printing a stop, and below, we'll
     select the first frame past the Ada run-time (see
     ada_find_printable_frame).  */
  select_frame (get_current_frame ());

  struct ada_catchpoint *c = (struct ada_catchpoint *) b;
  switch (c->m_kind)
    {
      case ada_catch_exception:
      case ada_catch_exception_unhandled:
      case ada_catch_handlers:
	{
	  const CORE_ADDR addr = ada_exception_name_addr (c->m_kind, b);
	  char exception_name[256];

	  if (addr != 0)
	    {
	      read_memory (addr, (gdb_byte *) exception_name,
			   sizeof (exception_name) - 1);
	      exception_name [sizeof (exception_name) - 1] = '\0';
	    }
	  else
	    {
	      /* For some reason, we were unable to read the exception
		 name.  This could happen if the Runtime was compiled
		 without debugging info, for instance.  In that case,
		 just replace the exception name by the generic string
		 "exception" - it will read as "an exception" in the
		 notification we are about to print.  */
	      memcpy (exception_name, "exception", sizeof ("exception"));
	    }
	  /* In the case of unhandled exception breakpoints, we print
	     the exception name as "unhandled EXCEPTION_NAME", to make
	     it clearer to the user which kind of catchpoint just got
	     hit.  We used ui_out_text to make sure that this extra
	     info does not pollute the exception name in the MI case.  */
	  if (c->m_kind == ada_catch_exception_unhandled)
	    uiout->text ("unhandled ");
	  uiout->field_string ("exception-name", exception_name);
	}
	break;
      case ada_catch_assert:
	/* In this case, the name of the exception is not really
	   important.  Just print "failed assertion" to make it clearer
	   that his program just hit an assertion-failure catchpoint.
	   We used ui_out_text because this info does not belong in
	   the MI output.  */
	uiout->text ("failed assertion");
	break;
    }

  gdb::unique_xmalloc_ptr<char> exception_message = ada_exception_message ();
  if (exception_message != NULL)
    {
      uiout->text (" (");
      uiout->field_string ("exception-message", exception_message.get ());
      uiout->text (")");
    }

  uiout->text (" at ");
  ada_find_printable_frame (get_current_frame ());

  return PRINT_SRC_AND_LOC;
}

/* Implement the PRINT_ONE method in the breakpoint_ops structure
   for all exception catchpoint kinds.  */

static void
print_one_exception (struct breakpoint *b, struct bp_location **last_loc)
{ 
  struct ui_out *uiout = current_uiout;
  struct ada_catchpoint *c = (struct ada_catchpoint *) b;
  struct value_print_options opts;

  get_user_print_options (&opts);

  if (opts.addressprint)
    uiout->field_skip ("addr");

  annotate_field (5);
  switch (c->m_kind)
    {
      case ada_catch_exception:
	if (!c->excep_string.empty ())
	  {
	    std::string msg = string_printf (_("`%s' Ada exception"),
					     c->excep_string.c_str ());

	    uiout->field_string ("what", msg);
	  }
	else
	  uiout->field_string ("what", "all Ada exceptions");
	
	break;

      case ada_catch_exception_unhandled:
	uiout->field_string ("what", "unhandled Ada exceptions");
	break;
      
      case ada_catch_handlers:
	if (!c->excep_string.empty ())
	  {
	    uiout->field_fmt ("what",
			      _("`%s' Ada exception handlers"),
			      c->excep_string.c_str ());
	  }
	else
	  uiout->field_string ("what", "all Ada exceptions handlers");
	break;

      case ada_catch_assert:
	uiout->field_string ("what", "failed Ada assertions");
	break;

      default:
	internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
	break;
    }
}

/* Implement the PRINT_MENTION method in the breakpoint_ops structure
   for all exception catchpoint kinds.  */

static void
print_mention_exception (struct breakpoint *b)
{
  struct ada_catchpoint *c = (struct ada_catchpoint *) b;
  struct ui_out *uiout = current_uiout;

  uiout->text (b->disposition == disp_del ? _("Temporary catchpoint ")
						 : _("Catchpoint "));
  uiout->field_signed ("bkptno", b->number);
  uiout->text (": ");

  switch (c->m_kind)
    {
      case ada_catch_exception:
	if (!c->excep_string.empty ())
	  {
	    std::string info = string_printf (_("`%s' Ada exception"),
					      c->excep_string.c_str ());
	    uiout->text (info);
	  }
	else
	  uiout->text (_("all Ada exceptions"));
	break;

      case ada_catch_exception_unhandled:
	uiout->text (_("unhandled Ada exceptions"));
	break;

      case ada_catch_handlers:
	if (!c->excep_string.empty ())
	  {
	    std::string info
	      = string_printf (_("`%s' Ada exception handlers"),
			       c->excep_string.c_str ());
	    uiout->text (info);
	  }
	else
	  uiout->text (_("all Ada exceptions handlers"));
	break;

      case ada_catch_assert:
	uiout->text (_("failed Ada assertions"));
	break;

      default:
	internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
	break;
    }
}

/* Implement the PRINT_RECREATE method in the breakpoint_ops structure
   for all exception catchpoint kinds.  */

static void
print_recreate_exception (struct breakpoint *b, struct ui_file *fp)
{
  struct ada_catchpoint *c = (struct ada_catchpoint *) b;

  switch (c->m_kind)
    {
      case ada_catch_exception:
	fprintf_filtered (fp, "catch exception");
	if (!c->excep_string.empty ())
	  fprintf_filtered (fp, " %s", c->excep_string.c_str ());
	break;

      case ada_catch_exception_unhandled:
	fprintf_filtered (fp, "catch exception unhandled");
	break;

      case ada_catch_handlers:
	fprintf_filtered (fp, "catch handlers");
	break;

      case ada_catch_assert:
	fprintf_filtered (fp, "catch assert");
	break;

      default:
	internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
    }
  print_recreate_thread (b, fp);
}

/* Virtual tables for various breakpoint types.  */
static struct breakpoint_ops catch_exception_breakpoint_ops;
static struct breakpoint_ops catch_exception_unhandled_breakpoint_ops;
static struct breakpoint_ops catch_assert_breakpoint_ops;
static struct breakpoint_ops catch_handlers_breakpoint_ops;

/* See ada-lang.h.  */

bool
is_ada_exception_catchpoint (breakpoint *bp)
{
  return (bp->ops == &catch_exception_breakpoint_ops
	  || bp->ops == &catch_exception_unhandled_breakpoint_ops
	  || bp->ops == &catch_assert_breakpoint_ops
	  || bp->ops == &catch_handlers_breakpoint_ops);
}

/* Split the arguments specified in a "catch exception" command.  
   Set EX to the appropriate catchpoint type.
   Set EXCEP_STRING to the name of the specific exception if
   specified by the user.
   IS_CATCH_HANDLERS_CMD: True if the arguments are for a
   "catch handlers" command.  False otherwise.
   If a condition is found at the end of the arguments, the condition
   expression is stored in COND_STRING (memory must be deallocated
   after use).  Otherwise COND_STRING is set to NULL.  */

static void
catch_ada_exception_command_split (const char *args,
				   bool is_catch_handlers_cmd,
				   enum ada_exception_catchpoint_kind *ex,
				   std::string *excep_string,
				   std::string *cond_string)
{
  std::string exception_name;

  exception_name = extract_arg (&args);
  if (exception_name == "if")
    {
      /* This is not an exception name; this is the start of a condition
	 expression for a catchpoint on all exceptions.  So, "un-get"
	 this token, and set exception_name to NULL.  */
      exception_name.clear ();
      args -= 2;
    }

  /* Check to see if we have a condition.  */

  args = skip_spaces (args);
  if (startswith (args, "if")
      && (isspace (args[2]) || args[2] == '\0'))
    {
      args += 2;
      args = skip_spaces (args);

      if (args[0] == '\0')
	error (_("Condition missing after `if' keyword"));
      *cond_string = args;

      args += strlen (args);
    }

  /* Check that we do not have any more arguments.  Anything else
     is unexpected.  */

  if (args[0] != '\0')
    error (_("Junk at end of expression"));

  if (is_catch_handlers_cmd)
    {
      /* Catch handling of exceptions.  */
      *ex = ada_catch_handlers;
      *excep_string = exception_name;
    }
  else if (exception_name.empty ())
    {
      /* Catch all exceptions.  */
      *ex = ada_catch_exception;
      excep_string->clear ();
    }
  else if (exception_name == "unhandled")
    {
      /* Catch unhandled exceptions.  */
      *ex = ada_catch_exception_unhandled;
      excep_string->clear ();
    }
  else
    {
      /* Catch a specific exception.  */
      *ex = ada_catch_exception;
      *excep_string = exception_name;
    }
}

/* Return the name of the symbol on which we should break in order to
   implement a catchpoint of the EX kind.  */

static const char *
ada_exception_sym_name (enum ada_exception_catchpoint_kind ex)
{
  struct ada_inferior_data *data = get_ada_inferior_data (current_inferior ());

  gdb_assert (data->exception_info != NULL);

  switch (ex)
    {
      case ada_catch_exception:
	return (data->exception_info->catch_exception_sym);
	break;
      case ada_catch_exception_unhandled:
	return (data->exception_info->catch_exception_unhandled_sym);
	break;
      case ada_catch_assert:
	return (data->exception_info->catch_assert_sym);
	break;
      case ada_catch_handlers:
	return (data->exception_info->catch_handlers_sym);
	break;
      default:
	internal_error (__FILE__, __LINE__,
			_("unexpected catchpoint kind (%d)"), ex);
    }
}

/* Return the breakpoint ops "virtual table" used for catchpoints
   of the EX kind.  */

static const struct breakpoint_ops *
ada_exception_breakpoint_ops (enum ada_exception_catchpoint_kind ex)
{
  switch (ex)
    {
      case ada_catch_exception:
	return (&catch_exception_breakpoint_ops);
	break;
      case ada_catch_exception_unhandled:
	return (&catch_exception_unhandled_breakpoint_ops);
	break;
      case ada_catch_assert:
	return (&catch_assert_breakpoint_ops);
	break;
      case ada_catch_handlers:
	return (&catch_handlers_breakpoint_ops);
	break;
      default:
	internal_error (__FILE__, __LINE__,
			_("unexpected catchpoint kind (%d)"), ex);
    }
}

/* Return the condition that will be used to match the current exception
   being raised with the exception that the user wants to catch.  This
   assumes that this condition is used when the inferior just triggered
   an exception catchpoint.
   EX: the type of catchpoints used for catching Ada exceptions.  */

static std::string
ada_exception_catchpoint_cond_string (const char *excep_string,
				      enum ada_exception_catchpoint_kind ex)
{
  int i;
  bool is_standard_exc = false;
  std::string result;

  if (ex == ada_catch_handlers)
    {
      /* For exception handlers catchpoints, the condition string does
	 not use the same parameter as for the other exceptions.  */
      result = ("long_integer (GNAT_GCC_exception_Access"
		"(gcc_exception).all.occurrence.id)");
    }
  else
    result = "long_integer (e)";

  /* The standard exceptions are a special case.  They are defined in
     runtime units that have been compiled without debugging info; if
     EXCEP_STRING is the not-fully-qualified name of a standard
     exception (e.g. "constraint_error") then, during the evaluation
     of the condition expression, the symbol lookup on this name would
     *not* return this standard exception.  The catchpoint condition
     may then be set only on user-defined exceptions which have the
     same not-fully-qualified name (e.g. my_package.constraint_error).

     To avoid this unexcepted behavior, these standard exceptions are
     systematically prefixed by "standard".  This means that "catch
     exception constraint_error" is rewritten into "catch exception
     standard.constraint_error".

     If an exception named constraint_error is defined in another package of
     the inferior program, then the only way to specify this exception as a
     breakpoint condition is to use its fully-qualified named:
     e.g. my_package.constraint_error.  */

  for (i = 0; i < sizeof (standard_exc) / sizeof (char *); i++)
    {
      if (strcmp (standard_exc [i], excep_string) == 0)
	{
	  is_standard_exc = true;
	  break;
	}
    }

  result += " = ";

  if (is_standard_exc)
    string_appendf (result, "long_integer (&standard.%s)", excep_string);
  else
    string_appendf (result, "long_integer (&%s)", excep_string);

  return result;
}

/* Return the symtab_and_line that should be used to insert an exception
   catchpoint of the TYPE kind.

   ADDR_STRING returns the name of the function where the real
   breakpoint that implements the catchpoints is set, depending on the
   type of catchpoint we need to create.  */

static struct symtab_and_line
ada_exception_sal (enum ada_exception_catchpoint_kind ex,
		   std::string *addr_string, const struct breakpoint_ops **ops)
{
  const char *sym_name;
  struct symbol *sym;

  /* First, find out which exception support info to use.  */
  ada_exception_support_info_sniffer ();

  /* Then lookup the function on which we will break in order to catch
     the Ada exceptions requested by the user.  */
  sym_name = ada_exception_sym_name (ex);
  sym = standard_lookup (sym_name, NULL, VAR_DOMAIN);

  if (sym == NULL)
    error (_("Catchpoint symbol not found: %s"), sym_name);

  if (SYMBOL_CLASS (sym) != LOC_BLOCK)
    error (_("Unable to insert catchpoint. %s is not a function."), sym_name);

  /* Set ADDR_STRING.  */
  *addr_string = sym_name;

  /* Set OPS.  */
  *ops = ada_exception_breakpoint_ops (ex);

  return find_function_start_sal (sym, 1);
}

/* Create an Ada exception catchpoint.

   EX_KIND is the kind of exception catchpoint to be created.

   If EXCEPT_STRING is empty, this catchpoint is expected to trigger
   for all exceptions.  Otherwise, EXCEPT_STRING indicates the name
   of the exception to which this catchpoint applies.

   COND_STRING, if not empty, is the catchpoint condition.

   TEMPFLAG, if nonzero, means that the underlying breakpoint
   should be temporary.

   FROM_TTY is the usual argument passed to all commands implementations.  */

void
create_ada_exception_catchpoint (struct gdbarch *gdbarch,
				 enum ada_exception_catchpoint_kind ex_kind,
				 const std::string &excep_string,
				 const std::string &cond_string,
				 int tempflag,
				 int disabled,
				 int from_tty)
{
  std::string addr_string;
  const struct breakpoint_ops *ops = NULL;
  struct symtab_and_line sal = ada_exception_sal (ex_kind, &addr_string, &ops);

  std::unique_ptr<ada_catchpoint> c (new ada_catchpoint (ex_kind));
  init_ada_exception_breakpoint (c.get (), gdbarch, sal, addr_string.c_str (),
				 ops, tempflag, disabled, from_tty);
  c->excep_string = excep_string;
  create_excep_cond_exprs (c.get (), ex_kind);
  if (!cond_string.empty ())
    set_breakpoint_condition (c.get (), cond_string.c_str (), from_tty, false);
  install_breakpoint (0, std::move (c), 1);
}

/* Implement the "catch exception" command.  */

static void
catch_ada_exception_command (const char *arg_entry, int from_tty,
			     struct cmd_list_element *command)
{
  const char *arg = arg_entry;
  struct gdbarch *gdbarch = get_current_arch ();
  int tempflag;
  enum ada_exception_catchpoint_kind ex_kind;
  std::string excep_string;
  std::string cond_string;

  tempflag = command->context () == CATCH_TEMPORARY;

  if (!arg)
    arg = "";
  catch_ada_exception_command_split (arg, false, &ex_kind, &excep_string,
				     &cond_string);
  create_ada_exception_catchpoint (gdbarch, ex_kind,
				   excep_string, cond_string,
				   tempflag, 1 /* enabled */,
				   from_tty);
}

/* Implement the "catch handlers" command.  */

static void
catch_ada_handlers_command (const char *arg_entry, int from_tty,
			    struct cmd_list_element *command)
{
  const char *arg = arg_entry;
  struct gdbarch *gdbarch = get_current_arch ();
  int tempflag;
  enum ada_exception_catchpoint_kind ex_kind;
  std::string excep_string;
  std::string cond_string;

  tempflag = command->context () == CATCH_TEMPORARY;

  if (!arg)
    arg = "";
  catch_ada_exception_command_split (arg, true, &ex_kind, &excep_string,
				     &cond_string);
  create_ada_exception_catchpoint (gdbarch, ex_kind,
				   excep_string, cond_string,
				   tempflag, 1 /* enabled */,
				   from_tty);
}

/* Completion function for the Ada "catch" commands.  */

static void
catch_ada_completer (struct cmd_list_element *cmd, completion_tracker &tracker,
		     const char *text, const char *word)
{
  std::vector<ada_exc_info> exceptions = ada_exceptions_list (NULL);

  for (const ada_exc_info &info : exceptions)
    {
      if (startswith (info.name, word))
	tracker.add_completion (make_unique_xstrdup (info.name));
    }
}

/* Split the arguments specified in a "catch assert" command.

   ARGS contains the command's arguments (or the empty string if
   no arguments were passed).

   If ARGS contains a condition, set COND_STRING to that condition
   (the memory needs to be deallocated after use).  */

static void
catch_ada_assert_command_split (const char *args, std::string &cond_string)
{
  args = skip_spaces (args);

  /* Check whether a condition was provided.  */
  if (startswith (args, "if")
      && (isspace (args[2]) || args[2] == '\0'))
    {
      args += 2;
      args = skip_spaces (args);
      if (args[0] == '\0')
	error (_("condition missing after `if' keyword"));
      cond_string.assign (args);
    }

  /* Otherwise, there should be no other argument at the end of
     the command.  */
  else if (args[0] != '\0')
    error (_("Junk at end of arguments."));
}

/* Implement the "catch assert" command.  */

static void
catch_assert_command (const char *arg_entry, int from_tty,
		      struct cmd_list_element *command)
{
  const char *arg = arg_entry;
  struct gdbarch *gdbarch = get_current_arch ();
  int tempflag;
  std::string cond_string;

  tempflag = command->context () == CATCH_TEMPORARY;

  if (!arg)
    arg = "";
  catch_ada_assert_command_split (arg, cond_string);
  create_ada_exception_catchpoint (gdbarch, ada_catch_assert,
				   "", cond_string,
				   tempflag, 1 /* enabled */,
				   from_tty);
}

/* Return non-zero if the symbol SYM is an Ada exception object.  */

static int
ada_is_exception_sym (struct symbol *sym)
{
  const char *type_name = SYMBOL_TYPE (sym)->name ();

  return (SYMBOL_CLASS (sym) != LOC_TYPEDEF
	  && SYMBOL_CLASS (sym) != LOC_BLOCK
	  && SYMBOL_CLASS (sym) != LOC_CONST
	  && SYMBOL_CLASS (sym) != LOC_UNRESOLVED
	  && type_name != NULL && strcmp (type_name, "exception") == 0);
}

/* Given a global symbol SYM, return non-zero iff SYM is a non-standard
   Ada exception object.  This matches all exceptions except the ones
   defined by the Ada language.  */

static int
ada_is_non_standard_exception_sym (struct symbol *sym)
{
  int i;

  if (!ada_is_exception_sym (sym))
    return 0;

  for (i = 0; i < ARRAY_SIZE (standard_exc); i++)
    if (strcmp (sym->linkage_name (), standard_exc[i]) == 0)
      return 0;  /* A standard exception.  */

  /* Numeric_Error is also a standard exception, so exclude it.
     See the STANDARD_EXC description for more details as to why
     this exception is not listed in that array.  */
  if (strcmp (sym->linkage_name (), "numeric_error") == 0)
    return 0;

  return 1;
}

/* A helper function for std::sort, comparing two struct ada_exc_info
   objects.

   The comparison is determined first by exception name, and then
   by exception address.  */

bool
ada_exc_info::operator< (const ada_exc_info &other) const
{
  int result;

  result = strcmp (name, other.name);
  if (result < 0)
    return true;
  if (result == 0 && addr < other.addr)
    return true;
  return false;
}

bool
ada_exc_info::operator== (const ada_exc_info &other) const
{
  return addr == other.addr && strcmp (name, other.name) == 0;
}

/* Sort EXCEPTIONS using compare_ada_exception_info as the comparison
   routine, but keeping the first SKIP elements untouched.

   All duplicates are also removed.  */

static void
sort_remove_dups_ada_exceptions_list (std::vector<ada_exc_info> *exceptions,
				      int skip)
{
  std::sort (exceptions->begin () + skip, exceptions->end ());
  exceptions->erase (std::unique (exceptions->begin () + skip, exceptions->end ()),
		     exceptions->end ());
}

/* Add all exceptions defined by the Ada standard whose name match
   a regular expression.

   If PREG is not NULL, then this regexp_t object is used to
   perform the symbol name matching.  Otherwise, no name-based
   filtering is performed.

   EXCEPTIONS is a vector of exceptions to which matching exceptions
   gets pushed.  */

static void
ada_add_standard_exceptions (compiled_regex *preg,
			     std::vector<ada_exc_info> *exceptions)
{
  int i;

  for (i = 0; i < ARRAY_SIZE (standard_exc); i++)
    {
      if (preg == NULL
	  || preg->exec (standard_exc[i], 0, NULL, 0) == 0)
	{
	  struct bound_minimal_symbol msymbol
	    = ada_lookup_simple_minsym (standard_exc[i]);

	  if (msymbol.minsym != NULL)
	    {
	      struct ada_exc_info info
		= {standard_exc[i], BMSYMBOL_VALUE_ADDRESS (msymbol)};

	      exceptions->push_back (info);
	    }
	}
    }
}

/* Add all Ada exceptions defined locally and accessible from the given
   FRAME.

   If PREG is not NULL, then this regexp_t object is used to
   perform the symbol name matching.  Otherwise, no name-based
   filtering is performed.

   EXCEPTIONS is a vector of exceptions to which matching exceptions
   gets pushed.  */

static void
ada_add_exceptions_from_frame (compiled_regex *preg,
			       struct frame_info *frame,
			       std::vector<ada_exc_info> *exceptions)
{
  const struct block *block = get_frame_block (frame, 0);

  while (block != 0)
    {
      struct block_iterator iter;
      struct symbol *sym;

      ALL_BLOCK_SYMBOLS (block, iter, sym)
	{
	  switch (SYMBOL_CLASS (sym))
	    {
	    case LOC_TYPEDEF:
	    case LOC_BLOCK:
	    case LOC_CONST:
	      break;
	    default:
	      if (ada_is_exception_sym (sym))
		{
		  struct ada_exc_info info = {sym->print_name (),
					      SYMBOL_VALUE_ADDRESS (sym)};

		  exceptions->push_back (info);
		}
	    }
	}
      if (BLOCK_FUNCTION (block) != NULL)
	break;
      block = BLOCK_SUPERBLOCK (block);
    }
}

/* Return true if NAME matches PREG or if PREG is NULL.  */

static bool
name_matches_regex (const char *name, compiled_regex *preg)
{
  return (preg == NULL
	  || preg->exec (ada_decode (name).c_str (), 0, NULL, 0) == 0);
}

/* Add all exceptions defined globally whose name name match
   a regular expression, excluding standard exceptions.

   The reason we exclude standard exceptions is that they need
   to be handled separately: Standard exceptions are defined inside
   a runtime unit which is normally not compiled with debugging info,
   and thus usually do not show up in our symbol search.  However,
   if the unit was in fact built with debugging info, we need to
   exclude them because they would duplicate the entry we found
   during the special loop that specifically searches for those
   standard exceptions.

   If PREG is not NULL, then this regexp_t object is used to
   perform the symbol name matching.  Otherwise, no name-based
   filtering is performed.

   EXCEPTIONS is a vector of exceptions to which matching exceptions
   gets pushed.  */

static void
ada_add_global_exceptions (compiled_regex *preg,
			   std::vector<ada_exc_info> *exceptions)
{
  /* In Ada, the symbol "search name" is a linkage name, whereas the
     regular expression used to do the matching refers to the natural
     name.  So match against the decoded name.  */
  expand_symtabs_matching (NULL,
			   lookup_name_info::match_any (),
			   [&] (const char *search_name)
			   {
			     std::string decoded = ada_decode (search_name);
			     return name_matches_regex (decoded.c_str (), preg);
			   },
			   NULL,
			   SEARCH_GLOBAL_BLOCK | SEARCH_STATIC_BLOCK,
			   VARIABLES_DOMAIN);

  for (objfile *objfile : current_program_space->objfiles ())
    {
      for (compunit_symtab *s : objfile->compunits ())
	{
	  const struct blockvector *bv = COMPUNIT_BLOCKVECTOR (s);
	  int i;

	  for (i = GLOBAL_BLOCK; i <= STATIC_BLOCK; i++)
	    {
	      const struct block *b = BLOCKVECTOR_BLOCK (bv, i);
	      struct block_iterator iter;
	      struct symbol *sym;

	      ALL_BLOCK_SYMBOLS (b, iter, sym)
		if (ada_is_non_standard_exception_sym (sym)
		    && name_matches_regex (sym->natural_name (), preg))
		  {
		    struct ada_exc_info info
		      = {sym->print_name (), SYMBOL_VALUE_ADDRESS (sym)};

		    exceptions->push_back (info);
		  }
	    }
	}
    }
}

/* Implements ada_exceptions_list with the regular expression passed
   as a regex_t, rather than a string.

   If not NULL, PREG is used to filter out exceptions whose names
   do not match.  Otherwise, all exceptions are listed.  */

static std::vector<ada_exc_info>
ada_exceptions_list_1 (compiled_regex *preg)
{
  std::vector<ada_exc_info> result;
  int prev_len;

  /* First, list the known standard exceptions.  These exceptions
     need to be handled separately, as they are usually defined in
     runtime units that have been compiled without debugging info.  */

  ada_add_standard_exceptions (preg, &result);

  /* Next, find all exceptions whose scope is local and accessible
     from the currently selected frame.  */

  if (has_stack_frames ())
    {
      prev_len = result.size ();
      ada_add_exceptions_from_frame (preg, get_selected_frame (NULL),
				     &result);
      if (result.size () > prev_len)
	sort_remove_dups_ada_exceptions_list (&result, prev_len);
    }

  /* Add all exceptions whose scope is global.  */

  prev_len = result.size ();
  ada_add_global_exceptions (preg, &result);
  if (result.size () > prev_len)
    sort_remove_dups_ada_exceptions_list (&result, prev_len);

  return result;
}

/* Return a vector of ada_exc_info.

   If REGEXP is NULL, all exceptions are included in the result.
   Otherwise, it should contain a valid regular expression,
   and only the exceptions whose names match that regular expression
   are included in the result.

   The exceptions are sorted in the following order:
     - Standard exceptions (defined by the Ada language), in
       alphabetical order;
     - Exceptions only visible from the current frame, in
       alphabetical order;
     - Exceptions whose scope is global, in alphabetical order.  */

std::vector<ada_exc_info>
ada_exceptions_list (const char *regexp)
{
  if (regexp == NULL)
    return ada_exceptions_list_1 (NULL);

  compiled_regex reg (regexp, REG_NOSUB, _("invalid regular expression"));
  return ada_exceptions_list_1 (&reg);
}

/* Implement the "info exceptions" command.  */

static void
info_exceptions_command (const char *regexp, int from_tty)
{
  struct gdbarch *gdbarch = get_current_arch ();

  std::vector<ada_exc_info> exceptions = ada_exceptions_list (regexp);

  if (regexp != NULL)
    printf_filtered
      (_("All Ada exceptions matching regular expression \"%s\":\n"), regexp);
  else
    printf_filtered (_("All defined Ada exceptions:\n"));

  for (const ada_exc_info &info : exceptions)
    printf_filtered ("%s: %s\n", info.name, paddress (gdbarch, info.addr));
}


				/* Language vector */

/* symbol_name_matcher_ftype adapter for wild_match.  */

static bool
do_wild_match (const char *symbol_search_name,
	       const lookup_name_info &lookup_name,
	       completion_match_result *comp_match_res)
{
  return wild_match (symbol_search_name, ada_lookup_name (lookup_name));
}

/* symbol_name_matcher_ftype adapter for full_match.  */

static bool
do_full_match (const char *symbol_search_name,
	       const lookup_name_info &lookup_name,
	       completion_match_result *comp_match_res)
{
  const char *lname = lookup_name.ada ().lookup_name ().c_str ();

  /* If both symbols start with "_ada_", just let the loop below
     handle the comparison.  However, if only the symbol name starts
     with "_ada_", skip the prefix and let the match proceed as
     usual.  */
  if (startswith (symbol_search_name, "_ada_")
      && !startswith (lname, "_ada"))
    symbol_search_name += 5;

  int uscore_count = 0;
  while (*lname != '\0')
    {
      if (*symbol_search_name != *lname)
	{
	  if (*symbol_search_name == 'B' && uscore_count == 2
	      && symbol_search_name[1] == '_')
	    {
	      symbol_search_name += 2;
	      while (isdigit (*symbol_search_name))
		++symbol_search_name;
	      if (symbol_search_name[0] == '_'
		  && symbol_search_name[1] == '_')
		{
		  symbol_search_name += 2;
		  continue;
		}
	    }
	  return false;
	}

      if (*symbol_search_name == '_')
	++uscore_count;
      else
	uscore_count = 0;

      ++symbol_search_name;
      ++lname;
    }

  return is_name_suffix (symbol_search_name);
}

/* symbol_name_matcher_ftype for exact (verbatim) matches.  */

static bool
do_exact_match (const char *symbol_search_name,
		const lookup_name_info &lookup_name,
		completion_match_result *comp_match_res)
{
  return strcmp (symbol_search_name, ada_lookup_name (lookup_name)) == 0;
}

/* Build the Ada lookup name for LOOKUP_NAME.  */

ada_lookup_name_info::ada_lookup_name_info (const lookup_name_info &lookup_name)
{
  gdb::string_view user_name = lookup_name.name ();

  if (!user_name.empty () && user_name[0] == '<')
    {
      if (user_name.back () == '>')
	m_encoded_name
	  = gdb::to_string (user_name.substr (1, user_name.size () - 2));
      else
	m_encoded_name
	  = gdb::to_string (user_name.substr (1, user_name.size () - 1));
      m_encoded_p = true;
      m_verbatim_p = true;
      m_wild_match_p = false;
      m_standard_p = false;
    }
  else
    {
      m_verbatim_p = false;

      m_encoded_p = user_name.find ("__") != gdb::string_view::npos;

      if (!m_encoded_p)
	{
	  const char *folded = ada_fold_name (user_name);
	  m_encoded_name = ada_encode_1 (folded, false);
	  if (m_encoded_name.empty ())
	    m_encoded_name = gdb::to_string (user_name);
	}
      else
	m_encoded_name = gdb::to_string (user_name);

      /* Handle the 'package Standard' special case.  See description
	 of m_standard_p.  */
      if (startswith (m_encoded_name.c_str (), "standard__"))
	{
	  m_encoded_name = m_encoded_name.substr (sizeof ("standard__") - 1);
	  m_standard_p = true;
	}
      else
	m_standard_p = false;

      /* If the name contains a ".", then the user is entering a fully
	 qualified entity name, and the match must not be done in wild
	 mode.  Similarly, if the user wants to complete what looks
	 like an encoded name, the match must not be done in wild
	 mode.  Also, in the standard__ special case always do
	 non-wild matching.  */
      m_wild_match_p
	= (lookup_name.match_type () != symbol_name_match_type::FULL
	   && !m_encoded_p
	   && !m_standard_p
	   && user_name.find ('.') == std::string::npos);
    }
}

/* symbol_name_matcher_ftype method for Ada.  This only handles
   completion mode.  */

static bool
ada_symbol_name_matches (const char *symbol_search_name,
			 const lookup_name_info &lookup_name,
			 completion_match_result *comp_match_res)
{
  return lookup_name.ada ().matches (symbol_search_name,
				     lookup_name.match_type (),
				     comp_match_res);
}

/* A name matcher that matches the symbol name exactly, with
   strcmp.  */

static bool
literal_symbol_name_matcher (const char *symbol_search_name,
			     const lookup_name_info &lookup_name,
			     completion_match_result *comp_match_res)
{
  gdb::string_view name_view = lookup_name.name ();

  if (lookup_name.completion_mode ()
      ? (strncmp (symbol_search_name, name_view.data (),
		  name_view.size ()) == 0)
      : symbol_search_name == name_view)
    {
      if (comp_match_res != NULL)
	comp_match_res->set_match (symbol_search_name);
      return true;
    }
  else
    return false;
}

/* Implement the "get_symbol_name_matcher" language_defn method for
   Ada.  */

static symbol_name_matcher_ftype *
ada_get_symbol_name_matcher (const lookup_name_info &lookup_name)
{
  if (lookup_name.match_type () == symbol_name_match_type::SEARCH_NAME)
    return literal_symbol_name_matcher;

  if (lookup_name.completion_mode ())
    return ada_symbol_name_matches;
  else
    {
      if (lookup_name.ada ().wild_match_p ())
	return do_wild_match;
      else if (lookup_name.ada ().verbatim_p ())
	return do_exact_match;
      else
	return do_full_match;
    }
}

/* Class representing the Ada language.  */

class ada_language : public language_defn
{
public:
  ada_language ()
    : language_defn (language_ada)
  { /* Nothing.  */ }

  /* See language.h.  */

  const char *name () const override
  { return "ada"; }

  /* See language.h.  */

  const char *natural_name () const override
  { return "Ada"; }

  /* See language.h.  */

  const std::vector<const char *> &filename_extensions () const override
  {
    static const std::vector<const char *> extensions
      = { ".adb", ".ads", ".a", ".ada", ".dg" };
    return extensions;
  }

  /* Print an array element index using the Ada syntax.  */

  void print_array_index (struct type *index_type,
			  LONGEST index,
			  struct ui_file *stream,
			  const value_print_options *options) const override
  {
    struct value *index_value = val_atr (index_type, index);

    value_print (index_value, stream, options);
    fprintf_filtered (stream, " => ");
  }

  /* Implement the "read_var_value" language_defn method for Ada.  */

  struct value *read_var_value (struct symbol *var,
				const struct block *var_block,
				struct frame_info *frame) const override
  {
    /* The only case where default_read_var_value is not sufficient
       is when VAR is a renaming...  */
    if (frame != nullptr)
      {
	const struct block *frame_block = get_frame_block (frame, NULL);
	if (frame_block != nullptr && ada_is_renaming_symbol (var))
	  return ada_read_renaming_var_value (var, frame_block);
      }

    /* This is a typical case where we expect the default_read_var_value
       function to work.  */
    return language_defn::read_var_value (var, var_block, frame);
  }

  /* See language.h.  */
  virtual bool symbol_printing_suppressed (struct symbol *symbol) const override
  {
    return symbol->artificial;
  }

  /* See language.h.  */
  void language_arch_info (struct gdbarch *gdbarch,
			   struct language_arch_info *lai) const override
  {
    const struct builtin_type *builtin = builtin_type (gdbarch);

    /* Helper function to allow shorter lines below.  */
    auto add = [&] (struct type *t)
    {
      lai->add_primitive_type (t);
    };

    add (arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
			    0, "integer"));
    add (arch_integer_type (gdbarch, gdbarch_long_bit (gdbarch),
			    0, "long_integer"));
    add (arch_integer_type (gdbarch, gdbarch_short_bit (gdbarch),
			    0, "short_integer"));
    struct type *char_type = arch_character_type (gdbarch, TARGET_CHAR_BIT,
						  0, "character");
    lai->set_string_char_type (char_type);
    add (char_type);
    add (arch_float_type (gdbarch, gdbarch_float_bit (gdbarch),
			  "float", gdbarch_float_format (gdbarch)));
    add (arch_float_type (gdbarch, gdbarch_double_bit (gdbarch),
			  "long_float", gdbarch_double_format (gdbarch)));
    add (arch_integer_type (gdbarch, gdbarch_long_long_bit (gdbarch),
			    0, "long_long_integer"));
    add (arch_float_type (gdbarch, gdbarch_long_double_bit (gdbarch),
			  "long_long_float",
			  gdbarch_long_double_format (gdbarch)));
    add (arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
			    0, "natural"));
    add (arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
			    0, "positive"));
    add (builtin->builtin_void);

    struct type *system_addr_ptr
      = lookup_pointer_type (arch_type (gdbarch, TYPE_CODE_VOID, TARGET_CHAR_BIT,
					"void"));
    system_addr_ptr->set_name ("system__address");
    add (system_addr_ptr);

    /* Create the equivalent of the System.Storage_Elements.Storage_Offset
       type.  This is a signed integral type whose size is the same as
       the size of addresses.  */
    unsigned int addr_length = TYPE_LENGTH (system_addr_ptr);
    add (arch_integer_type (gdbarch, addr_length * HOST_CHAR_BIT, 0,
			    "storage_offset"));

    lai->set_bool_type (builtin->builtin_bool);
  }

  /* See language.h.  */

  bool iterate_over_symbols
	(const struct block *block, const lookup_name_info &name,
	 domain_enum domain,
	 gdb::function_view<symbol_found_callback_ftype> callback) const override
  {
    std::vector<struct block_symbol> results
      = ada_lookup_symbol_list_worker (name, block, domain, 0);
    for (block_symbol &sym : results)
      {
	if (!callback (&sym))
	  return false;
      }

    return true;
  }

  /* See language.h.  */
  bool sniff_from_mangled_name (const char *mangled,
				char **out) const override
  {
    std::string demangled = ada_decode (mangled);

    *out = NULL;

    if (demangled != mangled && demangled[0] != '<')
      {
	/* Set the gsymbol language to Ada, but still return 0.
	   Two reasons for that:

	   1. For Ada, we prefer computing the symbol's decoded name
	   on the fly rather than pre-compute it, in order to save
	   memory (Ada projects are typically very large).

	   2. There are some areas in the definition of the GNAT
	   encoding where, with a bit of bad luck, we might be able
	   to decode a non-Ada symbol, generating an incorrect
	   demangled name (Eg: names ending with "TB" for instance
	   are identified as task bodies and so stripped from
	   the decoded name returned).

	   Returning true, here, but not setting *DEMANGLED, helps us get
	   a little bit of the best of both worlds.  Because we're last,
	   we should not affect any of the other languages that were
	   able to demangle the symbol before us; we get to correctly
	   tag Ada symbols as such; and even if we incorrectly tagged a
	   non-Ada symbol, which should be rare, any routing through the
	   Ada language should be transparent (Ada tries to behave much
	   like C/C++ with non-Ada symbols).  */
	return true;
      }

    return false;
  }

  /* See language.h.  */

  char *demangle_symbol (const char *mangled, int options) const override
  {
    return ada_la_decode (mangled, options);
  }

  /* See language.h.  */

  void print_type (struct type *type, const char *varstring,
		   struct ui_file *stream, int show, int level,
		   const struct type_print_options *flags) const override
  {
    ada_print_type (type, varstring, stream, show, level, flags);
  }

  /* See language.h.  */

  const char *word_break_characters (void) const override
  {
    return ada_completer_word_break_characters;
  }

  /* See language.h.  */

  void collect_symbol_completion_matches (completion_tracker &tracker,
					  complete_symbol_mode mode,
					  symbol_name_match_type name_match_type,
					  const char *text, const char *word,
					  enum type_code code) const override
  {
    struct symbol *sym;
    const struct block *b, *surrounding_static_block = 0;
    struct block_iterator iter;

    gdb_assert (code == TYPE_CODE_UNDEF);

    lookup_name_info lookup_name (text, name_match_type, true);

    /* First, look at the partial symtab symbols.  */
    expand_symtabs_matching (NULL,
			     lookup_name,
			     NULL,
			     NULL,
			     SEARCH_GLOBAL_BLOCK | SEARCH_STATIC_BLOCK,
			     ALL_DOMAIN);

    /* At this point scan through the misc symbol vectors and add each
       symbol you find to the list.  Eventually we want to ignore
       anything that isn't a text symbol (everything else will be
       handled by the psymtab code above).  */

    for (objfile *objfile : current_program_space->objfiles ())
      {
	for (minimal_symbol *msymbol : objfile->msymbols ())
	  {
	    QUIT;

	    if (completion_skip_symbol (mode, msymbol))
	      continue;

	    language symbol_language = msymbol->language ();

	    /* Ada minimal symbols won't have their language set to Ada.  If
	       we let completion_list_add_name compare using the
	       default/C-like matcher, then when completing e.g., symbols in a
	       package named "pck", we'd match internal Ada symbols like
	       "pckS", which are invalid in an Ada expression, unless you wrap
	       them in '<' '>' to request a verbatim match.

	       Unfortunately, some Ada encoded names successfully demangle as
	       C++ symbols (using an old mangling scheme), such as "name__2Xn"
	       -> "Xn::name(void)" and thus some Ada minimal symbols end up
	       with the wrong language set.  Paper over that issue here.  */
	    if (symbol_language == language_auto
		|| symbol_language == language_cplus)
	      symbol_language = language_ada;

	    completion_list_add_name (tracker,
				      symbol_language,
				      msymbol->linkage_name (),
				      lookup_name, text, word);
	  }
      }

    /* Search upwards from currently selected frame (so that we can
       complete on local vars.  */

    for (b = get_selected_block (0); b != NULL; b = BLOCK_SUPERBLOCK (b))
      {
	if (!BLOCK_SUPERBLOCK (b))
	  surrounding_static_block = b;   /* For elmin of dups */

	ALL_BLOCK_SYMBOLS (b, iter, sym)
	  {
	    if (completion_skip_symbol (mode, sym))
	      continue;

	    completion_list_add_name (tracker,
				      sym->language (),
				      sym->linkage_name (),
				      lookup_name, text, word);
	  }
      }

    /* Go through the symtabs and check the externs and statics for
       symbols which match.  */

    for (objfile *objfile : current_program_space->objfiles ())
      {
	for (compunit_symtab *s : objfile->compunits ())
	  {
	    QUIT;
	    b = BLOCKVECTOR_BLOCK (COMPUNIT_BLOCKVECTOR (s), GLOBAL_BLOCK);
	    ALL_BLOCK_SYMBOLS (b, iter, sym)
	      {
		if (completion_skip_symbol (mode, sym))
		  continue;

		completion_list_add_name (tracker,
					  sym->language (),
					  sym->linkage_name (),
					  lookup_name, text, word);
	      }
	  }
      }

    for (objfile *objfile : current_program_space->objfiles ())
      {
	for (compunit_symtab *s : objfile->compunits ())
	  {
	    QUIT;
	    b = BLOCKVECTOR_BLOCK (COMPUNIT_BLOCKVECTOR (s), STATIC_BLOCK);
	    /* Don't do this block twice.  */
	    if (b == surrounding_static_block)
	      continue;
	    ALL_BLOCK_SYMBOLS (b, iter, sym)
	      {
		if (completion_skip_symbol (mode, sym))
		  continue;

		completion_list_add_name (tracker,
					  sym->language (),
					  sym->linkage_name (),
					  lookup_name, text, word);
	      }
	  }
      }
  }

  /* See language.h.  */

  gdb::unique_xmalloc_ptr<char> watch_location_expression
	(struct type *type, CORE_ADDR addr) const override
  {
    type = check_typedef (TYPE_TARGET_TYPE (check_typedef (type)));
    std::string name = type_to_string (type);
    return gdb::unique_xmalloc_ptr<char>
      (xstrprintf ("{%s} %s", name.c_str (), core_addr_to_string (addr)));
  }

  /* See language.h.  */

  void value_print (struct value *val, struct ui_file *stream,
		    const struct value_print_options *options) const override
  {
    return ada_value_print (val, stream, options);
  }

  /* See language.h.  */

  void value_print_inner
	(struct value *val, struct ui_file *stream, int recurse,
	 const struct value_print_options *options) const override
  {
    return ada_value_print_inner (val, stream, recurse, options);
  }

  /* See language.h.  */

  struct block_symbol lookup_symbol_nonlocal
	(const char *name, const struct block *block,
	 const domain_enum domain) const override
  {
    struct block_symbol sym;

    sym = ada_lookup_symbol (name, block_static_block (block), domain);
    if (sym.symbol != NULL)
      return sym;

    /* If we haven't found a match at this point, try the primitive
       types.  In other languages, this search is performed before
       searching for global symbols in order to short-circuit that
       global-symbol search if it happens that the name corresponds
       to a primitive type.  But we cannot do the same in Ada, because
       it is perfectly legitimate for a program to declare a type which
       has the same name as a standard type.  If looking up a type in
       that situation, we have traditionally ignored the primitive type
       in favor of user-defined types.  This is why, unlike most other
       languages, we search the primitive types this late and only after
       having searched the global symbols without success.  */

    if (domain == VAR_DOMAIN)
      {
	struct gdbarch *gdbarch;

	if (block == NULL)
	  gdbarch = target_gdbarch ();
	else
	  gdbarch = block_gdbarch (block);
	sym.symbol
	  = language_lookup_primitive_type_as_symbol (this, gdbarch, name);
	if (sym.symbol != NULL)
	  return sym;
      }

    return {};
  }

  /* See language.h.  */

  int parser (struct parser_state *ps) const override
  {
    warnings_issued = 0;
    return ada_parse (ps);
  }

  /* See language.h.  */

  void emitchar (int ch, struct type *chtype,
		 struct ui_file *stream, int quoter) const override
  {
    ada_emit_char (ch, chtype, stream, quoter, 1);
  }

  /* See language.h.  */

  void printchar (int ch, struct type *chtype,
		  struct ui_file *stream) const override
  {
    ada_printchar (ch, chtype, stream);
  }

  /* See language.h.  */

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

  /* See language.h.  */

  void print_typedef (struct type *type, struct symbol *new_symbol,
		      struct ui_file *stream) const override
  {
    ada_print_typedef (type, new_symbol, stream);
  }

  /* See language.h.  */

  bool is_string_type_p (struct type *type) const override
  {
    return ada_is_string_type (type);
  }

  /* See language.h.  */

  const char *struct_too_deep_ellipsis () const override
  { return "(...)"; }

  /* See language.h.  */

  bool c_style_arrays_p () const override
  { return false; }

  /* See language.h.  */

  bool store_sym_names_in_linkage_form_p () const override
  { return true; }

  /* See language.h.  */

  const struct lang_varobj_ops *varobj_ops () const override
  { return &ada_varobj_ops; }

protected:
  /* See language.h.  */

  symbol_name_matcher_ftype *get_symbol_name_matcher_inner
	(const lookup_name_info &lookup_name) const override
  {
    return ada_get_symbol_name_matcher (lookup_name);
  }
};

/* Single instance of the Ada language class.  */

static ada_language ada_language_defn;

/* Command-list for the "set/show ada" prefix command.  */
static struct cmd_list_element *set_ada_list;
static struct cmd_list_element *show_ada_list;

static void
initialize_ada_catchpoint_ops (void)
{
  struct breakpoint_ops *ops;

  initialize_breakpoint_ops ();

  ops = &catch_exception_breakpoint_ops;
  *ops = bkpt_breakpoint_ops;
  ops->allocate_location = allocate_location_exception;
  ops->re_set = re_set_exception;
  ops->check_status = check_status_exception;
  ops->print_it = print_it_exception;
  ops->print_one = print_one_exception;
  ops->print_mention = print_mention_exception;
  ops->print_recreate = print_recreate_exception;

  ops = &catch_exception_unhandled_breakpoint_ops;
  *ops = bkpt_breakpoint_ops;
  ops->allocate_location = allocate_location_exception;
  ops->re_set = re_set_exception;
  ops->check_status = check_status_exception;
  ops->print_it = print_it_exception;
  ops->print_one = print_one_exception;
  ops->print_mention = print_mention_exception;
  ops->print_recreate = print_recreate_exception;

  ops = &catch_assert_breakpoint_ops;
  *ops = bkpt_breakpoint_ops;
  ops->allocate_location = allocate_location_exception;
  ops->re_set = re_set_exception;
  ops->check_status = check_status_exception;
  ops->print_it = print_it_exception;
  ops->print_one = print_one_exception;
  ops->print_mention = print_mention_exception;
  ops->print_recreate = print_recreate_exception;

  ops = &catch_handlers_breakpoint_ops;
  *ops = bkpt_breakpoint_ops;
  ops->allocate_location = allocate_location_exception;
  ops->re_set = re_set_exception;
  ops->check_status = check_status_exception;
  ops->print_it = print_it_exception;
  ops->print_one = print_one_exception;
  ops->print_mention = print_mention_exception;
  ops->print_recreate = print_recreate_exception;
}

/* This module's 'new_objfile' observer.  */

static void
ada_new_objfile_observer (struct objfile *objfile)
{
  ada_clear_symbol_cache ();
}

/* This module's 'free_objfile' observer.  */

static void
ada_free_objfile_observer (struct objfile *objfile)
{
  ada_clear_symbol_cache ();
}

void _initialize_ada_language ();
void
_initialize_ada_language ()
{
  initialize_ada_catchpoint_ops ();

  add_basic_prefix_cmd ("ada", no_class,
			_("Prefix command for changing Ada-specific settings."),
			&set_ada_list, 0, &setlist);

  add_show_prefix_cmd ("ada", no_class,
		       _("Generic command for showing Ada-specific settings."),
		       &show_ada_list, 0, &showlist);

  add_setshow_boolean_cmd ("trust-PAD-over-XVS", class_obscure,
			   &trust_pad_over_xvs, _("\
Enable or disable an optimization trusting PAD types over XVS types."), _("\
Show whether an optimization trusting PAD types over XVS types is activated."),
			   _("\
This is related to the encoding used by the GNAT compiler.  The debugger\n\
should normally trust the contents of PAD types, but certain older versions\n\
of GNAT have a bug that sometimes causes the information in the PAD type\n\
to be incorrect.  Turning this setting \"off\" allows the debugger to\n\
work around this bug.  It is always safe to turn this option \"off\", but\n\
this incurs a slight performance penalty, so it is recommended to NOT change\n\
this option to \"off\" unless necessary."),
			    NULL, NULL, &set_ada_list, &show_ada_list);

  add_setshow_boolean_cmd ("print-signatures", class_vars,
			   &print_signatures, _("\
Enable or disable the output of formal and return types for functions in the \
overloads selection menu."), _("\
Show whether the output of formal and return types for functions in the \
overloads selection menu is activated."),
			   NULL, NULL, NULL, &set_ada_list, &show_ada_list);

  add_catch_command ("exception", _("\
Catch Ada exceptions, when raised.\n\
Usage: catch exception [ARG] [if CONDITION]\n\
Without any argument, stop when any Ada exception is raised.\n\
If ARG is \"unhandled\" (without the quotes), only stop when the exception\n\
being raised does not have a handler (and will therefore lead to the task's\n\
termination).\n\
Otherwise, the catchpoint only stops when the name of the exception being\n\
raised is the same as ARG.\n\
CONDITION is a boolean expression that is evaluated to see whether the\n\
exception should cause a stop."),
		     catch_ada_exception_command,
		     catch_ada_completer,
		     CATCH_PERMANENT,
		     CATCH_TEMPORARY);

  add_catch_command ("handlers", _("\
Catch Ada exceptions, when handled.\n\
Usage: catch handlers [ARG] [if CONDITION]\n\
Without any argument, stop when any Ada exception is handled.\n\
With an argument, catch only exceptions with the given name.\n\
CONDITION is a boolean expression that is evaluated to see whether the\n\
exception should cause a stop."),
		     catch_ada_handlers_command,
		     catch_ada_completer,
		     CATCH_PERMANENT,
		     CATCH_TEMPORARY);
  add_catch_command ("assert", _("\
Catch failed Ada assertions, when raised.\n\
Usage: catch assert [if CONDITION]\n\
CONDITION is a boolean expression that is evaluated to see whether the\n\
exception should cause a stop."),
		     catch_assert_command,
		     NULL,
		     CATCH_PERMANENT,
		     CATCH_TEMPORARY);

  varsize_limit = 65536;
  add_setshow_uinteger_cmd ("varsize-limit", class_support,
			    &varsize_limit, _("\
Set the maximum number of bytes allowed in a variable-size object."), _("\
Show the maximum number of bytes allowed in a variable-size object."), _("\
Attempts to access an object whose size is not a compile-time constant\n\
and exceeds this limit will cause an error."),
			    NULL, NULL, &setlist, &showlist);

  add_info ("exceptions", info_exceptions_command,
	    _("\
List all Ada exception names.\n\
Usage: info exceptions [REGEXP]\n\
If a regular expression is passed as an argument, only those matching\n\
the regular expression are listed."));

  add_basic_prefix_cmd ("ada", class_maintenance,
			_("Set Ada maintenance-related variables."),
			&maint_set_ada_cmdlist,
			0/*allow-unknown*/, &maintenance_set_cmdlist);

  add_show_prefix_cmd ("ada", class_maintenance,
		       _("Show Ada maintenance-related variables."),
		       &maint_show_ada_cmdlist,
		       0/*allow-unknown*/, &maintenance_show_cmdlist);

  add_setshow_boolean_cmd
    ("ignore-descriptive-types", class_maintenance,
     &ada_ignore_descriptive_types_p,
     _("Set whether descriptive types generated by GNAT should be ignored."),
     _("Show whether descriptive types generated by GNAT should be ignored."),
     _("\
When enabled, the debugger will stop using the DW_AT_GNAT_descriptive_type\n\
DWARF attribute."),
     NULL, NULL, &maint_set_ada_cmdlist, &maint_show_ada_cmdlist);

  decoded_names_store = htab_create_alloc (256, htab_hash_string,
					   htab_eq_string,
					   NULL, xcalloc, xfree);

  /* The ada-lang observers.  */
  gdb::observers::new_objfile.attach (ada_new_objfile_observer, "ada-lang");
  gdb::observers::free_objfile.attach (ada_free_objfile_observer, "ada-lang");
  gdb::observers::inferior_exit.attach (ada_inferior_exit, "ada-lang");
}
