Split out some Ada type resolution code
[deliverable/binutils-gdb.git] / gdb / ada-lang.c
index b90e7a05bcdf295c45a2e148db1fd0c6fe02c526..098a5a6858f71cb99a9c3caa3dc237ccf6da436b 100644 (file)
@@ -1,6 +1,6 @@
 /* Ada language support routines for GDB, the GNU debugger.
 
-   Copyright (C) 1992-2020 Free Software Foundation, Inc.
+   Copyright (C) 1992-2021 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
@@ -57,6 +57,7 @@
 #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).
@@ -100,35 +101,31 @@ 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 (struct obstack *,
+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 (struct obstack *, const struct block *,
+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 (struct block_symbol *, int);
+static int is_nonfunction (const std::vector<struct block_symbol> &);
 
-static void add_defn_to_vec (struct obstack *, struct symbol *,
-                             const struct block *);
-
-static int num_defns_collected (struct obstack *);
-
-static struct block_symbol *defns_collected (struct obstack *, int);
+static void add_defn_to_vec (std::vector<struct block_symbol> &,
+                            struct symbol *,
+                            const struct block *);
 
 static struct value *resolve_subexp (expression_up *, int *, int,
-                                     struct type *, int,
+                                    struct type *, int,
                                     innermost_block_tracker *);
 
 static void replace_operator_with_call (expression_up *, int, int, int,
-                                        struct symbol *, const struct block *);
+                                       struct symbol *, const struct block *);
 
 static int possible_user_operator_p (enum exp_opcode, struct value **);
 
-static const char *ada_op_name (enum exp_opcode);
-
 static const char *ada_decoded_op_name (enum exp_opcode);
 
 static int numeric_type_p (struct type *);
@@ -140,18 +137,18 @@ 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);
+                                               int, int);
 
 static struct value *evaluate_subexp_type (struct expression *, int *);
 
 static struct type *ada_find_parallel_type_with_name (struct type *,
-                                                      const char *);
+                                                     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 *);
+                                                 CORE_ADDR, struct value *);
 
 static struct type *to_fixed_array_type (struct type *, struct value *, int);
 
@@ -170,15 +167,13 @@ static long decode_packed_array_bitsize (struct type *);
 
 static struct value *decode_constrained_packed_array (struct value *);
 
-static int ada_is_packed_array_type  (struct type *);
-
 static int ada_is_unconstrained_packed_array_type (struct type *);
 
 static struct value *value_subscript_packed (struct value *, int,
-                                             struct value **);
+                                            struct value **);
 
 static struct value *coerce_unspec_val_to_type (struct value *,
-                                                struct type *);
+                                               struct type *);
 
 static int lesseq_defined_than (struct symbol *, struct symbol *);
 
@@ -186,7 +181,7 @@ static int equiv_types (struct type *, struct type *);
 
 static int is_name_suffix (const char *);
 
-static int advance_wild_match (const char **, const char *, int);
+static int advance_wild_match (const char **, const char *, char);
 
 static bool wild_match (const char *name, const char *patn);
 
@@ -198,20 +193,18 @@ static struct value *value_pos_atr (struct type *, struct value *);
 
 static struct value *val_atr (struct type *, LONGEST);
 
-static struct value *value_val_atr (struct type *, struct value *);
-
 static struct symbol *standard_lookup (const char *, const struct block *,
-                                       domain_enum);
+                                      domain_enum);
 
 static struct value *ada_search_struct_field (const char *, struct value *, int,
-                                              struct type *);
+                                             struct type *);
 
 static int find_struct_field (const char *, struct type *, int,
-                              struct type **, int *, int *, int *, int *);
+                             struct type **, int *, int *, int *, int *);
 
-static int ada_resolve_function (struct block_symbol *, int,
-                                 struct value **, int, const char *,
-                                 struct type *, int);
+static int ada_resolve_function (std::vector<struct block_symbol> &,
+                                struct value **, int, const char *,
+                                struct type *, int);
 
 static int ada_is_direct_array_type (struct type *);
 
@@ -222,23 +215,24 @@ static struct value *assign_aggregate (struct value *, struct value *,
                                       struct expression *,
                                       int *, enum noside);
 
-static void aggregate_assign_from_choices (struct value *, struct value *, 
+static void aggregate_assign_from_choices (struct value *, struct value *,
                                           struct expression *,
-                                          int *, LONGEST *, int *,
-                                          int, LONGEST, LONGEST);
+                                          int *, std::vector<LONGEST> &,
+                                          LONGEST, LONGEST);
 
 static void aggregate_assign_positional (struct value *, struct value *,
                                         struct expression *,
-                                        int *, LONGEST *, int *, int,
+                                        int *, std::vector<LONGEST> &,
                                         LONGEST, LONGEST);
 
 
 static void aggregate_assign_others (struct value *, struct value *,
                                     struct expression *,
-                                    int *, LONGEST *, int, LONGEST, LONGEST);
+                                    int *, std::vector<LONGEST> &,
+                                    LONGEST, LONGEST);
 
 
-static void add_component_interval (LONGEST, LONGEST, LONGEST *, int *, int);
+static void add_component_interval (LONGEST, LONGEST, std::vector<LONGEST> &);
 
 
 static struct value *ada_evaluate_subexp (struct type *, struct expression *,
@@ -286,14 +280,12 @@ struct cache_entry
 struct ada_symbol_cache
 {
   /* An obstack used to store the entries in our cache.  */
-  struct obstack cache_space;
+  struct auto_obstack cache_space;
 
   /* The root of the hash table used to implement our symbol cache.  */
-  struct cache_entry *root[HASH_SIZE];
+  struct cache_entry *root[HASH_SIZE] {};
 };
 
-static void ada_free_symbol_cache (struct ada_symbol_cache *sym_cache);
-
 /* Maximum-sized dynamic type.  */
 static unsigned int varsize_limit;
 
@@ -388,14 +380,8 @@ ada_inferior_exit (struct inferior *inf)
 /* This module's per-program-space data.  */
 struct ada_pspace_data
 {
-  ~ada_pspace_data ()
-  {
-    if (sym_cache != NULL)
-      ada_free_symbol_cache (sym_cache);
-  }
-
   /* The Ada symbol cache.  */
-  struct ada_symbol_cache *sym_cache = nullptr;
+  std::unique_ptr<ada_symbol_cache> sym_cache;
 };
 
 /* Key to our per-program-space data.  */
@@ -418,7 +404,7 @@ get_ada_pspace_data (struct program_space *pspace)
   return data;
 }
 
-                        /* Utilities */
+                       /* Utilities */
 
 /* If TYPE is a TYPE_CODE_TYPEDEF type, return the target type after
    all typedef layers have been peeled.  Otherwise, return TYPE.
@@ -488,29 +474,6 @@ add_angle_brackets (const char *str)
   return string_printf ("<%s>", str);
 }
 
-/* Assuming V points to an array of S objects,  make sure that it contains at
-   least M objects, updating V and S as necessary.  */
-
-#define GROW_VECT(v, s, m)                                    \
-   if ((s) < (m)) (v) = (char *) grow_vect (v, &(s), m, sizeof *(v));
-
-/* Assuming VECT points to an array of *SIZE objects of size
-   ELEMENT_SIZE, grow it to contain at least MIN_SIZE objects,
-   updating *SIZE as necessary and returning the (new) array.  */
-
-static void *
-grow_vect (void *vect, size_t *size, size_t min_size, int element_size)
-{
-  if (*size < min_size)
-    {
-      *size *= 2;
-      if (*size < min_size)
-        *size = min_size;
-      vect = xrealloc (vect, *size * element_size);
-    }
-  return vect;
-}
-
 /* True (non-zero) iff TARGET matches FIELD_NAME up to any trailing
    suffix of FIELD_NAME beginning "___".  */
 
@@ -522,9 +485,9 @@ field_name_match (const char *field_name, const char *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)));
+        || (startswith (field_name + len, "___")
+            && strcmp (field_name + strlen (field_name) - 6,
+                       "___XVN") != 0)));
 }
 
 
@@ -538,7 +501,7 @@ field_name_match (const char *field_name, const char *target)
 
 int
 ada_get_field_index (const struct type *type, const char *field_name,
-                     int maybe_missing)
+                    int maybe_missing)
 {
   int fieldno;
   struct type *struct_type = check_typedef ((struct type *) type);
@@ -549,7 +512,7 @@ ada_get_field_index (const struct type *type, const char *field_name,
 
   if (!maybe_missing)
     error (_("Unable to find field %s in struct %s.  Aborting"),
-           field_name, struct_type->name ());
+          field_name, struct_type->name ());
 
   return -1;
 }
@@ -566,9 +529,9 @@ ada_name_prefix_len (const char *name)
       const char *p = strstr (name, "___");
 
       if (p == NULL)
-        return strlen (name);
+       return strlen (name);
       else
-        return p - name;
+       return p - name;
     }
 }
 
@@ -601,16 +564,20 @@ coerce_unspec_val_to_type (struct value *val, struct type *type)
       struct value *result;
 
       /* Make sure that the object size is not unreasonable before
-         trying to allocate some memory for it.  */
+        trying to allocate some memory for it.  */
       ada_ensure_varsize_limit (type);
 
-      if (value_lazy (val)
-          || TYPE_LENGTH (type) > TYPE_LENGTH (value_type (val)))
+      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_raw (result, 0, val, 0, TYPE_LENGTH (type));
+         value_contents_copy (result, 0, val, 0, TYPE_LENGTH (type));
        }
       set_value_component_location (result, val);
       set_value_bitsize (result, value_bitsize (val));
@@ -796,7 +763,7 @@ 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;
+       return type;
       type = TYPE_TARGET_TYPE (type);
     }
   return type;
@@ -814,12 +781,12 @@ ada_get_decoded_value (struct value *value)
 
   if (ada_is_array_descriptor_type (type)
       || (ada_is_constrained_packed_array_type (type)
-          && type->code () != TYPE_CODE_PTR))
+         && type->code () != TYPE_CODE_PTR))
     {
       if (type->code () == TYPE_CODE_TYPEDEF)  /* array access type.  */
-        value = ada_coerce_to_simple_array_ptr (value);
+       value = ada_coerce_to_simple_array_ptr (value);
       else
-        value = ada_coerce_to_simple_array (value);
+       value = ada_coerce_to_simple_array (value);
     }
   else
     value = ada_to_fixed_value (value);
@@ -843,7 +810,7 @@ ada_get_decoded_type (struct type *type)
 
 \f
 
-                                /* Language Selection */
+                               /* 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).  */
@@ -878,7 +845,7 @@ ada_main_name (void)
     {
       CORE_ADDR main_program_name_addr = BMSYMBOL_VALUE_ADDRESS (msym);
       if (main_program_name_addr == 0)
-        error (_("Invalid address for Ada main program name."));
+       error (_("Invalid address for Ada main program name."));
 
       main_program_name = target_read_string (main_program_name_addr, 1024);
       return main_program_name.get ();
@@ -888,7 +855,7 @@ ada_main_name (void)
   return NULL;
 }
 \f
-                                /* Symbols */
+                               /* Symbols */
 
 /* Table of Ada operators and their GNAT-encoded names.  Last entry is pair
    of NULLs.  */
@@ -918,67 +885,49 @@ const struct ada_opname_map ada_opname_table[] = {
   {NULL, NULL}
 };
 
-/* The "encoded" form of DECODED, according to GNAT conventions.  The
-   result is valid until the next call to ada_encode.  If
+/* The "encoded" form of DECODED, according to GNAT conventions.  If
    THROW_ERRORS, throw an error if invalid operator name is found.
-   Otherwise, return NULL in that case.  */
+   Otherwise, return the empty string in that case.  */
 
-static char *
+static std::string
 ada_encode_1 (const char *decoded, bool throw_errors)
 {
-  static char *encoding_buffer = NULL;
-  static size_t encoding_buffer_size = 0;
-  const char *p;
-  int k;
-
   if (decoded == NULL)
-    return NULL;
-
-  GROW_VECT (encoding_buffer, encoding_buffer_size,
-             2 * strlen (decoded) + 10);
+    return {};
 
-  k = 0;
-  for (p = decoded; *p != '\0'; p += 1)
+  std::string encoding_buffer;
+  for (const char *p = decoded; *p != '\0'; p += 1)
     {
       if (*p == '.')
-        {
-          encoding_buffer[k] = encoding_buffer[k + 1] = '_';
-          k += 2;
-        }
+       encoding_buffer.append ("__");
       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)
+       {
+         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 NULL;
+               return {};
            }
-          strcpy (encoding_buffer + k, mapping->encoded);
-          k += strlen (mapping->encoded);
-          break;
-        }
+         encoding_buffer.append (mapping->encoded);
+         break;
+       }
       else
-        {
-          encoding_buffer[k] = *p;
-          k += 1;
-        }
+       encoding_buffer.push_back (*p);
     }
 
-  encoding_buffer[k] = '\0';
   return encoding_buffer;
 }
 
-/* The "encoded" form of DECODED, according to GNAT conventions.
-   The result is valid until the next call to ada_encode.  */
+/* The "encoded" form of DECODED, according to GNAT conventions.  */
 
-char *
+std::string
 ada_encode (const char *decoded)
 {
   return ada_encode_1 (decoded, true);
@@ -988,29 +937,21 @@ ada_encode (const char *decoded)
    quotes, unfolded, but with the quotes stripped away.  Result good
    to next call.  */
 
-static char *
+static const char *
 ada_fold_name (gdb::string_view name)
 {
-  static char *fold_buffer = NULL;
-  static size_t fold_buffer_size = 0;
-
-  int len = name.size ();
-  GROW_VECT (fold_buffer, fold_buffer_size, len + 1);
+  static std::string fold_storage;
 
-  if (name[0] == '\'')
-    {
-      strncpy (fold_buffer, name.data () + 1, len - 2);
-      fold_buffer[len - 2] = '\000';
-    }
+  if (!name.empty () && name[0] == '\'')
+    fold_storage = gdb::to_string (name.substr (1, name.size () - 2));
   else
     {
-      int i;
-
-      for (i = 0; i <= len; i += 1)
-        fold_buffer[i] = tolower (name[i]);
+      fold_storage = gdb::to_string (name);
+      for (int i = 0; i < name.size (); i += 1)
+       fold_storage[i] = tolower (fold_storage[i]);
     }
 
-  return fold_buffer;
+  return fold_storage.c_str ();
 }
 
 /* Return nonzero if C is either a digit or a lowercase alphabet character.  */
@@ -1041,15 +982,15 @@ ada_remove_trailing_digits (const char *encoded, int *len)
       int i = *len - 2;
 
       while (i > 0 && isdigit (encoded[i]))
-        i--;
+       i--;
       if (i >= 0 && encoded[i] == '.')
-        *len = i;
+       *len = i;
       else if (i >= 0 && encoded[i] == '$')
-        *len = i;
+       *len = i;
       else if (i >= 2 && startswith (encoded + i - 2, "___"))
-        *len = i - 2;
+       *len = i - 2;
       else if (i >= 1 && startswith (encoded + i - 1, "__"))
-        *len = i - 1;
+       *len = i - 1;
     }
 }
 
@@ -1118,9 +1059,9 @@ ada_decode (const char *encoded)
   if (p != NULL && p - encoded < len0 - 3)
     {
       if (p[3] == 'X')
-        len0 = p - encoded;
+       len0 = p - encoded;
       else
-        goto Suppress;
+       goto Suppress;
     }
 
   /* Remove any trailing TKB suffix.  It tells us that this symbol
@@ -1153,12 +1094,12 @@ ada_decode (const char *encoded)
     {
       i = len0 - 2;
       while ((i >= 0 && isdigit (encoded[i]))
-             || (i >= 1 && encoded[i] == '_' && isdigit (encoded[i - 1])))
-        i -= 1;
+            || (i >= 1 && encoded[i] == '_' && isdigit (encoded[i - 1])))
+       i -= 1;
       if (i > 1 && encoded[i] == '_' && encoded[i - 1] == '_')
-        len0 = i - 1;
+       len0 = i - 1;
       else if (encoded[i] == '$')
-        len0 = i;
+       len0 = i;
     }
 
   /* The first few characters that are not alphabetic are not part
@@ -1172,136 +1113,136 @@ ada_decode (const char *encoded)
     {
       /* 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;
-        }
+       {
+         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).  */
+        into "." (just below).  */
 
       if (i < len0 - 4 && startswith (encoded + i, "TK__"))
-        i += 2;
+       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.  */
+        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;
-        }
+         && 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'.
+        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.  */
+        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;
-            }
-        }
+         && 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.  */
+        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++;
-        }
+         && 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;
-        }
+       {
+         /* 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;
-        }
+       {
+        /* 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;
-        }
+       {
+         /* 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);
 
@@ -1357,19 +1298,19 @@ ada_decode_symbol (const struct general_symbol_info *arg)
       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);
+         char **slot = (char **) htab_find_slot (decoded_names_store,
+                                                 decoded.c_str (), INSERT);
 
-          if (*slot == NULL)
-            *slot = xstrdup (decoded.c_str ());
-          *resultp = *slot;
-        }
+         if (*slot == NULL)
+           *slot = xstrdup (decoded.c_str ());
+         *resultp = *slot;
+       }
     }
 
   return *resultp;
@@ -1383,7 +1324,7 @@ ada_la_decode (const char *encoded, int options)
 
 \f
 
-                                /* Arrays */
+                               /* Arrays */
 
 /* Assuming that INDEX_DESC_TYPE is an ___XA structure, a structure
    generated by the GNAT compiler to describe the index type used
@@ -1426,7 +1367,7 @@ ada_fixup_array_indexes_type (struct type *index_desc_type)
      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)
+                TYPE_FIELD_NAME (index_desc_type, 0)) == 0)
     return;
 
   /* Fixup each field of INDEX_DESC_TYPE.  */
@@ -1457,7 +1398,7 @@ desc_base_type (struct type *type)
 
   if (type != NULL
       && (type->code () == TYPE_CODE_PTR
-          || type->code () == TYPE_CODE_REF))
+         || type->code () == TYPE_CODE_REF))
     return ada_check_typedef (TYPE_TARGET_TYPE (type));
   else
     return type;
@@ -1489,9 +1430,9 @@ thin_descriptor_type (struct type *type)
       struct type *alt_type = ada_find_parallel_type (base_type, "___XVE");
 
       if (alt_type == NULL)
-        return base_type;
+       return base_type;
       else
-        return alt_type;
+       return alt_type;
     }
 }
 
@@ -1518,7 +1459,7 @@ 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);
+         && lookup_struct_elt_type (type, "P_BOUNDS", 1) != NULL);
 }
 
 /* If TYPE is the type of an array descriptor (fat or thin pointer) or a
@@ -1537,16 +1478,16 @@ desc_bounds_type (struct type *type)
     {
       type = thin_descriptor_type (type);
       if (type == NULL)
-        return NULL;
+       return NULL;
       r = lookup_struct_elt_type (type, "BOUNDS", 1);
       if (r != NULL)
-        return ada_check_typedef (r);
+       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 ada_check_typedef (TYPE_TARGET_TYPE (ada_check_typedef (r)));
     }
   return NULL;
 }
@@ -1562,23 +1503,23 @@ desc_bounds (struct value *arr)
   if (is_thin_pntr (type))
     {
       struct type *bounds_type =
-        desc_bounds_type (thin_descriptor_type (type));
+       desc_bounds_type (thin_descriptor_type (type));
       LONGEST addr;
 
       if (bounds_type == NULL)
-        error (_("Bad GNAT array descriptor"));
+       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).  */
+        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);
+       addr = value_as_long (arr);
       else
-        addr = value_address (arr);
+       addr = value_address (arr);
 
       return
-        value_from_longest (lookup_pointer_type (bounds_type),
-                            addr - TYPE_LENGTH (bounds_type));
+       value_from_longest (lookup_pointer_type (bounds_type),
+                           addr - TYPE_LENGTH (bounds_type));
     }
 
   else if (is_thick_pntr (type))
@@ -1666,7 +1607,7 @@ desc_data (struct value *arr)
     return thin_data_pntr (arr);
   else if (is_thick_pntr (type))
     return value_struct_elt (&arr, NULL, "P_ARRAY", NULL,
-                             _("Bad GNAT array descriptor"));
+                            _("Bad GNAT array descriptor"));
   else
     return NULL;
 }
@@ -1706,7 +1647,7 @@ desc_one_bound (struct value *bounds, int i, int which)
   xsnprintf (bound_name, sizeof (bound_name), "%cB%d",
             which ? 'U' : 'L', i - 1);
   return value_struct_elt (&bounds, NULL, bound_name, NULL,
-                           _("Bad GNAT array descriptor bounds"));
+                          _("Bad GNAT array descriptor bounds"));
 }
 
 /* If BOUNDS is an array-bounds structure type, return the bit position
@@ -1776,7 +1717,7 @@ ada_is_direct_array_type (struct type *type)
     return 0;
   type = ada_check_typedef (type);
   return (type->code () == TYPE_CODE_ARRAY
-          || ada_is_array_descriptor_type (type));
+         || ada_is_array_descriptor_type (type));
 }
 
 /* Non-zero iff TYPE represents any kind of array in Ada, or a pointer
@@ -1833,7 +1774,7 @@ ada_is_bogus_array_descriptor (struct type *type)
     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)
+       || lookup_struct_elt_type (type, "P_ARRAY", 1) != NULL)
     && !ada_is_array_descriptor_type (type);
 }
 
@@ -1876,28 +1817,28 @@ ada_type_of_array (struct value *arr, int bounds)
       arity = ada_array_arity (value_type (arr));
 
       if (elt_type == NULL || arity == 0)
-        return ada_check_typedef (value_type (arr));
+       return ada_check_typedef (value_type (arr));
 
       descriptor = desc_bounds (arr);
       if (value_as_long (descriptor) == 0)
-        return NULL;
+       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),
+       {
+         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);
+         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
+                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);
@@ -1905,16 +1846,16 @@ ada_type_of_array (struct value *arr, int bounds)
              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.  */
+                zero, and does not need to be recomputed.  */
              if (lo < hi)
                {
                  int array_bitsize =
-                       (hi - lo + 1) * TYPE_FIELD_BITSIZE (elt_type, 0);
+                       (hi - lo + 1) * TYPE_FIELD_BITSIZE (elt_type, 0);
 
                  TYPE_LENGTH (array_type) = (array_bitsize + 7) / 8;
                }
            }
-        }
+       }
 
       return lookup_pointer_type (elt_type);
     }
@@ -1933,7 +1874,7 @@ ada_coerce_to_simple_array_ptr (struct value *arr)
       struct type *arrType = ada_type_of_array (arr, 1);
 
       if (arrType == NULL)
-        return NULL;
+       return NULL;
       return value_cast (arrType, value_copy (desc_data (arr)));
     }
   else if (ada_is_constrained_packed_array_type (value_type (arr)))
@@ -1954,7 +1895,7 @@ ada_coerce_to_simple_array (struct value *arr)
       struct value *arrVal = ada_coerce_to_simple_array_ptr (arr);
 
       if (arrVal == NULL)
-        error (_("Bounds unavailable for null array pointer."));
+       error (_("Bounds unavailable for null array pointer."));
       ada_ensure_varsize_limit (TYPE_TARGET_TYPE (value_type (arrVal)));
       return value_ind (arrVal);
     }
@@ -1983,7 +1924,7 @@ ada_coerce_to_simple_array_type (struct type *type)
 /* Non-zero iff TYPE represents a standard GNAT packed-array type.  */
 
 static int
-ada_is_packed_array_type  (struct type *type)
+ada_is_gnat_encoded_packed_array_type  (struct type *type)
 {
   if (type == NULL)
     return 0;
@@ -2000,7 +1941,7 @@ ada_is_packed_array_type  (struct type *type)
 int
 ada_is_constrained_packed_array_type (struct type *type)
 {
-  return ada_is_packed_array_type (type)
+  return ada_is_gnat_encoded_packed_array_type (type)
     && !ada_is_array_descriptor_type (type);
 }
 
@@ -2010,8 +1951,37 @@ ada_is_constrained_packed_array_type (struct type *type)
 static int
 ada_is_unconstrained_packed_array_type (struct type *type)
 {
-  return ada_is_packed_array_type (type)
-    && ada_is_array_descriptor_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),
@@ -2038,7 +2008,15 @@ decode_packed_array_bitsize (struct type *type)
     return 0;
 
   tail = strstr (raw_name, "___XP");
-  gdb_assert (tail != NULL);
+  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)
     {
@@ -2097,7 +2075,7 @@ constrained_packed_array_type (struct type *type, long *elt_bits)
 
   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) < 0)
+      || !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;
@@ -2105,7 +2083,7 @@ constrained_packed_array_type (struct type *type, long *elt_bits)
     {
       *elt_bits *= (high_bound - low_bound + 1);
       TYPE_LENGTH (new_type) =
-        (*elt_bits + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
+       (*elt_bits + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
     }
 
   new_type->set_is_fixed_instance (true);
@@ -2157,6 +2135,35 @@ decode_constrained_packed_array_type (struct type *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
@@ -2186,6 +2193,18 @@ decode_constrained_packed_array (struct value *arr)
       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)))
     {
@@ -2233,36 +2252,36 @@ value_subscript_packed (struct value *arr, int arity, struct value **ind)
   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 "
+         || 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) < 0)
-            {
-              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"),
+       {
+         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));
-        }
+         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);
+                                     bits, elt_type);
   return v;
 }
 
@@ -2307,7 +2326,7 @@ ada_unpack_from_contents (const gdb_byte *src, int bit_offset, int bit_size,
   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 */
+                                  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.  */
@@ -2336,26 +2355,26 @@ ada_unpack_from_contents (const gdb_byte *src, int bit_offset, int bit_size,
       src_idx = src_len - 1;
       if (is_signed_type
          && ((src[0] << bit_offset) & (1 << (HOST_CHAR_BIT - 1))))
-        sign = ~0;
+       sign = ~0;
 
       unusedLS =
-        (HOST_CHAR_BIT - (bit_size + bit_offset) % HOST_CHAR_BIT)
-        % HOST_CHAR_BIT;
+       (HOST_CHAR_BIT - (bit_size + bit_offset) % HOST_CHAR_BIT)
+       % HOST_CHAR_BIT;
 
       if (is_scalar)
        {
-          accumSize = 0;
-          unpacked_idx = unpacked_len - 1;
+         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;
+         /* 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
@@ -2367,31 +2386,31 @@ ada_unpack_from_contents (const gdb_byte *src, int bit_offset, int bit_size,
       accumSize = 0;
 
       if (is_signed_type && (src[src_len - 1] & (1 << sign_bit_offset)))
-        sign = ~0;
+       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.  */
+        part of the value.  */
       unsigned int unusedMSMask =
-        (1 << (srcBitsLeft >= HOST_CHAR_BIT ? HOST_CHAR_BIT : srcBitsLeft)) -
-        1;
+       (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;
+       (((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;
-        }
+       {
+         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;
@@ -2422,7 +2441,7 @@ ada_unpack_from_contents (const gdb_byte *src, int bit_offset, int bit_size,
 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 type *type)
 {
   struct value *v;
   const gdb_byte *src;                /* First byte containing data to unpack */
@@ -2451,7 +2470,7 @@ ada_value_primitive_packed_val (struct value *obj, const gdb_byte *valaddr,
       staging.resize (staging_len);
 
       ada_unpack_from_contents (src, bit_offset, bit_size,
-                               staging.data (), staging.size (),
+                               staging.data (), staging.size (),
                                is_big_endian, has_negatives (type),
                                is_scalar);
       type = resolve_dynamic_type (type, staging, 0);
@@ -2497,10 +2516,10 @@ ada_value_primitive_packed_val (struct value *obj, const gdb_byte *valaddr,
       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_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
@@ -2557,7 +2576,7 @@ ada_value_assign (struct value *toval, struct value *fromval)
   if (VALUE_LVAL (toval) == lval_memory
       && bits > 0
       && (type->code () == TYPE_CODE_FLT
-          || type->code () == TYPE_CODE_STRUCT))
+         || type->code () == TYPE_CODE_STRUCT))
     {
       int len = (value_bitpos (toval)
                 + bits + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT;
@@ -2567,7 +2586,7 @@ ada_value_assign (struct value *toval, struct value *fromval)
       CORE_ADDR to_addr = value_address (toval);
 
       if (type->code () == TYPE_CODE_FLT)
-        fromval = value_cast (type, fromval);
+       fromval = value_cast (type, fromval);
 
       read_memory (to_addr, buffer, len);
       from_size = value_bitsize (fromval);
@@ -2585,7 +2604,7 @@ ada_value_assign (struct value *toval, struct value *fromval)
 
       val = value_copy (toval);
       memcpy (value_contents_raw (val), value_contents (fromval),
-              TYPE_LENGTH (type));
+             TYPE_LENGTH (type));
       deprecated_set_value_type (val, type);
 
       return val;
@@ -2628,7 +2647,7 @@ value_assign_to_component (struct value *container, struct value *component,
       int src_offset;
 
       if (is_scalar_type (check_typedef (value_type (component))))
-        src_offset
+       src_offset
          = TYPE_LENGTH (value_type (component)) * TARGET_CHAR_BIT - bits;
       else
        src_offset = 0;
@@ -2674,7 +2693,7 @@ ada_value_subscript (struct value *arr, int arity, struct value **ind)
       struct type *saved_elt_type = TYPE_TARGET_TYPE (elt_type);
 
       if (elt_type->code () != TYPE_CODE_ARRAY)
-        error (_("too many subscripts (%d expected)"), k);
+       error (_("too many subscripts (%d expected)"), k);
 
       elt = value_subscript (elt, pos_atr (ind[k]));
 
@@ -2731,9 +2750,9 @@ ada_value_ptr_subscript (struct value *arr, int arity, struct value **ind)
       LONGEST lwb, upb;
 
       if (type->code () != TYPE_CODE_ARRAY)
-        error (_("too many subscripts (%d expected)"), k);
+       error (_("too many subscripts (%d expected)"), k);
       arr = value_cast (lookup_pointer_type (TYPE_TARGET_TYPE (type)),
-                        value_copy (arr));
+                       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);
@@ -2748,7 +2767,7 @@ ada_value_ptr_subscript (struct value *arr, int arity, struct value **ind)
    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)
+                         int low, int high)
 {
   struct type *type0 = ada_check_typedef (type);
   struct type *base_index_type = TYPE_TARGET_TYPE (type0->index_type ());
@@ -2759,20 +2778,24 @@ ada_value_slice_from_ptr (struct value *array_ptr, struct type *type,
                               type0->dyn_prop (DYN_PROP_BYTE_STRIDE),
                               TYPE_FIELD_BITSIZE (type0, 0));
   int base_low =  ada_discrete_type_low_bound (type0->index_type ());
-  LONGEST base_low_pos, low_pos;
+  gdb::optional<LONGEST> base_low_pos, low_pos;
   CORE_ADDR base;
 
-  if (!discrete_position (base_index_type, low, &low_pos)
-      || !discrete_position (base_index_type, base_low, &base_low_pos))
+  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;
     }
 
-  base = value_as_address (array_ptr)
-    + ((low_pos - base_low_pos)
-       * TYPE_LENGTH (TYPE_TARGET_TYPE (type0)));
+  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);
 }
 
@@ -2788,10 +2811,13 @@ ada_value_slice (struct value *array, int low, int high)
                              (NULL, TYPE_TARGET_TYPE (type), index_type,
                               type->dyn_prop (DYN_PROP_BYTE_STRIDE),
                               TYPE_FIELD_BITSIZE (type, 0));
-  LONGEST low_pos, high_pos;
+  gdb::optional<LONGEST> low_pos, high_pos;
+
 
-  if (!discrete_position (base_index_type, low, &low_pos)
-      || !discrete_position (base_index_type, high, &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;
@@ -2799,7 +2825,7 @@ ada_value_slice (struct value *array, int low, int high)
     }
 
   return value_cast (slice_type,
-                    value_slice (array, low, high_pos - low_pos + 1));
+                    value_slice (array, low, *high_pos - *low_pos + 1));
 }
 
 /* If type is a record type in the form of a standard GNAT array
@@ -2823,8 +2849,8 @@ ada_array_arity (struct type *type)
   else
     while (type->code () == TYPE_CODE_ARRAY)
       {
-        arity += 1;
-        type = ada_check_typedef (TYPE_TARGET_TYPE (type));
+       arity += 1;
+       type = ada_check_typedef (TYPE_TARGET_TYPE (type));
       }
 
   return arity;
@@ -2849,25 +2875,25 @@ ada_array_element_type (struct type *type, int nindices)
 
       k = ada_array_arity (type);
       if (k == 0)
-        return NULL;
+       return NULL;
 
       /* Initially p_array_type = elt_type(*)[]...(k times)...[].  */
       if (nindices >= 0 && k > nindices)
-        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;
-        }
+       {
+         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;
-        }
+       {
+         type = TYPE_TARGET_TYPE (type);
+         nindices -= 1;
+       }
       return type;
     }
 
@@ -2895,13 +2921,13 @@ ada_index_type (struct type *type, int n, const char *name)
       int i;
 
       for (i = 1; i < n; i += 1)
-        type = TYPE_TARGET_TYPE (type);
+       type = TYPE_TARGET_TYPE (type);
       result_type = TYPE_TARGET_TYPE (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.  */
+        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;
+       result_type = NULL;
     }
   else
     {
@@ -2966,8 +2992,8 @@ ada_array_bound_from_type (struct type *arr_type, int n, int which)
 
   return
     (LONGEST) (which == 0
-               ? ada_discrete_type_low_bound (index_type)
-               : ada_discrete_type_high_bound (index_type));
+              ? 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
@@ -3048,7 +3074,7 @@ 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,
+       (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);
 
@@ -3056,7 +3082,7 @@ empty_array (struct type *arr_type, int low, int high)
 }
 \f
 
-                                /* Name resolution */
+                               /* Name resolution */
 
 /* The "decoded" name for the user-definable Ada operator corresponding
    to OP.  */
@@ -3069,7 +3095,7 @@ ada_decoded_op_name (enum exp_opcode op)
   for (i = 0; ada_opname_table[i].encoded != NULL; i += 1)
     {
       if (ada_opname_table[i].op == op)
-        return ada_opname_table[i].decoded;
+       return ada_opname_table[i].decoded;
     }
   error (_("Could not find operator name for opcode"));
 }
@@ -3092,23 +3118,23 @@ encoded_ordered_before (const char *N0, const char *N1)
       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));
-        }
+         && (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);
     }
 }
@@ -3127,12 +3153,12 @@ sort_choices (struct block_symbol syms[], int nsyms)
       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];
-        }
+       {
+         if (encoded_ordered_before (syms[j].symbol->linkage_name (),
+                                     sym.symbol->linkage_name ()))
+           break;
+         syms[j + 1] = syms[j];
+       }
       syms[j + 1] = sym;
     }
 }
@@ -3198,7 +3224,7 @@ ada_print_symbol_signature (struct ui_file *stream, struct symbol *sym,
 
 static int
 get_selections (int *choices, int n_choices, int max_results,
-                int is_all_choice, const char *annotation_suffix)
+               int is_all_choice, const char *annotation_suffix)
 {
   const char *args;
   const char *prompt;
@@ -3225,41 +3251,41 @@ get_selections (int *choices, int n_choices, int max_results,
 
       args = skip_spaces (args);
       if (*args == '\0' && n_chosen == 0)
-        error_no_arg (_("one or more choice numbers"));
+       error_no_arg (_("one or more choice numbers"));
       else if (*args == '\0')
-        break;
+       break;
 
       choice = strtol (args, &args2, 10);
       if (args == args2 || choice < 0
-          || choice > n_choices + first_choice - 1)
-        error (_("Argument must be choice number"));
+         || choice > n_choices + first_choice - 1)
+       error (_("Argument must be choice number"));
       args = args2;
 
       if (choice == 0)
-        error (_("cancelled"));
+       error (_("cancelled"));
 
       if (choice < first_choice)
-        {
-          n_chosen = n_choices;
-          for (j = 0; j < n_choices; j += 1)
-            choices[j] = j;
-          break;
-        }
+       {
+         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;
+       {
+         int k;
 
-          for (k = n_chosen - 1; k > j; k -= 1)
-            choices[k + 1] = choices[k];
-          choices[j + 1] = choice;
-          n_chosen += 1;
-        }
+         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)
@@ -3310,12 +3336,12 @@ See set/show multiple-symbol."));
   for (i = 0; i < nsyms; i += 1)
     {
       if (syms[i].symbol == NULL)
-        continue;
+       continue;
 
       if (SYMBOL_CLASS (syms[i].symbol) == LOC_BLOCK)
-        {
-          struct symtab_and_line sal =
-            find_function_start_sal (syms[i].symbol, 1);
+       {
+         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,
@@ -3329,20 +3355,20 @@ See set/show multiple-symbol."));
               styled_string (file_name_style.style (),
                              symtab_to_filename_for_display (sal.symtab)),
               sal.line);
-          continue;
-        }
+         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);
+       {
+         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)
+         if (SYMBOL_LINE (syms[i].symbol) != 0 && symtab != NULL)
            {
              printf_filtered ("[%d] ", i + first_choice);
              ada_print_symbol_signature (gdb_stdout, syms[i].symbol,
@@ -3351,15 +3377,15 @@ See set/show multiple-symbol."));
                               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"),
+         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);
@@ -3376,11 +3402,11 @@ See set/show multiple-symbol."));
                                 ? _(" (enumeral)\n")
                                 : _(" at ?\n"));
            }
-        }
+       }
     }
 
   n_chosen = get_selections (chosen, nsyms, max_results, max_results > 1,
-                             "overload-choice");
+                            "overload-choice");
 
   for (i = 0; i < n_chosen; i += 1)
     syms[i] = syms[chosen[i]];
@@ -3388,6 +3414,126 @@ See set/show multiple-symbol."));
   return n_chosen;
 }
 
+/* See ada-lang.h.  */
+
+block_symbol
+ada_find_operator_symbol (enum exp_opcode op, int 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,
+                    int 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];
+}
+
+/* See ada-lang.h.  */
+
+block_symbol
+ada_resolve_variable (struct symbol *sym, const struct block *block,
+                     struct type *context_type,
+                     int 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 ());
+    }
+
+  int i;
+  if (candidates.empty ())
+    error (_("No definition found for %s"), sym->print_name ());
+  else if (candidates.size () == 1)
+    i = 0;
+  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];
+}
+
 /* Resolve the operator of the subexpression beginning at
    position *POS of *EXPP.  "Resolving" consists of replacing
    the symbols that have undefined namespaces in OP_VAR_VALUE nodes
@@ -3399,7 +3545,7 @@ See set/show multiple-symbol."));
 
 static struct value *
 resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
-                struct type *context_type, int parse_completion,
+               struct type *context_type, int parse_completion,
                innermost_block_tracker *tracker)
 {
   int pc = *pos;
@@ -3409,6 +3555,12 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
   struct value **argvec;        /* Vector of operand types (alloca'ed).  */
   int nargs;                    /* Number of operands.  */
   int oplen;
+  /* If we're resolving an expression like ARRAY(ARG...), then we set
+     this to the type of the array, so we can use the index types as
+     the expected types for resolution.  */
+  struct type *array_type = nullptr;
+  /* The arity of ARRAY_TYPE.  */
+  int array_arity = 0;
 
   argvec = NULL;
   nargs = 0;
@@ -3420,13 +3572,18 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
     {
     case OP_FUNCALL:
       if (exp->elts[pc + 3].opcode == OP_VAR_VALUE
-          && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
-        *pos += 7;
+         && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
+       *pos += 7;
       else
-        {
-          *pos += 3;
-          resolve_subexp (expp, pos, 0, NULL, parse_completion, tracker);
-        }
+       {
+         *pos += 3;
+         struct value *lhs = resolve_subexp (expp, pos, 0, NULL,
+                                             parse_completion, tracker);
+         struct type *lhstype = ada_check_typedef (value_type (lhs));
+         array_arity = ada_array_arity (lhstype);
+         if (array_arity > 0)
+           array_type = lhstype;
+       }
       nargs = longest_to_int (exp->elts[pc + 1].longconst);
       break;
 
@@ -3466,16 +3623,16 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
 
     case BINOP_ASSIGN:
       {
-        struct value *arg1;
-
-        *pos += 1;
-        arg1 = resolve_subexp (expp, pos, 0, NULL, parse_completion, tracker);
-        if (arg1 == NULL)
-          resolve_subexp (expp, pos, 1, NULL, parse_completion, tracker);
-        else
-          resolve_subexp (expp, pos, 1, value_type (arg1), parse_completion,
+       struct value *arg1;
+
+       *pos += 1;
+       arg1 = resolve_subexp (expp, pos, 0, NULL, parse_completion, tracker);
+       if (arg1 == NULL)
+         resolve_subexp (expp, pos, 1, NULL, parse_completion, tracker);
+       else
+         resolve_subexp (expp, pos, 1, value_type (arg1), parse_completion,
                          tracker);
-        break;
+       break;
       }
 
     case UNOP_CAST:
@@ -3562,8 +3719,13 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
 
   argvec = XALLOCAVEC (struct value *, nargs + 1);
   for (i = 0; i < nargs; i += 1)
-    argvec[i] = resolve_subexp (expp, pos, 1, NULL, parse_completion,
-                               tracker);
+    {
+      struct type *subtype = nullptr;
+      if (i < array_arity)
+       subtype = ada_index_type (array_type, i + 1, "array type");
+      argvec[i] = resolve_subexp (expp, pos, 1, subtype, parse_completion,
+                                 tracker);
+    }
   argvec[i] = NULL;
   exp = expp->get ();
 
@@ -3575,122 +3737,41 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
 
     case OP_VAR_VALUE:
       if (SYMBOL_DOMAIN (exp->elts[pc + 2].symbol) == UNDEF_DOMAIN)
-        {
-          std::vector<struct block_symbol> candidates;
-          int n_candidates;
-
-          n_candidates =
-            ada_lookup_symbol_list (exp->elts[pc + 2].symbol->linkage_name (),
-                                    exp->elts[pc + 1].block, VAR_DOMAIN,
-                                    &candidates);
-
-          if (n_candidates > 1)
-            {
-              /* Types tend to get re-introduced locally, so if there
-                 are any local symbols that are not types, first filter
-                 out all types.  */
-              int j;
-              for (j = 0; j < n_candidates; j += 1)
-                switch (SYMBOL_CLASS (candidates[j].symbol))
-                  {
-                  case LOC_REGISTER:
-                  case LOC_ARG:
-                  case LOC_REF_ARG:
-                  case LOC_REGPARM_ADDR:
-                  case LOC_LOCAL:
-                  case LOC_COMPUTED:
-                    goto FoundNonType;
-                  default:
-                    break;
-                  }
-            FoundNonType:
-              if (j < n_candidates)
-                {
-                  j = 0;
-                  while (j < n_candidates)
-                    {
-                      if (SYMBOL_CLASS (candidates[j].symbol) == LOC_TYPEDEF)
-                        {
-                          candidates[j] = candidates[n_candidates - 1];
-                          n_candidates -= 1;
-                        }
-                      else
-                        j += 1;
-                    }
-                }
-            }
-
-          if (n_candidates == 0)
-            error (_("No definition found for %s"),
-                   exp->elts[pc + 2].symbol->print_name ());
-          else if (n_candidates == 1)
-            i = 0;
-          else if (deprocedure_p
-                   && !is_nonfunction (candidates.data (), n_candidates))
-            {
-              i = ada_resolve_function
-                (candidates.data (), n_candidates, NULL, 0,
-                 exp->elts[pc + 2].symbol->linkage_name (),
-                 context_type, parse_completion);
-              if (i < 0)
-                error (_("Could not find a match for %s"),
-                       exp->elts[pc + 2].symbol->print_name ());
-            }
-          else
-            {
-              printf_filtered (_("Multiple matches for %s\n"),
-                               exp->elts[pc + 2].symbol->print_name ());
-              user_select_syms (candidates.data (), n_candidates, 1);
-              i = 0;
-            }
-
-          exp->elts[pc + 1].block = candidates[i].block;
-          exp->elts[pc + 2].symbol = candidates[i].symbol;
-         tracker->update (candidates[i]);
-        }
+       {
+         block_symbol resolved
+           = ada_resolve_variable (exp->elts[pc + 2].symbol,
+                                   exp->elts[pc + 1].block,
+                                   context_type, parse_completion,
+                                   deprocedure_p, tracker);
+         exp->elts[pc + 1].block = resolved.block;
+         exp->elts[pc + 2].symbol = resolved.symbol;
+       }
 
       if (deprocedure_p
-          && (SYMBOL_TYPE (exp->elts[pc + 2].symbol)->code ()
-              == TYPE_CODE_FUNC))
-        {
-          replace_operator_with_call (expp, pc, 0, 4,
-                                      exp->elts[pc + 2].symbol,
-                                      exp->elts[pc + 1].block);
-          exp = expp->get ();
-        }
+         && (SYMBOL_TYPE (exp->elts[pc + 2].symbol)->code ()
+             == TYPE_CODE_FUNC))
+       {
+         replace_operator_with_call (expp, pc, 0, 4,
+                                     exp->elts[pc + 2].symbol,
+                                     exp->elts[pc + 1].block);
+         exp = expp->get ();
+       }
       break;
 
     case OP_FUNCALL:
       {
-        if (exp->elts[pc + 3].opcode == OP_VAR_VALUE
-            && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
-          {
-           std::vector<struct block_symbol> candidates;
-            int n_candidates;
-
-            n_candidates =
-              ada_lookup_symbol_list (exp->elts[pc + 5].symbol->linkage_name (),
-                                      exp->elts[pc + 4].block, VAR_DOMAIN,
-                                      &candidates);
-
-            if (n_candidates == 1)
-              i = 0;
-            else
-              {
-                i = ada_resolve_function
-                  (candidates.data (), n_candidates,
-                   argvec, nargs,
-                   exp->elts[pc + 5].symbol->linkage_name (),
-                   context_type, parse_completion);
-                if (i < 0)
-                  error (_("Could not find a match for %s"),
-                         exp->elts[pc + 5].symbol->print_name ());
-              }
-
-            exp->elts[pc + 4].block = candidates[i].block;
-            exp->elts[pc + 5].symbol = candidates[i].symbol;
-           tracker->update (candidates[i]);
-          }
+       if (exp->elts[pc + 3].opcode == OP_VAR_VALUE
+           && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
+         {
+           block_symbol resolved
+             = ada_resolve_funcall (exp->elts[pc + 5].symbol,
+                                    exp->elts[pc + 4].block,
+                                    context_type, parse_completion,
+                                    nargs, argvec,
+                                    tracker);
+           exp->elts[pc + 4].block = resolved.block;
+           exp->elts[pc + 5].symbol = resolved.symbol;
+         }
       }
       break;
     case BINOP_ADD:
@@ -3714,27 +3795,16 @@ resolve_subexp (expression_up *expp, int *pos, int deprocedure_p,
     case UNOP_PLUS:
     case UNOP_LOGICAL_NOT:
     case UNOP_ABS:
-      if (possible_user_operator_p (op, argvec))
-        {
-         std::vector<struct block_symbol> candidates;
-          int n_candidates;
-
-          n_candidates =
-            ada_lookup_symbol_list (ada_decoded_op_name (op),
-                                   NULL, VAR_DOMAIN,
-                                    &candidates);
+      {
+       block_symbol found = ada_find_operator_symbol (op, parse_completion,
+                                                      nargs, argvec);
+       if (found.symbol == nullptr)
+         break;
 
-          i = ada_resolve_function (candidates.data (), n_candidates, argvec,
-                                   nargs, ada_decoded_op_name (op), NULL,
-                                   parse_completion);
-          if (i < 0)
-            break;
-
-         replace_operator_with_call (expp, pc, nargs, 1,
-                                     candidates[i].symbol,
-                                     candidates[i].block);
-          exp = expp->get ();
-        }
+       replace_operator_with_call (expp, pc, nargs, 1,
+                                   found.symbol, found.block);
+       exp = expp->get ();
+      }
       break;
 
     case OP_TYPE:
@@ -3774,35 +3844,35 @@ ada_type_match (struct type *ftype, struct type *atype, int may_deref)
       return ftype->code () == atype->code ();
     case TYPE_CODE_PTR:
       if (atype->code () == TYPE_CODE_PTR)
-        return ada_type_match (TYPE_TARGET_TYPE (ftype),
-                               TYPE_TARGET_TYPE (atype), 0);
+       return ada_type_match (TYPE_TARGET_TYPE (ftype),
+                              TYPE_TARGET_TYPE (atype), 0);
       else
-        return (may_deref
-                && ada_type_match (TYPE_TARGET_TYPE (ftype), atype, 0));
+       return (may_deref
+               && ada_type_match (TYPE_TARGET_TYPE (ftype), atype, 0));
     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_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));
+             || 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));
+       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));
+       return (atype->code () == TYPE_CODE_STRUCT
+               && !ada_is_array_descriptor_type (atype));
 
     case TYPE_CODE_UNION:
     case TYPE_CODE_FLT:
@@ -3833,15 +3903,15 @@ ada_args_match (struct symbol *func, struct value **actuals, int n_actuals)
   for (i = 0; i < n_actuals; i += 1)
     {
       if (actuals[i] == NULL)
-        return 0;
+       return 0;
       else
-        {
-          struct type *ftype = ada_check_typedef (func_type->field (i).type ());
-          struct type *atype = ada_check_typedef (value_type (actuals[i]));
+       {
+         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, 1))
-            return 0;
-        }
+         if (!ada_type_match (ftype, atype, 1))
+           return 0;
+       }
     }
   return 1;
 }
@@ -3877,7 +3947,7 @@ return_match (struct type *func_type, struct type *context_type)
 }
 
 
-/* Returns the index in SYMS[0..NSYMS-1] that contains  the symbol for the
+/* 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
@@ -3890,9 +3960,9 @@ return_match (struct type *func_type, struct type *context_type)
    the process; the index returned is for the modified vector.  */
 
 static int
-ada_resolve_function (struct block_symbol syms[],
-                      int nsyms, struct value **args, int nargs,
-                      const char *name, struct type *context_type,
+ada_resolve_function (std::vector<struct block_symbol> &syms,
+                     struct value **args, int nargs,
+                     const char *name, struct type *context_type,
                      int parse_completion)
 {
   int fallback;
@@ -3905,17 +3975,17 @@ ada_resolve_function (struct block_symbol syms[],
      where every function is accepted.  */
   for (fallback = 0; m == 0 && fallback < 2; fallback++)
     {
-      for (k = 0; k < nsyms; k += 1)
-        {
-          struct type *type = ada_check_typedef (SYMBOL_TYPE (syms[k].symbol));
+      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 (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
@@ -3927,7 +3997,7 @@ ada_resolve_function (struct block_symbol syms[],
   else if (m > 1 && !parse_completion)
     {
       printf_filtered (_("Multiple matches for %s\n"), name);
-      user_select_syms (syms, m, 1);
+      user_select_syms (syms.data (), m, 1);
       return 0;
     }
   return 0;
@@ -3939,31 +4009,30 @@ ada_resolve_function (struct block_symbol syms[],
 
 static void
 replace_operator_with_call (expression_up *expp, int pc, int nargs,
-                            int oplen, struct symbol *sym,
-                            const struct block *block)
-{
-  /* A new expression, with 6 more elements (3 for funcall, 4 for function
-     symbol, -oplen for operator being replaced).  */
-  struct expression *newexp = (struct expression *)
-    xzalloc (sizeof (struct expression)
-             + EXP_ELEM_TO_BYTES ((*expp)->nelts + 7 - oplen));
+                           int oplen, struct symbol *sym,
+                           const struct block *block)
+{
+  /* We want to add 6 more elements (3 for funcall, 4 for function
+     symbol, -OPLEN for operator being replaced) to the
+     expression.  */
   struct expression *exp = expp->get ();
+  int save_nelts = exp->nelts;
+  int extra_elts = 7 - oplen;
+  exp->nelts += extra_elts;
 
-  newexp->nelts = exp->nelts + 7 - oplen;
-  newexp->language_defn = exp->language_defn;
-  newexp->gdbarch = exp->gdbarch;
-  memcpy (newexp->elts, exp->elts, EXP_ELEM_TO_BYTES (pc));
-  memcpy (newexp->elts + pc + 7, exp->elts + pc + oplen,
-          EXP_ELEM_TO_BYTES (exp->nelts - pc - oplen));
+  if (extra_elts > 0)
+    exp->resize (exp->nelts);
+  memmove (exp->elts + pc + 7, exp->elts + pc + oplen,
+          EXP_ELEM_TO_BYTES (save_nelts - pc - oplen));
+  if (extra_elts < 0)
+    exp->resize (exp->nelts);
 
-  newexp->elts[pc].opcode = newexp->elts[pc + 2].opcode = OP_FUNCALL;
-  newexp->elts[pc + 1].longconst = (LONGEST) nargs;
+  exp->elts[pc].opcode = exp->elts[pc + 2].opcode = OP_FUNCALL;
+  exp->elts[pc + 1].longconst = (LONGEST) nargs;
 
-  newexp->elts[pc + 3].opcode = newexp->elts[pc + 6].opcode = OP_VAR_VALUE;
-  newexp->elts[pc + 4].block = block;
-  newexp->elts[pc + 5].symbol = sym;
-
-  expp->reset (newexp);
+  exp->elts[pc + 3].opcode = exp->elts[pc + 6].opcode = OP_VAR_VALUE;
+  exp->elts[pc + 4].block = block;
+  exp->elts[pc + 5].symbol = sym;
 }
 
 /* Type-class predicates */
@@ -3979,16 +4048,16 @@ numeric_type_p (struct type *type)
   else
     {
       switch (type->code ())
-        {
-        case TYPE_CODE_INT:
-        case TYPE_CODE_FLT:
-          return 1;
-        case TYPE_CODE_RANGE:
-          return (type == TYPE_TARGET_TYPE (type)
-                  || numeric_type_p (TYPE_TARGET_TYPE (type)));
-        default:
-          return 0;
-        }
+       {
+       case TYPE_CODE_INT:
+       case TYPE_CODE_FLT:
+         return 1;
+       case TYPE_CODE_RANGE:
+         return (type == TYPE_TARGET_TYPE (type)
+                 || numeric_type_p (TYPE_TARGET_TYPE (type)));
+       default:
+         return 0;
+       }
     }
 }
 
@@ -4002,15 +4071,15 @@ integer_type_p (struct type *type)
   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;
-        }
+       {
+       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;
+       }
     }
 }
 
@@ -4024,15 +4093,15 @@ scalar_type_p (struct type *type)
   else
     {
       switch (type->code ())
-        {
-        case TYPE_CODE_INT:
-        case TYPE_CODE_RANGE:
-        case TYPE_CODE_ENUM:
-        case TYPE_CODE_FLT:
-          return 1;
-        default:
-          return 0;
-        }
+       {
+       case TYPE_CODE_INT:
+       case TYPE_CODE_RANGE:
+       case TYPE_CODE_ENUM:
+       case TYPE_CODE_FLT:
+         return 1;
+       default:
+         return 0;
+       }
     }
 }
 
@@ -4046,15 +4115,15 @@ discrete_type_p (struct type *type)
   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;
-        }
+       {
+       case TYPE_CODE_INT:
+       case TYPE_CODE_RANGE:
+       case TYPE_CODE_ENUM:
+       case TYPE_CODE_BOOL:
+         return 1;
+       default:
+         return 0;
+       }
     }
 }
 
@@ -4114,7 +4183,7 @@ possible_user_operator_p (enum exp_opcode op, struct value *args[])
     }
 }
 \f
-                                /* Renaming */
+                               /* Renaming */
 
 /* NOTES: 
 
@@ -4221,7 +4290,7 @@ ada_read_renaming_var_value (struct symbol *renaming_sym,
 }
 \f
 
-                                /* Evaluation: Function Calls */
+                               /* 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
@@ -4235,7 +4304,7 @@ ensure_lval (struct value *val)
     {
       int len = TYPE_LENGTH (ada_check_typedef (value_type (val)));
       const CORE_ADDR addr =
-        value_as_long (value_allocate_space_in_inferior (len));
+       value_as_long (value_allocate_space_in_inferior (len));
 
       VALUE_LVAL (val) = lval_memory;
       set_value_address (val, addr);
@@ -4273,10 +4342,10 @@ ada_value_struct_elt (struct value *arg, const char *name, int no_err)
        goto BadValue;
       t1 = ada_check_typedef (t1);
       if (t1->code () == TYPE_CODE_PTR)
-        {
-          arg = coerce_ref (arg);
-          t = t1;
-        }
+       {
+         arg = coerce_ref (arg);
+         t = t1;
+       }
     }
 
   while (t->code () == TYPE_CODE_PTR)
@@ -4286,12 +4355,12 @@ ada_value_struct_elt (struct value *arg, const char *name, int no_err)
        goto BadValue;
       t1 = ada_check_typedef (t1);
       if (t1->code () == TYPE_CODE_PTR)
-        {
-          arg = value_ind (arg);
-          t = t1;
-        }
+       {
+         arg = value_ind (arg);
+         t = t1;
+       }
       else
-        break;
+       break;
     }
 
   if (t1->code () != TYPE_CODE_STRUCT && t1->code () != TYPE_CODE_UNION)
@@ -4311,25 +4380,25 @@ ada_value_struct_elt (struct value *arg, const char *name, int no_err)
        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.  */
+        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.
+         || (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))
+         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;
 
@@ -4338,23 +4407,27 @@ ada_value_struct_elt (struct value *arg, const char *name, int no_err)
       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);
-        }
+                            &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)
@@ -4396,23 +4469,23 @@ ada_convert_actual (struct value *actual, struct type *formal_type0)
       struct value *result;
 
       if (formal_target->code () == TYPE_CODE_ARRAY
-          && ada_is_array_descriptor_type (actual_target))
+         && 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);
-        }
+       {
+         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);
@@ -4441,13 +4514,12 @@ ada_convert_actual (struct value *actual, struct type *formal_type0)
 static CORE_ADDR
 value_pointer (struct value *value, struct type *type)
 {
-  struct gdbarch *gdbarch = get_type_arch (type);
   unsigned len = TYPE_LENGTH (type);
   gdb_byte *buf = (gdb_byte *) alloca (len);
   CORE_ADDR addr;
 
   addr = value_address (value);
-  gdbarch_address_to_pointer (gdbarch, type, buf, addr);
+  gdbarch_address_to_pointer (type->arch (), type, buf, addr);
   addr = extract_unsigned_integer (buf, len, type_byte_order (type));
   return addr;
 }
@@ -4505,7 +4577,7 @@ make_array_descriptor (struct type *type, struct value *arr)
     return descriptor;
 }
 \f
-                                /* Symbol Cache Module */
+                               /* Symbol Cache Module */
 
 /* Performance measurements made as of 2010-01-15 indicate that
    this cache does bring some noticeable improvements.  Depending
@@ -4517,24 +4589,6 @@ make_array_descriptor (struct type *type, struct value *arr)
    even in this case, some expensive name-based symbol searches are still
    sometimes necessary - to find an XVZ variable, mostly.  */
 
-/* Initialize the contents of SYM_CACHE.  */
-
-static void
-ada_init_symbol_cache (struct ada_symbol_cache *sym_cache)
-{
-  obstack_init (&sym_cache->cache_space);
-  memset (sym_cache->root, '\000', sizeof (sym_cache->root));
-}
-
-/* Free the memory used by SYM_CACHE.  */
-
-static void
-ada_free_symbol_cache (struct ada_symbol_cache *sym_cache)
-{
-  obstack_free (&sym_cache->cache_space, NULL);
-  xfree (sym_cache);
-}
-
 /* Return the symbol cache associated to the given program space PSPACE.
    If not allocated for this PSPACE yet, allocate and initialize one.  */
 
@@ -4543,25 +4597,22 @@ ada_get_symbol_cache (struct program_space *pspace)
 {
   struct ada_pspace_data *pspace_data = get_ada_pspace_data (pspace);
 
-  if (pspace_data->sym_cache == NULL)
-    {
-      pspace_data->sym_cache = XCNEW (struct ada_symbol_cache);
-      ada_init_symbol_cache (pspace_data->sym_cache);
-    }
+  if (pspace_data->sym_cache == nullptr)
+    pspace_data->sym_cache.reset (new ada_symbol_cache);
 
-  return pspace_data->sym_cache;
+  return pspace_data->sym_cache.get ();
 }
 
 /* Clear all entries from the symbol cache.  */
 
 static void
-ada_clear_symbol_cache (void)
+ada_clear_symbol_cache ()
 {
-  struct ada_symbol_cache *sym_cache
-    = ada_get_symbol_cache (current_program_space);
+  struct ada_pspace_data *pspace_data
+    = get_ada_pspace_data (current_program_space);
 
-  obstack_free (&sym_cache->cache_space, NULL);
-  ada_init_symbol_cache (sym_cache);
+  if (pspace_data->sym_cache != nullptr)
+    pspace_data->sym_cache.reset ();
 }
 
 /* Search our cache for an entry matching NAME and DOMAIN.
@@ -4578,7 +4629,7 @@ find_entry (const char *name, domain_enum domain)
   for (e = &sym_cache->root[h]; *e != NULL; e = &(*e)->next)
     {
       if (domain == (*e)->domain && strcmp (name, (*e)->name) == 0)
-        return e;
+       return e;
     }
   return NULL;
 }
@@ -4591,7 +4642,7 @@ find_entry (const char *name, domain_enum domain)
 
 static int
 lookup_cached_symbol (const char *name, domain_enum domain,
-                      struct symbol **sym, const struct block **block)
+                     struct symbol **sym, const struct block **block)
 {
   struct cache_entry **e = find_entry (name, domain);
 
@@ -4609,7 +4660,7 @@ lookup_cached_symbol (const char *name, domain_enum domain,
 
 static void
 cache_symbol (const char *name, domain_enum domain, struct symbol *sym,
-              const struct block *block)
+             const struct block *block)
 {
   struct ada_symbol_cache *sym_cache
     = ada_get_symbol_cache (current_program_space);
@@ -4642,7 +4693,7 @@ cache_symbol (const char *name, domain_enum domain, struct symbol *sym,
   e->block = block;
 }
 \f
-                                /* Symbol Lookup */
+                               /* Symbol Lookup */
 
 /* Return the symbol name match type that should be used used when
    searching for all symbols matching LOOKUP_NAME.
@@ -4663,7 +4714,7 @@ name_match_type_from_name (const char *lookup_name)
 
 static struct symbol *
 standard_lookup (const char *name, const struct block *block,
-                 domain_enum domain)
+                domain_enum domain)
 {
   /* Initialize it just to avoid a GCC false warning.  */
   struct block_symbol sym = {};
@@ -4677,17 +4728,15 @@ standard_lookup (const char *name, const struct block *block,
 
 
 /* Non-zero iff there is at least one non-function/non-enumeral symbol
-   in the symbol fields of SYMS[0..N-1].  We treat enumerals as functions, 
+   in the symbol fields of SYMS.  We treat enumerals as functions, 
    since they contend in overloading in the same way.  */
 static int
-is_nonfunction (struct block_symbol syms[], int n)
+is_nonfunction (const std::vector<struct block_symbol> &syms)
 {
-  int i;
-
-  for (i = 0; i < n; i += 1)
-    if (SYMBOL_TYPE (syms[i].symbol)->code () != TYPE_CODE_FUNC
-        && (SYMBOL_TYPE (syms[i].symbol)->code () != TYPE_CODE_ENUM
-            || SYMBOL_CLASS (syms[i].symbol) != LOC_CONST))
+  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;
@@ -4731,28 +4780,28 @@ lesseq_defined_than (struct symbol *sym0, struct symbol *sym1)
       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")));
+       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));
+       && 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));
+       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:
@@ -4760,17 +4809,14 @@ lesseq_defined_than (struct symbol *sym0, struct symbol *sym1)
     }
 }
 
-/* Append (SYM,BLOCK,SYMTAB) to the end of the array of struct block_symbol
-   records in OBSTACKP.  Do nothing if SYM is a duplicate.  */
+/* 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 (struct obstack *obstackp,
-                 struct symbol *sym,
-                 const struct block *block)
+add_defn_to_vec (std::vector<struct block_symbol> &result,
+                struct symbol *sym,
+                const struct block *block)
 {
-  int i;
-  struct block_symbol *prevDefns = defns_collected (obstackp, 0);
-
   /* 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
@@ -4780,46 +4826,22 @@ add_defn_to_vec (struct obstack *obstackp,
      matches, with at least one of them complete.  It can then filter
      out the stub ones if needed.  */
 
-  for (i = num_defns_collected (obstackp) - 1; i >= 0; i -= 1)
+  for (int i = result.size () - 1; i >= 0; i -= 1)
     {
-      if (lesseq_defined_than (sym, prevDefns[i].symbol))
-        return;
-      else if (lesseq_defined_than (prevDefns[i].symbol, sym))
-        {
-          prevDefns[i].symbol = sym;
-          prevDefns[i].block = block;
-          return;
-        }
+      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;
-    obstack_grow (obstackp, &info, sizeof (struct block_symbol));
-  }
-}
-
-/* Number of block_symbol structures currently collected in current vector in
-   OBSTACKP.  */
-
-static int
-num_defns_collected (struct obstack *obstackp)
-{
-  return obstack_object_size (obstackp) / sizeof (struct block_symbol);
-}
-
-/* Vector of block_symbol structures currently collected in current vector in
-   OBSTACKP.  If FINISH, close off the vector and return its final address.  */
-
-static struct block_symbol *
-defns_collected (struct obstack *obstackp, int finish)
-{
-  if (finish)
-    return (struct block_symbol *) obstack_finish (obstackp);
-  else
-    return (struct block_symbol *) obstack_base (obstackp);
+  struct block_symbol info;
+  info.symbol = sym;
+  info.block = block;
+  result.push_back (info);
 }
 
 /* Return a bound minimal symbol matching NAME according to Ada
@@ -4860,12 +4882,12 @@ ada_lookup_simple_minsym (const char *name)
 
 /* For all subprograms that statically enclose the subprogram of the
    selected frame, add symbols matching identifier NAME in DOMAIN
-   and their blocks to the list of data in OBSTACKP, as for
+   and their blocks to the list of data in RESULT, as for
    ada_add_block_symbols (q.v.).   If WILD_MATCH_P, treat as NAME
    with a wildcard prefix.  */
 
 static void
-add_symbols_from_enclosing_procs (struct obstack *obstackp,
+add_symbols_from_enclosing_procs (std::vector<struct block_symbol> &result,
                                  const lookup_name_info &lookup_name,
                                  domain_enum domain)
 {
@@ -4916,7 +4938,7 @@ ada_identical_enum_types_p (struct type *type1, struct type *type2)
       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),
+         || strncmp (TYPE_FIELD_NAME (type1, i),
                      TYPE_FIELD_NAME (type2, i),
                      len_1) != 0)
        return 0;
@@ -4970,7 +4992,7 @@ symbols_are_identical_enums (const std::vector<struct block_symbol> &syms)
   /* 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 ())
+       != SYMBOL_TYPE (syms[0].symbol)->num_fields ())
       return 0;
 
   /* All the sanity checks passed, so we might have a set of
@@ -4978,7 +5000,7 @@ symbols_are_identical_enums (const std::vector<struct block_symbol> &syms)
      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)))
+                                    SYMBOL_TYPE (syms[0].symbol)))
       return 0;
 
   return 1;
@@ -4988,10 +5010,9 @@ symbols_are_identical_enums (const std::vector<struct block_symbol> &syms)
    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.
-   Returns the number of items in the modified list.  */
+   debugging symbols)).  Modifies SYMS to squeeze out deleted entries.  */
 
-static int
+static void
 remove_extra_symbols (std::vector<struct block_symbol> *syms)
 {
   int i, j;
@@ -5000,7 +5021,7 @@ remove_extra_symbols (std::vector<struct block_symbol> *syms)
      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 syms->size ();
+    return;
 
   i = 0;
   while (i < syms->size ())
@@ -5008,42 +5029,42 @@ remove_extra_symbols (std::vector<struct block_symbol> *syms)
       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.  */
+        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;
-            }
-        }
+         && (*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.  */
+        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)[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;
-            }
-        }
+                 && SYMBOL_VALUE_ADDRESS ((*syms)[i].symbol)
+                 == SYMBOL_VALUE_ADDRESS ((*syms)[j].symbol))
+               remove_p = 1;
+           }
+       }
       
       if (remove_p)
        syms->erase (syms->begin () + i);
@@ -5065,8 +5086,6 @@ remove_extra_symbols (std::vector<struct block_symbol> *syms)
      isn't missing some choices that were identical and yet distinct.  */
   if (symbols_are_identical_enums (*syms))
     syms->resize (1);
-
-  return syms->size ();
 }
 
 /* Given a type that corresponds to a renaming entity, use the type name
@@ -5158,8 +5177,8 @@ old_renaming_is_invisible (const struct symbol *sym, const char *function_name)
    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 and returns the number of surviving symbols.
-   
+   SYMS.
+
    Rationale:
    First, in cases where an object renaming is implemented as a
    reference variable, GNAT may produce both the actual reference
@@ -5181,17 +5200,17 @@ old_renaming_is_invisible (const struct symbol *sym, const char *function_name)
    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.
-        
+       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.  */
+       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 int
+static void
 remove_irrelevant_renamings (std::vector<struct block_symbol> *syms,
                             const struct block *current_block)
 {
@@ -5240,22 +5259,23 @@ remove_irrelevant_renamings (std::vector<struct block_symbol> *syms,
              (*syms)[k] = (*syms)[j];
              k += 1;
            }
-      return k;
+      syms->resize (k);
+      return;
     }
 
   /* Extract the function name associated to CURRENT_BLOCK.
      Abort if unable to do so.  */
 
   if (current_block == NULL)
-    return syms->size ();
+    return;
 
   current_function = block_linkage_function (current_block);
   if (current_function == NULL)
-    return syms->size ();
+    return;
 
   current_function_name = current_function->linkage_name ();
   if (current_function_name == NULL)
-    return syms->size ();
+    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
@@ -5265,18 +5285,16 @@ remove_irrelevant_renamings (std::vector<struct block_symbol> *syms,
   while (i < syms->size ())
     {
       if (ada_parse_renaming ((*syms)[i].symbol, NULL, NULL, NULL)
-          == ADA_OBJECT_RENAMING
-          && old_renaming_is_invisible ((*syms)[i].symbol,
+         == ADA_OBJECT_RENAMING
+         && old_renaming_is_invisible ((*syms)[i].symbol,
                                        current_function_name))
        syms->erase (syms->begin () + i);
       else
-        i += 1;
+       i += 1;
     }
-
-  return syms->size ();
 }
 
-/* Add to OBSTACKP all symbols from BLOCK (and its super-blocks)
+/* Add to RESULT all symbols from BLOCK (and its super-blocks)
    whose name and domain match NAME and DOMAIN respectively.
    If no match was found, then extend the search to "enclosing"
    routines (in other words, if we're inside a nested function,
@@ -5284,10 +5302,10 @@ remove_irrelevant_renamings (std::vector<struct block_symbol> *syms,
    If WILD_MATCH_P is nonzero, perform the naming matching in
    "wild" mode (see function "wild_match" for more info).
 
-   Note: This function assumes that OBSTACKP has 0 (zero) element in it.  */
+   Note: This function assumes that RESULT has 0 (zero) element in it.  */
 
 static void
-ada_add_local_symbols (struct obstack *obstackp,
+ada_add_local_symbols (std::vector<struct block_symbol> &result,
                       const lookup_name_info &lookup_name,
                       const struct block *block, domain_enum domain)
 {
@@ -5296,20 +5314,19 @@ ada_add_local_symbols (struct obstack *obstackp,
   while (block != NULL)
     {
       block_depth += 1;
-      ada_add_block_symbols (obstackp, block, lookup_name, domain, NULL);
+      ada_add_block_symbols (result, block, lookup_name, domain, NULL);
 
       /* If we found a non-function match, assume that's the one.  */
-      if (is_nonfunction (defns_collected (obstackp, 0),
-                          num_defns_collected (obstackp)))
-        return;
+      if (is_nonfunction (result))
+       return;
 
       block = BLOCK_SUPERBLOCK (block);
     }
 
   /* If no luck so far, try to find NAME as a local symbol in some lexically
      enclosing subprogram.  */
-  if (num_defns_collected (obstackp) == 0 && block_depth > 2)
-    add_symbols_from_enclosing_procs (obstackp, lookup_name, domain);
+  if (result.empty () && block_depth > 2)
+    add_symbols_from_enclosing_procs (result, lookup_name, domain);
 }
 
 /* An object of this type is used as the user_data argument when
@@ -5317,15 +5334,21 @@ ada_add_local_symbols (struct obstack *obstackp,
 
 struct match_data
 {
-  struct objfile *objfile;
-  struct obstack *obstackp;
-  struct symbol *arg_sym;
-  int found_sym;
+  explicit match_data (std::vector<struct block_symbol> *rp)
+    : resultp (rp)
+  {
+  }
+  DISABLE_COPY_AND_ASSIGN (match_data);
+
+  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.  DATA is a pointer to a struct match_data *
-   containing the obstack that collects the symbol list, the file that SYM
+   containing the vector that collects the symbol list, the file that SYM
    must come from, a flag indicating whether a non-argument symbol has
    been found in the current block, and the last argument symbol
    passed in SYM within the current block (if any).  When SYM is null,
@@ -5342,10 +5365,10 @@ aux_add_nonlocal_symbols (struct block_symbol *bsym,
   if (sym == NULL)
     {
       if (!data->found_sym && data->arg_sym != NULL) 
-       add_defn_to_vec (data->obstackp,
+       add_defn_to_vec (*data->resultp,
                         fixup_symbol_section (data->arg_sym, data->objfile),
                         block);
-      data->found_sym = 0;
+      data->found_sym = false;
       data->arg_sym = NULL;
     }
   else 
@@ -5356,8 +5379,8 @@ aux_add_nonlocal_symbols (struct block_symbol *bsym,
        data->arg_sym = sym;
       else
        {
-         data->found_sym = 1;
-         add_defn_to_vec (data->obstackp,
+         data->found_sym = true;
+         add_defn_to_vec (*data->resultp,
                           fixup_symbol_section (sym, data->objfile),
                           block);
        }
@@ -5367,16 +5390,16 @@ aux_add_nonlocal_symbols (struct block_symbol *bsym,
 
 /* Helper for add_nonlocal_symbols.  Find symbols in DOMAIN which are
    targeted by renamings matching LOOKUP_NAME in BLOCK.  Add these
-   symbols to OBSTACKP.  Return whether we found such symbols.  */
+   symbols to RESULT.  Return whether we found such symbols.  */
 
 static int
-ada_add_block_renamings (struct obstack *obstackp,
+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 = num_defns_collected (obstackp);
+  int defns_mark = result.size ();
 
   symbol_name_matcher_ftype *name_match
     = ada_get_symbol_name_matcher (lookup_name);
@@ -5414,12 +5437,12 @@ ada_add_block_renamings (struct obstack *obstackp,
        {
          lookup_name_info decl_lookup_name (renaming->declaration,
                                             lookup_name.match_type ());
-         ada_add_all_symbols (obstackp, block, decl_lookup_name, domain,
+         ada_add_all_symbols (result, block, decl_lookup_name, domain,
                               1, NULL);
        }
       renaming->searched = 0;
     }
-  return num_defns_collected (obstackp) != defns_mark;
+  return result.size () != defns_mark;
 }
 
 /* Implements compare_names, but only applying the comparision using
@@ -5516,20 +5539,17 @@ ada_lookup_name (const lookup_name_info &lookup_name)
   return lookup_name.ada ().lookup_name ().c_str ();
 }
 
-/* Add to OBSTACKP all non-local symbols whose name and domain match
+/* 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 (struct obstack *obstackp,
+add_nonlocal_symbols (std::vector<struct block_symbol> &result,
                      const lookup_name_info &lookup_name,
                      domain_enum domain, int global)
 {
-  struct match_data data;
-
-  memset (&data, 0, sizeof data);
-  data.obstackp = obstackp;
+  struct match_data data (&result);
 
   bool is_wild_match = lookup_name.ada ().wild_match_p ();
 
@@ -5542,41 +5562,43 @@ add_nonlocal_symbols (struct obstack *obstackp,
     {
       data.objfile = objfile;
 
-      objfile->sf->qf->map_matching_symbols (objfile, lookup_name,
-                                            domain, global, callback,
-                                            (is_wild_match
-                                             ? NULL : compare_names));
+      if (objfile->sf != nullptr)
+       objfile->sf->qf->map_matching_symbols (objfile, lookup_name,
+                                              domain, global, callback,
+                                              (is_wild_match
+                                               ? NULL : compare_names));
 
       for (compunit_symtab *cu : objfile->compunits ())
        {
          const struct block *global_block
            = BLOCKVECTOR_BLOCK (COMPUNIT_BLOCKVECTOR (cu), GLOBAL_BLOCK);
 
-         if (ada_add_block_renamings (obstackp, global_block, lookup_name,
+         if (ada_add_block_renamings (result, global_block, lookup_name,
                                       domain))
-           data.found_sym = 1;
+           data.found_sym = true;
        }
     }
 
-  if (num_defns_collected (obstackp) == 0 && global && !is_wild_match)
+  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 ())
-        {
+       {
          data.objfile = objfile;
-         objfile->sf->qf->map_matching_symbols (objfile, name1,
-                                                domain, global, callback,
-                                                compare_names);
+         if (objfile->sf != nullptr)
+           objfile->sf->qf->map_matching_symbols (objfile, name1,
+                                                  domain, global, callback,
+                                                  compare_names);
        }
     }          
 }
 
 /* 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 OBSTACKP.
+   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,
@@ -5592,7 +5614,7 @@ add_nonlocal_symbols (struct obstack *obstackp,
    to lookup global symbols.  */
 
 static void
-ada_add_all_symbols (struct obstack *obstackp,
+ada_add_all_symbols (std::vector<struct block_symbol> &result,
                     const struct block *block,
                     const lookup_name_info &lookup_name,
                     domain_enum domain,
@@ -5619,15 +5641,15 @@ ada_add_all_symbols (struct obstack *obstackp,
   if (block != NULL)
     {
       if (full_search)
-       ada_add_local_symbols (obstackp, lookup_name, block, domain);
+       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 (obstackp, block, lookup_name, domain, NULL);
+         ada_add_block_symbols (result, block, lookup_name, domain, NULL);
        }
-      if (num_defns_collected (obstackp) > 0 || !full_search)
+      if (!result.empty () || !full_search)
        return;
     }
 
@@ -5639,7 +5661,7 @@ ada_add_all_symbols (struct obstack *obstackp,
                            domain, &sym, &block))
     {
       if (sym != NULL)
-       add_defn_to_vec (obstackp, sym, block);
+       add_defn_to_vec (result, sym, block);
       return;
     }
 
@@ -5648,21 +5670,20 @@ ada_add_all_symbols (struct obstack *obstackp,
 
   /* Search symbols from all global blocks.  */
  
-  add_nonlocal_symbols (obstackp, lookup_name, domain, 1);
+  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 (num_defns_collected (obstackp) == 0)
-    add_nonlocal_symbols (obstackp, lookup_name, domain, 0);
+  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, returning the number of
-   matches.
-   Fills *RESULTS with (SYM,BLOCK) tuples, indicating the symbols
-   found and the blocks and symbol tables (if any) in which they were
-   found.
+   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,
@@ -5673,55 +5694,44 @@ ada_add_all_symbols (struct obstack *obstackp,
    Names prefixed with "standard__" are handled specially: "standard__"
    is first stripped off, and only static and global symbols are searched.  */
 
-static int
+static std::vector<struct block_symbol>
 ada_lookup_symbol_list_worker (const lookup_name_info &lookup_name,
                               const struct block *block,
                               domain_enum domain,
-                              std::vector<struct block_symbol> *results,
                               int full_search)
 {
   int syms_from_global_search;
-  int ndefns;
-  auto_obstack obstack;
+  std::vector<struct block_symbol> results;
 
-  ada_add_all_symbols (&obstack, block, lookup_name,
+  ada_add_all_symbols (results, block, lookup_name,
                       domain, full_search, &syms_from_global_search);
 
-  ndefns = num_defns_collected (&obstack);
-
-  struct block_symbol *base = defns_collected (&obstack, 1);
-  for (int i = 0; i < ndefns; ++i)
-    results->push_back (base[i]);
+  remove_extra_symbols (&results);
 
-  ndefns = remove_extra_symbols (results);
-
-  if (ndefns == 0 && full_search && syms_from_global_search)
+  if (results.empty () && full_search && syms_from_global_search)
     cache_symbol (ada_lookup_name (lookup_name), domain, NULL, NULL);
 
-  if (ndefns == 1 && full_search && syms_from_global_search)
+  if (results.size () == 1 && full_search && syms_from_global_search)
     cache_symbol (ada_lookup_name (lookup_name), domain,
-                 (*results)[0].symbol, (*results)[0].block);
-
-  ndefns = remove_irrelevant_renamings (results, block);
+                 results[0].symbol, results[0].block);
 
-  return ndefns;
+  remove_irrelevant_renamings (&results, block);
+  return results;
 }
 
 /* Find symbols in DOMAIN matching NAME, in BLOCK and enclosing scope and
-   in global scopes, returning the number of matches, and filling *RESULTS
-   with (SYM,BLOCK) tuples.
+   in global scopes, returning (SYM,BLOCK) tuples.
 
    See ada_lookup_symbol_list_worker for further details.  */
 
-int
+std::vector<struct block_symbol>
 ada_lookup_symbol_list (const char *name, const struct block *block,
-                       domain_enum domain,
-                       std::vector<struct block_symbol> *results)
+                       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, results, 1);
+  return ada_lookup_symbol_list_worker (lookup_name, block, domain, 1);
 }
 
 /* The result is as for ada_lookup_symbol_list with FULL_SEARCH set
@@ -5742,7 +5752,7 @@ ada_lookup_encoded_symbol (const char *name, const struct block *block,
      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 = std::string ("<") + name + '>';
+  std::string verbatim = add_angle_brackets (name);
 
   gdb_assert (info != NULL);
   *info = ada_lookup_symbol (verbatim.c_str (), block, domain);
@@ -5755,14 +5765,12 @@ ada_lookup_encoded_symbol (const char *name, const struct block *block,
 
 struct block_symbol
 ada_lookup_symbol (const char *name, const struct block *block0,
-                   domain_enum domain)
+                  domain_enum domain)
 {
-  std::vector<struct block_symbol> candidates;
-  int n_candidates;
-
-  n_candidates = ada_lookup_symbol_list (name, block0, domain, &candidates);
+  std::vector<struct block_symbol> candidates
+    = ada_lookup_symbol_list (name, block0, domain);
 
-  if (n_candidates == 0)
+  if (candidates.empty ())
     return {};
 
   block_symbol info = candidates[0];
@@ -5799,7 +5807,7 @@ is_name_suffix (const char *str)
     {
       str += 3;
       while (isdigit (str[0]))
-        str += 1;
+       str += 1;
     }
   
   /* [.$][0-9]+ */
@@ -5808,9 +5816,9 @@ is_name_suffix (const char *str)
     {
       matching = str + 1;
       while (isdigit (matching[0]))
-        matching += 1;
+       matching += 1;
       if (matching[0] == '\0')
-        return 1;
+       return 1;
     }
 
   /* ___[0-9]+ */
@@ -5819,9 +5827,9 @@ is_name_suffix (const char *str)
     {
       matching = str + 3;
       while (isdigit (matching[0]))
-        matching += 1;
+       matching += 1;
       if (matching[0] == '\0')
-        return 1;
+       return 1;
     }
 
   /* "TKB" suffixes are used for subprograms implementing task bodies.  */
@@ -5851,10 +5859,10 @@ is_name_suffix (const char *str)
     {
       matching = str + 3;
       while (isdigit (matching[0]))
-        matching += 1;
+       matching += 1;
       if ((matching[0] == 'b' || matching[0] == 's')
-          && matching [1] == '\0')
-        return 1;
+         && matching [1] == '\0')
+       return 1;
     }
 
   /* ??? We should not modify STR directly, as we are doing below.  This
@@ -5866,11 +5874,11 @@ is_name_suffix (const char *str)
     {
       str += 1;
       while (str[0] != '_' && str[0] != '\0')
-        {
-          if (str[0] != 'n' && str[0] != 'b')
-            return 0;
-          str += 1;
-        }
+       {
+         if (str[0] != 'n' && str[0] != 'b')
+           return 0;
+         str += 1;
+       }
     }
 
   if (str[0] == '\000')
@@ -5879,39 +5887,39 @@ is_name_suffix (const char *str)
   if (str[0] == '_')
     {
       if (str[1] != '_' || str[2] == '\000')
-        return 0;
+       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 (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;
+       return 0;
       for (k = 3; str[k] != '\0'; k += 1)
-        if (!isdigit (str[k]) && str[k] != '_')
-          return 0;
+       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;
+       if (!isdigit (str[k]) && str[k] != '_')
+         return 0;
       return 1;
     }
   return 0;
@@ -5939,18 +5947,18 @@ is_valid_name_for_wild_match (const char *name0)
   return 1;
 }
 
-/* Advance *NAMEP to next occurrence of TARGET0 in the string NAME0
-   that could start a simple name.  Assumes that *NAMEP points into
-   the string beginning at NAME0.  */
+/* 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, int target0)
+advance_wild_match (const char **namep, const char *name0, char target0)
 {
   const char *name = *namep;
 
   while (1)
     {
-      int t0, t1;
+      char t0, t1;
 
       t0 = *name;
       if (t0 == '_')
@@ -5970,6 +5978,13 @@ advance_wild_match (const char **namep, const char *name0, int 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;
        }
@@ -6014,34 +6029,11 @@ wild_match (const char *name, const char *patn)
     }
 }
 
-/* Returns true iff symbol name SYM_NAME matches SEARCH_NAME, ignoring
-   any trailing suffixes that encode debugging information or leading
-   _ada_ on SYM_NAME (see is_name_suffix commentary for the debugging
-   information that is ignored).  */
-
-static bool
-full_match (const char *sym_name, const char *search_name)
-{
-  size_t search_name_len = strlen (search_name);
-
-  if (strncmp (sym_name, search_name, search_name_len) == 0
-      && is_name_suffix (sym_name + search_name_len))
-    return true;
-
-  if (startswith (sym_name, "_ada_")
-      && strncmp (sym_name + 5, search_name, search_name_len) == 0
-      && is_name_suffix (sym_name + search_name_len + 5))
-    return true;
-
-  return false;
-}
-
-/* Add symbols from BLOCK matching LOOKUP_NAME in DOMAIN to vector
-   *defn_symbols, updating the list of symbols in OBSTACKP (if
+/* 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 (struct obstack *obstackp,
+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)
@@ -6050,11 +6042,11 @@ ada_add_block_symbols (struct obstack *obstackp,
   /* A matching argument symbol, if any.  */
   struct symbol *arg_sym;
   /* Set true when we find a matching non-argument symbol.  */
-  int found_sym;
+  bool found_sym;
   struct symbol *sym;
 
   arg_sym = NULL;
-  found_sym = 0;
+  found_sym = false;
   for (sym = block_iter_match_first (block, lookup_name, &iter);
        sym != NULL;
        sym = block_iter_match_next (lookup_name, &iter))
@@ -6067,8 +6059,8 @@ ada_add_block_symbols (struct obstack *obstackp,
                arg_sym = sym;
              else
                {
-                 found_sym = 1;
-                 add_defn_to_vec (obstackp,
+                 found_sym = true;
+                 add_defn_to_vec (result,
                                   fixup_symbol_section (sym, objfile),
                                   block);
                }
@@ -6078,72 +6070,72 @@ ada_add_block_symbols (struct obstack *obstackp,
 
   /* Handle renamings.  */
 
-  if (ada_add_block_renamings (obstackp, block, lookup_name, domain))
-    found_sym = 1;
+  if (ada_add_block_renamings (result, block, lookup_name, domain))
+    found_sym = true;
 
   if (!found_sym && arg_sym != NULL)
     {
-      add_defn_to_vec (obstackp,
-                       fixup_symbol_section (arg_sym, objfile),
-                       block);
+      add_defn_to_vec (result,
+                      fixup_symbol_section (arg_sym, objfile),
+                      block);
     }
 
   if (!lookup_name.ada ().wild_match_p ())
     {
       arg_sym = NULL;
-      found_sym = 0;
+      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_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 = 1;
-                       add_defn_to_vec (obstackp,
+                       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?  */
+        They aren't parameters, right?  */
       if (!found_sym && arg_sym != NULL)
-        {
-          add_defn_to_vec (obstackp,
-                           fixup_symbol_section (arg_sym, objfile),
-                           block);
-        }
+       {
+         add_defn_to_vec (result,
+                          fixup_symbol_section (arg_sym, objfile),
+                          block);
+       }
     }
 }
 \f
 
-                                /* Symbol Completion */
+                               /* Symbol Completion */
 
 /* See symtab.h.  */
 
@@ -6166,9 +6158,9 @@ ada_lookup_name_info::matches
   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.  */
+        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);
@@ -6177,10 +6169,10 @@ ada_lookup_name_info::matches
   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.  */
+        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++);
@@ -6193,8 +6185,8 @@ ada_lookup_name_info::matches
   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.  */
+        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)
@@ -6227,7 +6219,7 @@ ada_lookup_name_info::matches
   return true;
 }
 
-                                /* Field Access */
+                               /* Field Access */
 
 /* Return non-zero if TYPE is a pointer to the GNAT dispatch table used
    for tagged types.  */
@@ -6324,7 +6316,7 @@ ada_is_tag_type (struct type *type)
       const char *name = ada_type_name (TYPE_TARGET_TYPE (type));
 
       return (name != NULL
-              && strcmp (name, "ada__tags__dispatch_table") == 0);
+             && strcmp (name, "ada__tags__dispatch_table") == 0);
     }
 }
 
@@ -6360,13 +6352,13 @@ ada_value_tag (struct value *val)
 static struct value *
 value_tag_from_contents_and_address (struct type *type,
                                     const gdb_byte *valaddr,
-                                     CORE_ADDR address)
+                                    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))
+                        NULL, NULL, NULL))
     {
       const gdb_byte *valaddr1 = ((valaddr == NULL)
                                  ? NULL
@@ -6384,7 +6376,7 @@ 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 ()));
+    return ada_find_any_type (ada_encode (type_name.get ()).c_str ());
   return NULL;
 }
 
@@ -6609,15 +6601,15 @@ ada_parent_type (struct type *type)
   for (i = 0; i < type->num_fields (); i += 1)
     if (ada_is_parent_field (type, i))
       {
-        struct type *parent_type = type->field (i).type ();
+       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);
+       /* 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 ada_check_typedef (parent_type);
       }
 
   return NULL;
@@ -6633,8 +6625,8 @@ 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")));
+         && (startswith (name, "PARENT")
+             || startswith (name, "_parent")));
 }
 
 /* True iff field number FIELD_NUM of structure type TYPE is a
@@ -6660,10 +6652,10 @@ ada_is_wrapper_field (struct type *type, int field_num)
     }
 
   return (name != NULL
-          && (startswith (name, "PARENT")
-              || strcmp (name, "REP") == 0
-              || startswith (name, "_parent")
-              || name[0] == 'S' || name[0] == 'R' || name[0] == 'O'));
+         && (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
@@ -6717,8 +6709,7 @@ ada_is_others_clause (struct type *type, int field_num)
 const char *
 ada_variant_discrim_name (struct type *type0)
 {
-  static char *result = NULL;
-  static size_t result_len = 0;
+  static std::string result;
   struct type *type;
   const char *name;
   const char *discrim_end;
@@ -6738,7 +6729,7 @@ ada_variant_discrim_name (struct type *type0)
        discrim_end -= 1)
     {
       if (startswith (discrim_end, "___XVN"))
-        break;
+       break;
     }
   if (discrim_end == name)
     return "";
@@ -6747,17 +6738,15 @@ ada_variant_discrim_name (struct type *type0)
        discrim_start -= 1)
     {
       if (discrim_start == name + 1)
-        return "";
+       return "";
       if ((discrim_start > name + 3
-           && startswith (discrim_start - 3, "___"))
-          || discrim_start[-1] == '.')
-        break;
+          && startswith (discrim_start - 3, "___"))
+         || discrim_start[-1] == '.')
+       break;
     }
 
-  GROW_VECT (result, result_len, discrim_end - discrim_start + 1);
-  strncpy (result, discrim_start, discrim_end - discrim_start);
-  result[discrim_end - discrim_start] = '\0';
-  return result;
+  result = std::string (discrim_start, discrim_end - discrim_start);
+  return result.c_str ();
 }
 
 /* Scan STR for a subtype-encoded number, beginning at position K.
@@ -6789,7 +6778,7 @@ ada_scan_number (const char str[], int k, LONGEST * R, int *new_k)
   if (str[k] == 'm')
     {
       if (R != NULL)
-        *R = (-(LONGEST) (RU - 1)) - 1;
+       *R = (-(LONGEST) (RU - 1)) - 1;
       k += 1;
     }
   else if (R != NULL)
@@ -6820,35 +6809,35 @@ ada_in_variant (LONGEST val, struct type *type, int field_num)
   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;
-        }
+       {
+       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;
+       }
     }
 }
 
@@ -6861,7 +6850,7 @@ ada_in_variant (LONGEST val, struct type *type, int field_num)
 
 struct value *
 ada_value_primitive_field (struct value *arg1, int offset, int fieldno,
-                           struct type *arg_type)
+                          struct type *arg_type)
 {
   struct type *type;
 
@@ -6877,8 +6866,8 @@ ada_value_primitive_field (struct value *arg1, int offset, int 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);
+                                            offset + bit_pos / 8,
+                                            bit_pos % 8, bit_size, type);
     }
   else
     return value_primitive_field (arg1, offset, fieldno, arg_type);
@@ -6901,21 +6890,21 @@ ada_value_primitive_field (struct value *arg1, int offset, int fieldno,
    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;
+        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;
+        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';
+       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:
@@ -6951,8 +6940,8 @@ ada_value_primitive_field (struct value *arg1, int offset, int fieldno,
 
 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,
+                  struct type **field_type_p,
+                  int *byte_offset_p, int *bit_offset_p, int *bit_size_p,
                   int *index_p)
 {
   int i;
@@ -6976,10 +6965,10 @@ find_struct_field (const char *name, struct type *type, int offset,
       const char *t_field_name = TYPE_FIELD_NAME (type, i);
 
       if (t_field_name == NULL)
-        continue;
+       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
@@ -6988,13 +6977,13 @@ find_struct_field (const char *name, struct type *type, int offset,
             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;
-        }
+         parent_offset = i;
+         continue;
+       }
 
       else if (name != NULL && field_name_match (t_field_name, name))
-        {
-          int bit_size = TYPE_FIELD_BITSIZE (type, i);
+       {
+         int bit_size = TYPE_FIELD_BITSIZE (type, i);
 
          if (field_type_p != NULL)
            *field_type_p = type->field (i).type ();
@@ -7004,33 +6993,33 @@ find_struct_field (const char *name, struct type *type, int offset,
            *bit_offset_p = bit_pos % 8;
          if (bit_size_p != NULL)
            *bit_size_p = bit_size;
-          return 1;
-        }
+         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;
-        }
+           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
+         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;
-            }
-        }
+         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;
     }
@@ -7044,9 +7033,9 @@ find_struct_field (const char *name, struct type *type, int 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;
+                            fld_offset, field_type_p, byte_offset_p,
+                            bit_offset_p, bit_size_p, index_p))
+       return 1;
     }
 
   return 0;
@@ -7075,7 +7064,7 @@ num_visible_fields (struct type *type)
 
 static struct value *
 ada_search_struct_field (const char *name, struct value *arg, int offset,
-                         struct type *type)
+                        struct type *type)
 {
   int i;
   int parent_offset = -1;
@@ -7086,10 +7075,10 @@ ada_search_struct_field (const char *name, struct value *arg, int offset,
       const char *t_field_name = TYPE_FIELD_NAME (type, i);
 
       if (t_field_name == NULL)
-        continue;
+       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
@@ -7098,43 +7087,43 @@ ada_search_struct_field (const char *name, struct value *arg, int offset,
             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;
-        }
+         parent_offset = i;
+         continue;
+       }
 
       else if (field_name_match (t_field_name, name))
-        return ada_value_primitive_field (arg, offset, i, type);
+       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 ());
+       {
+         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;
-        }
+         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;
+         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
+         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 ());
+               (name, arg,
+                var_offset + TYPE_FIELD_BITPOS (field_type, j) / 8,
+                field_type->field (j).type ());
 
-              if (v != NULL)
-                return v;
-            }
-        }
+             if (v != NULL)
+               return v;
+           }
+       }
     }
 
   /* Field not found so far.  If this is a tagged type which
@@ -7147,7 +7136,7 @@ ada_search_struct_field (const char *name, struct value *arg, int offset,
        type->field (parent_offset).type ());
 
       if (v != NULL)
-        return v;
+       return v;
     }
 
   return NULL;
@@ -7184,26 +7173,26 @@ ada_index_struct_field_1 (int *index_p, struct value *arg, int offset,
   for (i = 0; i < type->num_fields (); i += 1)
     {
       if (TYPE_FIELD_NAME (type, i) == NULL)
-        continue;
+       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,
+       {
+         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;
-        }
+         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);
+       return ada_value_primitive_field (arg, offset, i, type);
       else
        *index_p -= 1;
     }
@@ -7244,7 +7233,7 @@ type_as_string (struct type *type)
 
 static struct type *
 ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
-                            int noerr)
+                           int noerr)
 {
   int i;
   int parent_offset = -1;
@@ -7255,10 +7244,10 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
   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);
+       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
@@ -7266,7 +7255,7 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
          && type->code () != TYPE_CODE_UNION))
     {
       if (noerr)
-        return NULL;
+       return NULL;
 
       error (_("Type %s is not a structure or union type"),
             type != NULL ? type_as_string (type).c_str () : _("(null)"));
@@ -7280,10 +7269,10 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
       struct type *t;
 
       if (t_field_name == NULL)
-        continue;
+       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
@@ -7292,32 +7281,32 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
             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;
-        }
+         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)
+       {
+         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 ());
+       {
+         int j;
+         struct type *field_type = ada_check_typedef (type->field (i).type ());
 
-          for (j = field_type->num_fields () - 1; j >= 0; j -= 1)
-            {
+         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
+                NOT wrapped in a struct, since the compiler sometimes
                 generates these for unchecked variant types.  Revisit
-                if the compiler changes this practice.  */
+                if the compiler changes this practice.  */
              const char *v_field_name = TYPE_FIELD_NAME (field_type, j);
 
              if (v_field_name != NULL 
@@ -7327,10 +7316,10 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
                t = ada_lookup_struct_elt_type (field_type->field (j).type (),
                                                name, 0, 1);
 
-              if (t != NULL)
+             if (t != NULL)
                return t;
-            }
-        }
+           }
+       }
 
     }
 
@@ -7339,11 +7328,11 @@ ada_lookup_struct_elt_type (struct type *type, const char *name, int refok,
 
     if (parent_offset != -1)
       {
-        struct type *t;
+       struct type *t;
 
-        t = ada_lookup_struct_elt_type (type->field (parent_offset).type (),
-                                        name, 0, 1);
-        if (t != NULL)
+       t = ada_lookup_struct_elt_type (type->field (parent_offset).type (),
+                                       name, 0, 1);
+       if (t != NULL)
          return t;
       }
 
@@ -7398,9 +7387,9 @@ ada_which_variant_applies (struct type *var_type, struct value *outer)
   for (i = 0; i < var_type->num_fields (); i += 1)
     {
       if (ada_is_others_clause (var_type, i))
-        others_clause = i;
+       others_clause = i;
       else if (ada_in_variant (discrim_val, var_type, i))
-        return i;
+       return i;
     }
 
   return others_clause;
@@ -7408,7 +7397,7 @@ ada_which_variant_applies (struct type *var_type, struct value *outer)
 \f
 
 
-                                /* Dynamic-Sized Records */
+                               /* 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
@@ -7574,7 +7563,7 @@ ada_prefer_type (struct type *type0, struct type *type1)
   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))
+          && !ada_is_array_descriptor_type (type1))
     return 1;
   else
     {
@@ -7621,10 +7610,10 @@ find_parallel_type_by_descriptive_type (struct type *type, const char *name)
       const char *result_name = ada_type_name (result);
 
       if (result_name == NULL)
-        {
-          warning (_("unexpected null name on descriptive type"));
-          return NULL;
-        }
+       {
+         warning (_("unexpected null name on descriptive type"));
+         return NULL;
+       }
 
       /* If the names match, stop.  */
       if (strcmp (result_name, name) == 0)
@@ -7715,9 +7704,9 @@ dynamic_template_type (struct type *type)
       int len = strlen (ada_type_name (type));
 
       if (len > 6 && strcmp (ada_type_name (type) + len - 6, "___XVE") == 0)
-        return type;
+       return type;
       else
-        return ada_find_parallel_type (type, "___XVE");
+       return ada_find_parallel_type (type, "___XVE");
     }
 }
 
@@ -7748,7 +7737,7 @@ variant_field_index (struct type *type)
   for (f = 0; f < type->num_fields (); f += 1)
     {
       if (ada_is_variant_part (type, f))
-        return f;
+       return f;
     }
   return -1;
 }
@@ -7787,8 +7776,8 @@ empty_record (struct type *templ)
 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)
+                                    CORE_ADDR address, struct value *dval0,
+                                    int keep_dynamic_fields)
 {
   struct value *mark = value_mark ();
   struct value *dval;
@@ -7808,9 +7797,9 @@ ada_template_to_fixed_record_type_1 (struct type *type,
     {
       nfields = 0;
       while (nfields < type->num_fields ()
-             && !ada_is_variant_part (type, nfields)
-             && !is_dynamic_field (type, nfields))
-        nfields++;
+            && !ada_is_variant_part (type, nfields)
+            && !is_dynamic_field (type, nfields))
+       nfields++;
     }
 
   rtype = alloc_type_copy (type);
@@ -7834,18 +7823,18 @@ ada_template_to_fixed_record_type_1 (struct type *type,
       TYPE_FIELD_BITSIZE (rtype, f) = 0;
 
       if (ada_is_variant_part (type, f))
-        {
-          variant_field = f;
-          fld_bit_len = 0;
-        }
+       {
+         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)
+         if (dval0 == NULL)
            {
              /* rtype's length is computed based on the run-time
                 value of discriminants.  If the discriminants are not
@@ -7862,8 +7851,8 @@ ada_template_to_fixed_record_type_1 (struct type *type,
                                                                 address);
              rtype = value_type (dval);
            }
-          else
-            dval = dval0;
+         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.
@@ -7903,18 +7892,18 @@ ada_template_to_fixed_record_type_1 (struct type *type,
          ada_ensure_varsize_limit (field_type);
 
          rtype->field (f).set_type (field_type);
-          TYPE_FIELD_NAME (rtype, f) = TYPE_FIELD_NAME (type, f);
+         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;
-        }
+         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.
 
@@ -7925,12 +7914,12 @@ ada_template_to_fixed_record_type_1 (struct type *type,
             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
+         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 ();
 
@@ -7941,15 +7930,15 @@ ada_template_to_fixed_record_type_1 (struct type *type,
              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;
+             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;
+       bit_len = off + fld_bit_len;
       off += fld_bit_len;
       TYPE_LENGTH (rtype) =
-        align_up (bit_len, TARGET_CHAR_BIT) / TARGET_CHAR_BIT;
+       align_up (bit_len, TARGET_CHAR_BIT) / TARGET_CHAR_BIT;
     }
 
   /* We handle the variant part, if any, at the end because of certain
@@ -7972,31 +7961,31 @@ ada_template_to_fixed_record_type_1 (struct type *type,
          rtype = value_type (dval);
        }
       else
-        dval = dval0;
+       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);
+       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);
+       {
+         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;
-        }
+       {
+         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
@@ -8031,10 +8020,10 @@ ada_template_to_fixed_record_type_1 (struct type *type,
 
 static struct type *
 template_to_fixed_record_type (struct type *type, const gdb_byte *valaddr,
-                               CORE_ADDR address, struct value *dval0)
+                              CORE_ADDR address, struct value *dval0)
 {
   return ada_template_to_fixed_record_type_1 (type, valaddr,
-                                              address, dval0, 1);
+                                             address, dval0, 1);
 }
 
 /* An ordinary record type in which ___XVL-convention fields and
@@ -8077,10 +8066,10 @@ template_to_static_fixed_type (struct type *type0)
       if (is_dynamic_field (type0, f))
        {
          field_type = ada_check_typedef (field_type);
-          new_type = to_static_fixed_type (TYPE_TARGET_TYPE (field_type));
+         new_type = to_static_fixed_type (TYPE_TARGET_TYPE (field_type));
        }
       else
-        new_type = static_unwrap_type (field_type);
+       new_type = static_unwrap_type (field_type);
 
       if (new_type != field_type)
        {
@@ -8120,7 +8109,7 @@ template_to_static_fixed_type (struct type *type0)
 
 static struct type *
 to_record_with_fixed_variant_part (struct type *type, const gdb_byte *valaddr,
-                                   CORE_ADDR address, struct value *dval0)
+                                  CORE_ADDR address, struct value *dval0)
 {
   struct value *mark = value_mark ();
   struct value *dval;
@@ -8157,17 +8146,17 @@ to_record_with_fixed_variant_part (struct type *type, const gdb_byte *valaddr,
   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),
+                      TYPE_FIELD_BITPOS (type, variant_field)
+                      / TARGET_CHAR_BIT),
      cond_offset_target (address,
-                         TYPE_FIELD_BITPOS (type, variant_field)
-                         / TARGET_CHAR_BIT), dval);
+                        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->field (f - 1) = rtype->field (f);
       rtype->set_num_fields (rtype->num_fields () - 1);
     }
   else
@@ -8203,7 +8192,7 @@ to_record_with_fixed_variant_part (struct type *type, const gdb_byte *valaddr,
 
 static struct type *
 to_fixed_record_type (struct type *type0, const gdb_byte *valaddr,
-                      CORE_ADDR address, struct value *dval)
+                     CORE_ADDR address, struct value *dval)
 {
   struct type *templ_type;
 
@@ -8217,9 +8206,9 @@ to_fixed_record_type (struct type *type0, const gdb_byte *valaddr,
   else if (variant_field_index (type0) >= 0)
     {
       if (dval == NULL && valaddr == NULL && address == 0)
-        return type0;
+       return type0;
       return to_record_with_fixed_variant_part (type0, valaddr, address,
-                                                dval);
+                                               dval);
     }
   else
     {
@@ -8239,7 +8228,7 @@ to_fixed_record_type (struct type *type0, const gdb_byte *valaddr,
 
 static struct type *
 to_fixed_variant_branch_type (struct type *var_type0, const gdb_byte *valaddr,
-                              CORE_ADDR address, struct value *dval)
+                             CORE_ADDR address, struct value *dval)
 {
   int which;
   struct type *templ_type;
@@ -8355,7 +8344,7 @@ ada_is_redundant_index_type_desc (struct type *array_type,
 
 static struct type *
 to_fixed_array_type (struct type *type0, struct value *dval,
-                     int ignore_too_big)
+                    int ignore_too_big)
 {
   struct type *index_type_desc;
   struct type *result;
@@ -8368,7 +8357,11 @@ to_fixed_array_type (struct type *type0, struct value *dval,
 
   constrained_packed_array_p = ada_is_constrained_packed_array_type (type0);
   if (constrained_packed_array_p)
-    type0 = decode_constrained_packed_array_type (type0);
+    {
+      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);
 
@@ -8411,26 +8404,26 @@ to_fixed_array_type (struct type *type0, struct value *dval,
       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.  */
+        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.  */
+        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;
+       result = type0;
       else
-        result = create_array_type (alloc_type_copy (type0),
-                                    elt_type, type0->index_type ());
+       result = create_array_type (alloc_type_copy (type0),
+                                   elt_type, type0->index_type ());
     }
   else
     {
@@ -8439,34 +8432,34 @@ to_fixed_array_type (struct type *type0, struct value *dval,
 
       elt_type0 = type0;
       for (i = index_type_desc->num_fields (); i > 0; i -= 1)
-        elt_type0 = TYPE_TARGET_TYPE (elt_type0);
+       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.  */
+        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.  */
+        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);
+       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);
+       {
+         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);
+         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"));
+       error (_("array type with dynamic size is larger than varsize-limit"));
     }
 
   /* We want to preserve the type name.  This can be useful when
@@ -8486,7 +8479,7 @@ to_fixed_array_type (struct type *type0, struct value *dval,
       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)++;
+       TYPE_LENGTH (result)++;
     }
 
   result->set_is_fixed_instance (true);
@@ -8508,7 +8501,7 @@ to_fixed_array_type (struct type *type0, struct value *dval,
    
 static struct type *
 ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
-                   CORE_ADDR address, struct value *dval, int check_tag)
+                  CORE_ADDR address, struct value *dval, int check_tag)
 {
   type = ada_check_typedef (type);
 
@@ -8522,19 +8515,19 @@ ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
       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 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,
@@ -8545,24 +8538,24 @@ ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
              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
+           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
+         }
+
+       /* 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;
+           LONGEST size;
 
-            xsnprintf (xvz_name, strlen (name) + 7, "%s___XVZ", name);
+           xsnprintf (xvz_name, strlen (name) + 7, "%s___XVZ", name);
            try
              {
                xvz_found = get_int_var_value (xvz_name, size);
@@ -8579,43 +8572,43 @@ ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
                             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.  */
+           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;
+             }
+         }
+       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;
+       return type;
       else
-        return to_fixed_variant_branch_type (type, valaddr, address, dval);
+       return to_fixed_variant_branch_type (type, valaddr, address, dval);
     }
 }
 
@@ -8641,7 +8634,7 @@ ada_to_fixed_type_1 (struct type *type, const gdb_byte *valaddr,
 
 struct type *
 ada_to_fixed_type (struct type *type, const gdb_byte *valaddr,
-                   CORE_ADDR address, struct value *dval, int check_tag)
+                  CORE_ADDR address, struct value *dval, int check_tag)
 
 {
   struct type *fixed_type =
@@ -8695,15 +8688,15 @@ to_static_fixed_type (struct type *type0)
     case TYPE_CODE_STRUCT:
       type = dynamic_template_type (type0);
       if (type != NULL)
-        return template_to_static_fixed_type (type);
+       return template_to_static_fixed_type (type);
       else
-        return template_to_static_fixed_type (type0);
+       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);
+       return template_to_static_fixed_type (type);
       else
-        return template_to_static_fixed_type (type0);
+       return template_to_static_fixed_type (type0);
     }
 }
 
@@ -8725,9 +8718,9 @@ static_unwrap_type (struct type *type)
       struct type *raw_real_type = ada_get_base_type (type);
 
       if (raw_real_type == type)
-        return type;
+       return type;
       else
-        return to_static_fixed_type (raw_real_type);
+       return to_static_fixed_type (raw_real_type);
     }
 }
 
@@ -8771,7 +8764,7 @@ ada_check_typedef (struct type *type)
       struct type *type1 = ada_find_any_type (name);
 
       if (type1 == NULL)
-        return type;
+       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
@@ -8792,7 +8785,7 @@ ada_check_typedef (struct type *type)
 
 static struct value *
 ada_to_fixed_value_create (struct type *type0, CORE_ADDR address,
-                           struct value *val0)
+                          struct value *val0)
 {
   struct type *type = ada_to_fixed_type (type0, 0, address, NULL, 1);
 
@@ -8861,15 +8854,15 @@ pos_atr (struct value *arg)
 {
   struct value *val = coerce_ref (arg);
   struct type *type = value_type (val);
-  LONGEST result;
 
   if (!discrete_type_p (type))
     error (_("'POS only defined on discrete types"));
 
-  if (!discrete_position (type, value_as_long (val), &result))
+  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;
+  return *result;
 }
 
 static struct value *
@@ -8889,15 +8882,18 @@ val_atr (struct type *type, LONGEST val)
   if (type->code () == TYPE_CODE_ENUM)
     {
       if (val < 0 || val >= type->num_fields ())
-        error (_("argument to 'VAL out of range"));
+       error (_("argument to 'VAL out of range"));
       val = TYPE_FIELD_ENUMVAL (type, val);
     }
   return value_from_longest (type, val);
 }
 
 static struct value *
-value_val_atr (struct type *type, struct value *arg)
+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)))
@@ -8907,7 +8903,7 @@ value_val_atr (struct type *type, struct value *arg)
 }
 \f
 
-                                /* Evaluation */
+                               /* Evaluation */
 
 /* True if TYPE appears to be an Ada character type.
    [At the moment, this is true only for Character and Wide_Character;
@@ -8927,12 +8923,12 @@ ada_is_character_type (struct type *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));
+         && (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.  */
@@ -8944,7 +8940,7 @@ ada_is_string_type (struct type *type)
   if (type != NULL
       && type->code () != TYPE_CODE_PTR
       && (ada_is_simple_array_type (type)
-          || ada_is_array_descriptor_type (type))
+         || ada_is_array_descriptor_type (type))
       && ada_array_arity (type) == 1)
     {
       struct type *elttype = ada_array_element_type (type, 1);
@@ -8979,8 +8975,8 @@ ada_is_aligner_type (struct type *type)
     return 0;
 
   return (type->code () == TYPE_CODE_STRUCT
-          && type->num_fields () == 1
-          && strcmp (TYPE_FIELD_NAME (type, 0), "F") == 0);
+         && type->num_fields () == 1
+         && strcmp (TYPE_FIELD_NAME (type, 0), "F") == 0);
 }
 
 /* If there is an ___XVS-convention type parallel to SUBTYPE, return
@@ -9052,9 +9048,9 @@ 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);
+                                  valaddr +
+                                  TYPE_FIELD_BITPOS (type,
+                                                     0) / TARGET_CHAR_BIT);
   else
     return valaddr;
 }
@@ -9066,8 +9062,7 @@ ada_aligned_value_addr (struct type *type, const gdb_byte *valaddr)
 const char *
 ada_enum_name (const char *name)
 {
-  static char *result;
-  static size_t result_len = 0;
+  static std::string storage;
   const char *tmp;
 
   /* First, unqualify the enumeration name:
@@ -9085,12 +9080,12 @@ ada_enum_name (const char *name)
   else
     {
       while ((tmp = strstr (name, "__")) != NULL)
-        {
-          if (isdigit (tmp[2]))
-            break;
-          else
-            name = tmp + 2;
-        }
+       {
+         if (isdigit (tmp[2]))
+           break;
+         else
+           name = tmp + 2;
+       }
     }
 
   if (name[0] == 'Q')
@@ -9098,30 +9093,28 @@ ada_enum_name (const char *name)
       int v;
 
       if (name[1] == 'U' || name[1] == 'W')
-        {
-          if (sscanf (name + 2, "%x", &v) != 1)
-            return name;
-        }
+       {
+         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')
        {
-         GROW_VECT (result, result_len, 4);
-         xsnprintf (result, result_len, "'%c'", name[1]);
-         return result;
+         storage = string_printf ("'%c'", name[1]);
+         return storage.c_str ();
        }
       else
-        return name;
+       return name;
 
-      GROW_VECT (result, result_len, 16);
       if (isascii (v) && isprint (v))
-        xsnprintf (result, result_len, "'%c'", v);
+       storage = string_printf ("'%c'", v);
       else if (name[1] == 'U')
-        xsnprintf (result, result_len, "[\"%02x\"]", v);
+       storage = string_printf ("[\"%02x\"]", v);
       else
-        xsnprintf (result, result_len, "[\"%04x\"]", v);
+       storage = string_printf ("[\"%04x\"]", v);
 
-      return result;
+      return storage.c_str ();
     }
   else
     {
@@ -9129,12 +9122,10 @@ ada_enum_name (const char *name)
       if (tmp == NULL)
        tmp = strstr (name, "$");
       if (tmp != NULL)
-        {
-          GROW_VECT (result, result_len, tmp - name + 1);
-          strncpy (result, name, tmp - name);
-          result[tmp - name] = '\0';
-          return result;
-        }
+       {
+         storage = std::string (name, tmp - name);
+         return storage.c_str ();
+       }
 
       return name;
     }
@@ -9171,7 +9162,7 @@ unwrap_value (struct value *val)
   else
     {
       struct type *raw_real_type =
-        ada_check_typedef (ada_get_base_type (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.  */
@@ -9180,39 +9171,13 @@ unwrap_value (struct value *val)
        return val;
 
       return
-        coerce_unspec_val_to_type
-        (val, ada_to_fixed_type (raw_real_type, 0,
-                                 value_address (val),
-                                 NULL, 1));
+       coerce_unspec_val_to_type
+       (val, ada_to_fixed_type (raw_real_type, 0,
+                                value_address (val),
+                                NULL, 1));
     }
 }
 
-static struct value *
-cast_from_fixed (struct type *type, struct value *arg)
-{
-  struct value *scale = ada_scaling_factor (value_type (arg));
-  arg = value_cast (value_type (scale), arg);
-
-  arg = value_binop (arg, scale, BINOP_MUL);
-  return value_cast (type, arg);
-}
-
-static struct value *
-cast_to_fixed (struct type *type, struct value *arg)
-{
-  if (type == value_type (arg))
-    return arg;
-
-  struct value *scale = ada_scaling_factor (type);
-  if (ada_is_gnat_encoded_fixed_point_type (value_type (arg)))
-    arg = cast_from_fixed (value_type (scale), arg);
-  else
-    arg = value_cast (value_type (scale), arg);
-
-  arg = value_binop (arg, scale, BINOP_DIV);
-  return value_cast (type, arg);
-}
-
 /* Given two array types T1 and T2, return nonzero iff both arrays
    contain the same number of elements.  */
 
@@ -9317,8 +9282,8 @@ coerce_for_assign (struct type *type, struct value *val)
        }
 
       if (TYPE_LENGTH (TYPE_TARGET_TYPE (type2))
-          != TYPE_LENGTH (TYPE_TARGET_TYPE (type)))
-        error (_("Incompatible types in assignment"));
+         != TYPE_LENGTH (TYPE_TARGET_TYPE (type)))
+       error (_("Incompatible types in assignment"));
       deprecated_set_value_type (val, type);
     }
   return val;
@@ -9363,12 +9328,12 @@ ada_value_binop (struct value *arg1, struct value *arg2, enum exp_opcode op)
     case BINOP_DIV:
       v = v1 / v2;
       if (!TRUNCATION_TOWARDS_ZERO && v1 * (v1 % v2) < 0)
-        v += v > 0 ? -1 : 1;
+       v += v > 0 ? -1 : 1;
       break;
     case BINOP_REM:
       v = v1 % v2;
       if (v * v1 < 0)
-        v -= v2;
+       v -= v2;
       break;
     default:
       /* Should not reach this point.  */
@@ -9377,7 +9342,7 @@ ada_value_binop (struct value *arg1, struct value *arg2, enum exp_opcode op)
 
   val = allocate_value (type1);
   store_unsigned_integer (value_contents_raw (val),
-                          TYPE_LENGTH (value_type (val)),
+                         TYPE_LENGTH (value_type (val)),
                          type_byte_order (type1), v);
   return val;
 }
@@ -9391,7 +9356,7 @@ ada_value_equal (struct value *arg1, struct value *arg2)
       struct type *arg1_type, *arg2_type;
 
       /* Automatically dereference any array reference before
-         we attempt to perform the comparison.  */
+        we attempt to perform the comparison.  */
       arg1 = ada_coerce_ref (arg1);
       arg2 = ada_coerce_ref (arg2);
 
@@ -9402,11 +9367,11 @@ ada_value_equal (struct value *arg1, struct value *arg2)
       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"));
+         || 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.  */
+        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);
@@ -9414,34 +9379,6 @@ ada_value_equal (struct value *arg1, struct value *arg2)
   return value_equal (arg1, arg2);
 }
 
-/* Total number of component associations in the aggregate starting at
-   index PC in EXP.  Assumes that index PC is the start of an
-   OP_AGGREGATE.  */
-
-static int
-num_component_specs (struct expression *exp, int pc)
-{
-  int n, m, i;
-
-  m = exp->elts[pc + 1].longconst;
-  pc += 3;
-  n = 0;
-  for (i = 0; i < m; i += 1)
-    {
-      switch (exp->elts[pc].opcode) 
-       {
-       default:
-         n += 1;
-         break;
-       case OP_CHOICES:
-         n += exp->elts[pc + 1].longconst;
-         break;
-       }
-      ada_evaluate_subexp (NULL, exp, &pc, EVAL_SKIP);
-    }
-  return n;
-}
-
 /* Assign the result of evaluating EXP starting at *POS to the INDEXth 
    component of LHS (a simple array or a record), updating *POS past
    the expression, assuming that LHS is contained in CONTAINER.  Does
@@ -9495,9 +9432,6 @@ assign_aggregate (struct value *container,
   struct type *lhs_type;
   int n = exp->elts[*pos+1].longconst;
   LONGEST low_index, high_index;
-  int num_specs;
-  LONGEST *indices;
-  int max_indices, num_indices;
   int i;
 
   *pos += 3;
@@ -9531,32 +9465,27 @@ assign_aggregate (struct value *container,
   else
     error (_("Left-hand side must be array or record."));
 
-  num_specs = num_component_specs (exp, *pos - 3);
-  max_indices = 4 * num_specs + 4;
-  indices = XALLOCAVEC (LONGEST, max_indices);
+  std::vector<LONGEST> indices (4);
   indices[0] = indices[1] = low_index - 1;
   indices[2] = indices[3] = high_index + 1;
-  num_indices = 4;
 
   for (i = 0; i < n; i += 1)
     {
       switch (exp->elts[*pos].opcode)
        {
          case OP_CHOICES:
-           aggregate_assign_from_choices (container, lhs, exp, pos, indices, 
-                                          &num_indices, max_indices,
+           aggregate_assign_from_choices (container, lhs, exp, pos, indices,
                                           low_index, high_index);
            break;
          case OP_POSITIONAL:
            aggregate_assign_positional (container, lhs, exp, pos, indices,
-                                        &num_indices, max_indices,
                                         low_index, high_index);
            break;
          case OP_OTHERS:
            if (i != n-1)
              error (_("Misplaced 'others' clause"));
-           aggregate_assign_others (container, lhs, exp, pos, indices, 
-                                    num_indices, low_index, high_index);
+           aggregate_assign_others (container, lhs, exp, pos, indices,
+                                    low_index, high_index);
            break;
          default:
            error (_("Internal error: bad aggregate clause"));
@@ -9568,15 +9497,14 @@ assign_aggregate (struct value *container,
              
 /* Assign into the component of LHS indexed by the OP_POSITIONAL
    construct at *POS, updating *POS past the construct, given that
-   the positions are relative to lower bound LOW, where HIGH is the 
-   upper bound.  Record the position in INDICES[0 .. MAX_INDICES-1]
-   updating *NUM_INDICES as needed.  CONTAINER is as for
+   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.  */
 static void
 aggregate_assign_positional (struct value *container,
                             struct value *lhs, struct expression *exp,
-                            int *pos, LONGEST *indices, int *num_indices,
-                            int max_indices, LONGEST low, LONGEST high) 
+                            int *pos, std::vector<LONGEST> &indices,
+                            LONGEST low, LONGEST high)
 {
   LONGEST ind = longest_to_int (exp->elts[*pos + 1].longconst) + low;
   
@@ -9584,7 +9512,7 @@ aggregate_assign_positional (struct value *container,
     warning (_("Extra components in aggregate ignored."));
   if (ind <= high)
     {
-      add_component_interval (ind, ind, indices, num_indices, max_indices);
+      add_component_interval (ind, ind, indices);
       *pos += 3;
       assign_component (container, lhs, ind, exp, pos);
     }
@@ -9595,13 +9523,12 @@ aggregate_assign_positional (struct value *container,
 /* 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[0 .. MAX_INDICES-1], updating *NUM_INDICES as
-   needed.  CONTAINER is as for assign_aggregate.  */
+   to in INDICES.  CONTAINER is as for assign_aggregate.  */
 static void
 aggregate_assign_from_choices (struct value *container,
                               struct value *lhs, struct expression *exp,
-                              int *pos, LONGEST *indices, int *num_indices,
-                              int max_indices, LONGEST low, LONGEST high) 
+                              int *pos, std::vector<LONGEST> &indices,
+                              LONGEST low, LONGEST high)
 {
   int j;
   int n_choices = longest_to_int (exp->elts[*pos+1].longconst);
@@ -9661,8 +9588,7 @@ aggregate_assign_from_choices (struct value *container,
       if (lower <= upper && (lower < low || upper > high))
        error (_("Index in component association out of bounds."));
 
-      add_component_interval (lower, upper, indices, num_indices,
-                             max_indices);
+      add_component_interval (lower, upper, indices);
       while (lower <= upper)
        {
          int pos1;
@@ -9677,17 +9603,18 @@ aggregate_assign_from_choices (struct value *container,
 /* 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[0 .. NUM_INDICES-1].  Updates *POS to after the 
-   OP_OTHERS clause.  CONTAINER is as for assign_aggregate.  */
+   are in INDICES.  Updates *POS to after the OP_OTHERS clause.
+   CONTAINER is as for assign_aggregate.  */
 static void
 aggregate_assign_others (struct value *container,
                         struct value *lhs, struct expression *exp,
-                        int *pos, LONGEST *indices, int num_indices,
+                        int *pos, std::vector<LONGEST> &indices,
                         LONGEST low, LONGEST high) 
 {
   int i;
   int expr_pc = *pos + 1;
   
+  int num_indices = indices.size ();
   for (i = 0; i < num_indices - 2; i += 2)
     {
       LONGEST ind;
@@ -9703,22 +9630,22 @@ aggregate_assign_others (struct value *container,
   ada_evaluate_subexp (NULL, exp, pos, EVAL_SKIP);
 }
 
-/* Add the interval [LOW .. HIGH] to the sorted set of intervals 
-   [ INDICES[0] .. INDICES[1] ],..., [ INDICES[*SIZE-2] .. INDICES[*SIZE-1] ],
-   modifying *SIZE as needed.  It is an error if *SIZE exceeds
-   MAX_SIZE.  The resulting intervals do not overlap.  */
+/* 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, 
-                       LONGEST* indices, int *size, int max_size)
+                       std::vector<LONGEST> &indices)
 {
   int i, j;
 
-  for (i = 0; i < *size; i += 2) {
+  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)
+       for (kh = i + 2; kh < size; kh += 2)
          if (high < indices[kh])
            break;
        if (low < indices[i])
@@ -9726,18 +9653,16 @@ add_component_interval (LONGEST low, LONGEST high,
        indices[i + 1] = indices[kh - 1];
        if (high > indices[i + 1])
          indices[i + 1] = high;
-       memcpy (indices + i + 2, indices + kh, *size - kh);
-       *size -= kh - i - 2;
+       memcpy (indices.data () + i + 2, indices.data () + kh, size - kh);
+       indices.resize (kh - i - 2);
        return;
       }
     else if (high < indices[i])
       break;
   }
        
-  if (*size == max_size)
-    error (_("Internal error: miscounted aggregate components."));
-  *size += 2;
-  for (j = *size-1; j >= i+2; j -= 1)
+  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;
@@ -9752,12 +9677,6 @@ ada_value_cast (struct type *type, struct value *arg2)
   if (type == ada_check_typedef (value_type (arg2)))
     return arg2;
 
-  if (ada_is_gnat_encoded_fixed_point_type (type))
-    return cast_to_fixed (type, arg2);
-
-  if (ada_is_gnat_encoded_fixed_point_type (value_type (arg2)))
-    return cast_from_fixed (type, arg2);
-
   return value_cast (type, arg2);
 }
 
@@ -9803,10 +9722,10 @@ ada_value_cast (struct type *type, struct value *arg2)
     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;
+         case Empty is
+            when True => null;
+            when False => Value : Integer;
+         end case;
        end record;
        Yes : Rec := (Empty => False, Value => 1);
        No  : Rec := (empty => True);
@@ -9823,15 +9742,15 @@ ada_value_cast (struct type *type, struct value *arg2)
     type would look like this:
 
        type Rec is record
-          Empty : Boolean;
-          Value : Integer;
+         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;
+         Empty : Boolean;
        end record;
 
     Things become a little more complicated when trying to fix an entity
@@ -9871,11 +9790,11 @@ ada_value_cast (struct type *type, struct value *arg2)
     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);
+       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
@@ -9894,19 +9813,19 @@ ada_value_cast (struct type *type, struct value *arg2)
     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;
+       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));
+       Hello : Wrapper_Array := (others => (Has_Length => True,
+                                            Data => (others => 17),
+                                            Length => 1));
 
 
     The debugging info would describe variable Hello as being an
@@ -9926,11 +9845,11 @@ ada_value_cast (struct type *type, struct value *arg2)
 
     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);
+       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
@@ -9944,16 +9863,16 @@ ada_value_cast (struct type *type, struct value *arg2)
     (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;
+         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);
+                                   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
@@ -9978,14 +9897,14 @@ ada_value_cast (struct type *type, struct value *arg2)
     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 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;
+       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.
@@ -10032,32 +9951,32 @@ ada_evaluate_subexp_for_cast (expression *exp, int *pos,
 
       value *val;
       if (exp->elts[pc].opcode == OP_VAR_MSYM_VALUE)
-        {
-          if (noside == EVAL_AVOID_SIDE_EFFECTS)
-            return value_zero (to_type, not_lval);
-
-          val = evaluate_var_msym_value (noside,
-                                         exp->elts[pc + 1].objfile,
-                                         exp->elts[pc + 2].msymbol);
-        }
+       {
+         if (noside == EVAL_AVOID_SIDE_EFFECTS)
+           return value_zero (to_type, not_lval);
+
+         val = evaluate_var_msym_value (noside,
+                                        exp->elts[pc + 1].objfile,
+                                        exp->elts[pc + 2].msymbol);
+       }
       else
-        val = evaluate_var_value (noside,
-                                  exp->elts[pc + 1].block,
-                                  exp->elts[pc + 2].symbol);
+       val = evaluate_var_value (noside,
+                                 exp->elts[pc + 1].block,
+                                 exp->elts[pc + 2].symbol);
 
       if (noside == EVAL_SKIP)
-        return eval_skip_value (exp);
+       return eval_skip_value (exp);
 
       val = ada_value_cast (to_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;
-        }
+       {
+         if (value_lazy (val))
+           value_fetch_lazy (val);
+         VALUE_LVAL (val) = not_lval;
+       }
       return val;
     }
 
@@ -10067,59 +9986,567 @@ ada_evaluate_subexp_for_cast (expression *exp, int *pos,
   return ada_value_cast (to_type, val);
 }
 
-/* Implement the evaluate_exp routine in the exp_descriptor structure
-   for the Ada language.  */
+/* A helper function for TERNOP_IN_RANGE.  */
 
-static struct value *
-ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
-                     int *pos, enum noside noside)
+static value *
+eval_ternop_in_range (struct type *expect_type, struct expression *exp,
+                     enum noside noside,
+                     value *arg1, value *arg2, value *arg3)
 {
-  enum exp_opcode op;
-  int tem;
-  int pc;
-  int preeval_pos;
-  struct value *arg1 = NULL, *arg2 = NULL, *arg3;
-  struct type *type;
-  int nargs, oplen;
-  struct value **argvec;
+  if (noside == EVAL_SKIP)
+    return eval_skip_value (exp);
 
-  pc = *pos;
-  *pos += 1;
-  op = exp->elts[pc].opcode;
+  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)));
+}
 
-  switch (op)
-    {
-    default:
-      *pos -= 1;
-      arg1 = evaluate_subexp_standard (expect_type, exp, pos, noside);
+/* A helper function for UNOP_NEG.  */
 
-      if (noside == EVAL_NORMAL)
-       arg1 = unwrap_value (arg1);
+value *
+ada_unop_neg (struct type *expect_type,
+             struct expression *exp,
+             enum noside noside, enum exp_opcode op,
+             struct value *arg1)
+{
+  if (noside == EVAL_SKIP)
+    return eval_skip_value (exp);
+  unop_promote (exp->language_defn, exp->gdbarch, &arg1);
+  return value_neg (arg1);
+}
 
-      /* 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.
+/* A helper function for UNOP_IN_RANGE.  */
 
-         Similarly, we need to perform the conversion from OP_LONG
-         ourselves.  */
-      if ((op == OP_FLOAT || op == OP_LONG) && expect_type != NULL)
-        arg1 = ada_value_cast (expect_type, arg1);
+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)
+{
+  if (noside == EVAL_SKIP)
+    return eval_skip_value (exp);
 
-      return arg1;
+  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 OP_STRING:
-      {
-        struct value *result;
-
-        *pos -= 1;
-        result = evaluate_subexp_standard (expect_type, exp, pos, 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;
+    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_SKIP)
+    return eval_skip_value (exp);
+  else 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.  */
+
+static 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.  */
+
+static 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.  */
+
+static 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.  */
+
+static 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.  */
+
+static 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 == OP_ATR_MIN ? BINOP_MIN : BINOP_MAX);
+    }
+}
+
+/* A helper function for BINOP_EXP.  */
+
+static 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
+{
+
+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);
+}
+
+}
+
+/* Implement the evaluate_exp routine in the exp_descriptor structure
+   for the Ada language.  */
+
+static struct value *
+ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
+                    int *pos, enum noside noside)
+{
+  enum exp_opcode op;
+  int tem;
+  int pc;
+  int preeval_pos;
+  struct value *arg1 = NULL, *arg2 = NULL, *arg3;
+  struct type *type;
+  int nargs, oplen;
+  struct value **argvec;
+
+  pc = *pos;
+  *pos += 1;
+  op = exp->elts[pc].opcode;
+
+  switch (op)
+    {
+    default:
+      *pos -= 1;
+      arg1 = evaluate_subexp_standard (expect_type, exp, pos, noside);
+
+      if (noside == EVAL_NORMAL)
+       arg1 = unwrap_value (arg1);
+
+      /* 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 ((op == OP_FLOAT || op == OP_LONG) && expect_type != NULL)
+       arg1 = ada_value_cast (expect_type, arg1);
+
+      return arg1;
+
+    case OP_STRING:
+      {
+       struct value *result;
+
+       *pos -= 1;
+       result = evaluate_subexp_standard (expect_type, exp, pos, 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;
       }
 
     case UNOP_CAST:
@@ -10142,80 +10569,80 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *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.  */
+        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.  */
       type = value_type (arg1);
       if (VALUE_LVAL (arg1) == lval_internalvar)
-         type = NULL;
+        type = NULL;
       arg2 = evaluate_subexp (type, exp, pos, noside);
       if (noside == EVAL_SKIP || noside == EVAL_AVOID_SIDE_EFFECTS)
-        return arg1;
+       return arg1;
       if (VALUE_LVAL (arg1) == lval_internalvar)
        {
          /* Nothing.  */
        }
-      else if (ada_is_gnat_encoded_fixed_point_type (value_type (arg1)))
-        arg2 = cast_to_fixed (value_type (arg1), arg2);
-      else if (ada_is_gnat_encoded_fixed_point_type (value_type (arg2)))
-        error
-          (_("Fixed-point values must be assigned to fixed-point variables"));
       else
-        arg2 = coerce_for_assign (value_type (arg1), arg2);
+       arg2 = coerce_for_assign (value_type (arg1), arg2);
       return ada_value_assign (arg1, arg2);
 
     case BINOP_ADD:
       arg1 = evaluate_subexp_with_coercion (exp, pos, noside);
       arg2 = evaluate_subexp_with_coercion (exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       if (value_type (arg1)->code () == TYPE_CODE_PTR)
-        return (value_from_longest
-                 (value_type (arg1),
-                  value_as_long (arg1) + value_as_long (arg2)));
+       return (value_from_longest
+                (value_type (arg1),
+                 value_as_long (arg1) + value_as_long (arg2)));
       if (value_type (arg2)->code () == TYPE_CODE_PTR)
-        return (value_from_longest
-                 (value_type (arg2),
-                  value_as_long (arg1) + value_as_long (arg2)));
-      if ((ada_is_gnat_encoded_fixed_point_type (value_type (arg1))
-           || ada_is_gnat_encoded_fixed_point_type (value_type (arg2)))
-          && value_type (arg1) != value_type (arg2))
-        error (_("Operands of fixed-point addition must have the same type"));
-      /* Do the addition, and cast the result to the type of the first
-         argument.  We cannot cast the result to a reference type, so if
-         ARG1 is a reference type, find its underlying type.  */
+       return (value_from_longest
+                (value_type (arg2),
+                 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.  */
       type = value_type (arg1);
       while (type->code () == TYPE_CODE_REF)
-        type = TYPE_TARGET_TYPE (type);
+       type = TYPE_TARGET_TYPE (type);
       binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
-      return value_cast (type, value_binop (arg1, arg2, BINOP_ADD));
+      arg1 = value_binop (arg1, arg2, BINOP_ADD);
+      /* We need to special-case the result of adding to 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;
 
     case BINOP_SUB:
       arg1 = evaluate_subexp_with_coercion (exp, pos, noside);
       arg2 = evaluate_subexp_with_coercion (exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       if (value_type (arg1)->code () == TYPE_CODE_PTR)
-        return (value_from_longest
-                 (value_type (arg1),
-                  value_as_long (arg1) - value_as_long (arg2)));
+       return (value_from_longest
+                (value_type (arg1),
+                 value_as_long (arg1) - value_as_long (arg2)));
       if (value_type (arg2)->code () == TYPE_CODE_PTR)
-        return (value_from_longest
-                 (value_type (arg2),
-                  value_as_long (arg1) - value_as_long (arg2)));
-      if ((ada_is_gnat_encoded_fixed_point_type (value_type (arg1))
-           || ada_is_gnat_encoded_fixed_point_type (value_type (arg2)))
-          && value_type (arg1) != value_type (arg2))
-        error (_("Operands of fixed-point subtraction "
-                "must have the same type"));
-      /* Do the substraction, and cast the result to the type of the first
-         argument.  We cannot cast the result to a reference type, so if
-         ARG1 is a reference type, find its underlying type.  */
+       return (value_from_longest
+                (value_type (arg2),
+                 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.  */
       type = value_type (arg1);
       while (type->code () == TYPE_CODE_REF)
-        type = TYPE_TARGET_TYPE (type);
+       type = TYPE_TARGET_TYPE (type);
       binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
-      return value_cast (type, value_binop (arg1, arg2, BINOP_SUB));
+      arg1 = value_binop (arg1, arg2, BINOP_SUB);
+      /* We need to special-case the result of adding to 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;
 
     case BINOP_MUL:
     case BINOP_DIV:
@@ -10224,105 +10651,74 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       arg2 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      else if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        {
-          binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
-          return value_zero (value_type (arg1), not_lval);
-        }
-      else
-        {
-          type = builtin_type (exp->gdbarch)->builtin_double;
-          if (ada_is_gnat_encoded_fixed_point_type (value_type (arg1)))
-            arg1 = cast_from_fixed (type, arg1);
-          if (ada_is_gnat_encoded_fixed_point_type (value_type (arg2)))
-            arg2 = cast_from_fixed (type, arg2);
-          binop_promote (exp->language_defn, exp->gdbarch, &arg1, &arg2);
-          return ada_value_binop (arg1, arg2, op);
-        }
+       goto nosideret;
+      return ada_mult_binop (expect_type, exp, noside, op,
+                            arg1, arg2);
 
     case BINOP_EQUAL:
     case BINOP_NOTEQUAL:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       arg2 = evaluate_subexp (value_type (arg1), exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      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;
-      type = language_bool_type (exp->language_defn, exp->gdbarch);
-      return value_from_longest (type, (LONGEST) tem);
+       goto nosideret;
+      return ada_equal_binop (expect_type, exp, noside, op, arg1, arg2);
 
     case UNOP_NEG:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
-      if (noside == EVAL_SKIP)
-        goto nosideret;
-      else if (ada_is_gnat_encoded_fixed_point_type (value_type (arg1)))
-        return value_cast (value_type (arg1), value_neg (arg1));
-      else
-       {
-         unop_promote (exp->language_defn, exp->gdbarch, &arg1);
-         return value_neg (arg1);
-       }
+      return ada_unop_neg (expect_type, exp, noside, op, arg1);
 
     case BINOP_LOGICAL_AND:
     case BINOP_LOGICAL_OR:
     case UNOP_LOGICAL_NOT:
       {
-        struct value *val;
+       struct value *val;
 
-        *pos -= 1;
-        val = evaluate_subexp_standard (expect_type, exp, pos, noside);
+       *pos -= 1;
+       val = evaluate_subexp_standard (expect_type, exp, pos, noside);
        type = language_bool_type (exp->language_defn, exp->gdbarch);
-        return value_cast (type, val);
+       return value_cast (type, val);
       }
 
     case BINOP_BITWISE_AND:
     case BINOP_BITWISE_IOR:
     case BINOP_BITWISE_XOR:
       {
-        struct value *val;
+       struct value *val;
 
        arg1 = evaluate_subexp (nullptr, exp, pos, EVAL_AVOID_SIDE_EFFECTS);
        *pos = pc;
-        val = evaluate_subexp_standard (expect_type, exp, pos, noside);
+       val = evaluate_subexp_standard (expect_type, exp, pos, noside);
 
-        return value_cast (value_type (arg1), val);
+       return value_cast (value_type (arg1), val);
       }
 
     case OP_VAR_VALUE:
       *pos -= 1;
 
       if (noside == EVAL_SKIP)
-        {
-          *pos += 4;
-          goto nosideret;
-        }
+       {
+         *pos += 4;
+         goto nosideret;
+       }
 
       if (SYMBOL_DOMAIN (exp->elts[pc + 2].symbol) == 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"),
-               exp->elts[pc + 2].symbol->print_name ());
+       /* 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"),
+              exp->elts[pc + 2].symbol->print_name ());
 
       if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        {
-          type = static_unwrap_type (SYMBOL_TYPE (exp->elts[pc + 2].symbol));
-          /* 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)))
+       {
+         type = static_unwrap_type (SYMBOL_TYPE (exp->elts[pc + 2].symbol));
+         /* 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
@@ -10384,7 +10780,7 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
              *pos += 4;
              return value_zero (to_static_fixed_type (type), not_lval);
            }
-        }
+       }
 
       arg1 = evaluate_subexp_standard (expect_type, exp, pos, noside);
       return ada_to_fixed_value (arg1);
@@ -10393,33 +10789,33 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       (*pos) += 2;
 
       /* Allocate arg vector, including space for the function to be
-         called in argvec[0] and a terminating NULL.  */
+        called in argvec[0] and a terminating NULL.  */
       nargs = longest_to_int (exp->elts[pc + 1].longconst);
       argvec = XALLOCAVEC (struct value *, nargs + 2);
 
       if (exp->elts[*pos].opcode == OP_VAR_VALUE
-          && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
-        error (_("Unexpected unresolved symbol, %s, during evaluation"),
-               exp->elts[pc + 5].symbol->print_name ());
+         && SYMBOL_DOMAIN (exp->elts[pc + 5].symbol) == UNDEF_DOMAIN)
+       error (_("Unexpected unresolved symbol, %s, during evaluation"),
+              exp->elts[pc + 5].symbol->print_name ());
       else
-        {
-          for (tem = 0; tem <= nargs; tem += 1)
+       {
+         for (tem = 0; tem <= nargs; tem += 1)
            argvec[tem] = evaluate_subexp (nullptr, exp, pos, noside);
          argvec[tem] = 0;
 
-          if (noside == EVAL_SKIP)
-            goto nosideret;
-        }
+         if (noside == EVAL_SKIP)
+           goto nosideret;
+       }
 
       if (ada_is_constrained_packed_array_type
          (desc_base_type (value_type (argvec[0]))))
-        argvec[0] = ada_coerce_to_simple_array (argvec[0]);
+       argvec[0] = ada_coerce_to_simple_array (argvec[0]);
       else if (value_type (argvec[0])->code () == TYPE_CODE_ARRAY
-               && TYPE_FIELD_BITSIZE (value_type (argvec[0]), 0) != 0)
-        /* This is a packed array that has already been fixed, and
+              && TYPE_FIELD_BITSIZE (value_type (argvec[0]), 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 (argvec[0])->code () == TYPE_CODE_REF)
        {
          /* Make sure we dereference references so that all the code below
@@ -10441,30 +10837,30 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
        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)
-                argvec[0] = ada_value_ind (argvec[0]);
-              type = ada_check_typedef (TYPE_TARGET_TYPE (type));
-              break;
-            default:
-              error (_("cannot subscript or call something of type `%s'"),
-                     ada_type_name (value_type (argvec[0])));
-              break;
-            }
-        }
+       {
+         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)
+               argvec[0] = ada_value_ind (argvec[0]);
+             type = ada_check_typedef (TYPE_TARGET_TYPE (type));
+             break;
+           default:
+             error (_("cannot subscript or call something of type `%s'"),
+                    ada_type_name (value_type (argvec[0])));
+             break;
+           }
+       }
 
       switch (type->code ())
-        {
-        case TYPE_CODE_FUNC:
-          if (noside == EVAL_AVOID_SIDE_EFFECTS)
+       {
+       case TYPE_CODE_FUNC:
+         if (noside == EVAL_AVOID_SIDE_EFFECTS)
            {
              if (TYPE_TARGET_TYPE (type) == NULL)
                error_call_unknown_return_type (NULL);
@@ -10484,53 +10880,53 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
            return call_internal_function (exp->gdbarch, exp->language_defn,
                                           argvec[0], nargs, argvec + 1);
 
-        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
-                            (argvec[0], nargs, argvec + 1));
-          }
-        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 (argvec[0]),
-                           nargs, argvec + 1));
-        case TYPE_CODE_PTR:     /* Pointer to array */
-          if (noside == EVAL_AVOID_SIDE_EFFECTS)
-            {
+       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
+                           (argvec[0], nargs, argvec + 1));
+         }
+       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 (argvec[0]),
+                          nargs, argvec + 1));
+       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 (argvec[0],
+             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 (argvec[0],
                                                   nargs, argvec + 1));
 
-        default:
-          error (_("Attempt to index or call something other than an "
+       default:
+         error (_("Attempt to index or call something other than an "
                   "array or function"));
-        }
+       }
 
     case TERNOP_SLICE:
       {
@@ -10539,113 +10935,19 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
          = evaluate_subexp (nullptr, exp, pos, noside);
        struct value *high_bound_val
          = evaluate_subexp (nullptr, exp, pos, noside);
-       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 (noside == EVAL_SKIP)
-          goto nosideret;
-
-        /* 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_constrained_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));
+
+       if (noside == EVAL_SKIP)
+         goto nosideret;
+
+       return ada_ternop_slice (exp, noside, array, low_bound_val,
+                                high_bound_val);
       }
 
     case UNOP_IN_RANGE:
       (*pos) += 2;
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       type = check_typedef (exp->elts[pc + 1].type);
-
-      if (noside == EVAL_SKIP)
-        goto nosideret;
-
-      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)));
-        }
+      return ada_unop_in_range (expect_type, exp, noside, op, arg1, type);
 
     case BINOP_IN_BOUNDS:
       (*pos) += 2;
@@ -10653,204 +10955,53 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       arg2 = evaluate_subexp (nullptr, exp, pos, noside);
 
       if (noside == EVAL_SKIP)
-        goto nosideret;
-
-      if (noside == EVAL_AVOID_SIDE_EFFECTS)
-       {
-         type = language_bool_type (exp->language_defn, exp->gdbarch);
-         return value_zero (type, not_lval);
-       }
+       goto nosideret;
 
       tem = longest_to_int (exp->elts[pc + 1].longconst);
 
-      type = ada_index_type (value_type (arg2), tem, "range");
-      if (!type)
-       type = value_type (arg1);
-
-      arg3 = value_from_longest (type, ada_array_bound (arg2, tem, 1));
-      arg2 = value_from_longest (type, ada_array_bound (arg2, tem, 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)));
+      return ada_binop_in_bounds (exp, noside, arg1, arg2, tem);
 
     case TERNOP_IN_RANGE:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       arg2 = evaluate_subexp (nullptr, exp, pos, noside);
       arg3 = evaluate_subexp (nullptr, exp, pos, noside);
 
-      if (noside == EVAL_SKIP)
-        goto nosideret;
-
-      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)));
+      return eval_ternop_in_range (expect_type, exp, noside, arg1, arg2, arg3);
 
     case OP_ATR_FIRST:
     case OP_ATR_LAST:
     case OP_ATR_LENGTH:
       {
-        struct type *type_arg;
+       struct type *type_arg;
 
-        if (exp->elts[*pos].opcode == OP_TYPE)
-          {
+       if (exp->elts[*pos].opcode == OP_TYPE)
+         {
            evaluate_subexp (nullptr, exp, pos, EVAL_SKIP);
            arg1 = NULL;
-            type_arg = check_typedef (exp->elts[pc + 2].type);
-          }
-        else
-          {
+           type_arg = check_typedef (exp->elts[pc + 2].type);
+         }
+       else
+         {
            arg1 = evaluate_subexp (nullptr, exp, pos, noside);
            type_arg = NULL;
-          }
-
-        if (exp->elts[*pos].opcode != OP_LONG)
-          error (_("Invalid operand to '%s"), ada_attribute_name (op));
-        tem = longest_to_int (exp->elts[*pos + 2].longconst);
-        *pos += 4;
-
-        if (noside == EVAL_SKIP)
-          goto nosideret;
-       else 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);
 
-            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;
-             }
+       if (exp->elts[*pos].opcode != OP_LONG)
+         error (_("Invalid operand to '%s"), ada_attribute_name (op));
+       tem = longest_to_int (exp->elts[*pos + 2].longconst);
+       *pos += 4;
 
-            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);
-
-           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;
-             }
+       if (noside == EVAL_SKIP)
+         goto nosideret;
 
-            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);
-              }
-          }
+       return ada_unop_atr (exp, noside, op, arg1, type_arg, tem);
       }
 
     case OP_ATR_TAG:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-
-      if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        return value_zero (ada_tag_type (arg1), not_lval);
-
-      return ada_value_tag (arg1);
+       goto nosideret;
+      return ada_atr_tag (expect_type, exp, noside, op, arg1);
 
     case OP_ATR_MIN:
     case OP_ATR_MAX:
@@ -10858,29 +11009,22 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       arg2 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      else 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 == OP_ATR_MIN ? BINOP_MIN : BINOP_MAX);
-       }
+       goto nosideret;
+      return ada_binop_minmax (expect_type, exp, noside, op, arg1, arg2);
 
     case OP_ATR_MODULUS:
       {
-        struct type *type_arg = check_typedef (exp->elts[pc + 2].type);
+       struct type *type_arg = check_typedef (exp->elts[pc + 2].type);
 
        evaluate_subexp (nullptr, exp, pos, EVAL_SKIP);
        if (noside == EVAL_SKIP)
-          goto nosideret;
+         goto nosideret;
 
-        if (!ada_is_modular_type (type_arg))
-          error (_("'modulus must be applied to modular type"));
+       if (!ada_is_modular_type (type_arg))
+         error (_("'modulus must be applied to modular type"));
 
-        return value_from_longest (TYPE_TARGET_TYPE (type_arg),
-                                   ada_modulus (type_arg));
+       return value_from_longest (TYPE_TARGET_TYPE (type_arg),
+                                  ada_modulus (type_arg));
       }
 
 
@@ -10888,7 +11032,7 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       evaluate_subexp (nullptr, exp, pos, EVAL_SKIP);
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       type = builtin_type (exp->gdbarch)->builtin_int;
       if (noside == EVAL_AVOID_SIDE_EFFECTS)
        return value_zero (type, not_lval);
@@ -10897,95 +11041,62 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
 
     case OP_ATR_SIZE:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
-      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_SKIP)
-        goto nosideret;
-      else 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));
+      return ada_atr_size (expect_type, exp, noside, op, arg1);
 
     case OP_ATR_VAL:
       evaluate_subexp (nullptr, exp, pos, EVAL_SKIP);
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       type = exp->elts[pc + 2].type;
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      else if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        return value_zero (type, not_lval);
-      else
-        return value_val_atr (type, arg1);
+       goto nosideret;
+      return ada_val_atr (noside, type, arg1);
 
     case BINOP_EXP:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       arg2 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      else 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);
-       }
+       goto nosideret;
+      return ada_binop_exp (expect_type, exp, noside, op, arg1, arg2);
 
     case UNOP_PLUS:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       else
-        return arg1;
+       return arg1;
 
     case UNOP_ABS:
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
-      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;
+       goto nosideret;
+      return ada_abs (expect_type, exp, noside, op, arg1);
 
     case UNOP_IND:
       preeval_pos = *pos;
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       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 (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)
@@ -11002,9 +11113,9 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
                     (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)
+             return value_zero (type, lval_memory);
+           }
+         else if (type->code () == TYPE_CODE_INT)
            {
              /* GDB allows dereferencing an int.  */
              if (expect_type == NULL)
@@ -11017,30 +11128,30 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
                  return value_zero (expect_type, lval_memory);
                }
            }
-          else
-            error (_("Attempt to take contents of a non-pointer value."));
-        }
+         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)
+         /* 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));
-        }
+       }
 
       if (ada_is_array_descriptor_type (type))
-        /* GDB allows dereferencing GNAT array descriptors.  */
-        return ada_coerce_to_simple_array (arg1);
+       /* GDB allows dereferencing GNAT array descriptors.  */
+       return ada_coerce_to_simple_array (arg1);
       else
-        return ada_value_ind (arg1);
+       return ada_value_ind (arg1);
 
     case STRUCTOP_STRUCT:
       tem = longest_to_int (exp->elts[pc + 1].longconst);
@@ -11048,22 +11159,22 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
       preeval_pos = *pos;
       arg1 = evaluate_subexp (nullptr, exp, pos, noside);
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        {
-          struct type *type1 = value_type (arg1);
+       {
+         struct type *type1 = value_type (arg1);
 
-          if (ada_is_tagged_type (type1, 1))
-            {
-              type = ada_lookup_struct_elt_type (type1,
-                                                 &exp->elts[pc + 2].string,
-                                                 1, 1);
+         if (ada_is_tagged_type (type1, 1))
+           {
+             type = ada_lookup_struct_elt_type (type1,
+                                                &exp->elts[pc + 2].string,
+                                                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)
+             if (type == NULL)
                {
                  arg1
                    = evaluate_subexp (nullptr, exp, &preeval_pos, EVAL_NORMAL);
@@ -11073,14 +11184,14 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
                  arg1 = unwrap_value (arg1);
                  type = value_type (ada_to_fixed_value (arg1));
                }
-            }
-          else
-            type =
-              ada_lookup_struct_elt_type (type1, &exp->elts[pc + 2].string, 1,
-                                          0);
-
-          return value_zero (ada_aligned_type (type), lval_memory);
-        }
+           }
+         else
+           type =
+             ada_lookup_struct_elt_type (type1, &exp->elts[pc + 2].string, 1,
+                                         0);
+
+         return value_zero (ada_aligned_type (type), lval_memory);
+       }
       else
        {
          arg1 = ada_value_struct_elt (arg1, &exp->elts[pc + 2].string, 0);
@@ -11090,14 +11201,14 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
 
     case OP_TYPE:
       /* The value is not supposed to be used.  This is here to make it
-         easier to accommodate expressions that contain types.  */
+        easier to accommodate expressions that contain types.  */
       (*pos) += 2;
       if (noside == EVAL_SKIP)
-        goto nosideret;
+       goto nosideret;
       else if (noside == EVAL_AVOID_SIDE_EFFECTS)
-        return allocate_value (exp->elts[pc + 1].type);
+       return allocate_value (exp->elts[pc + 1].type);
       else
-        error (_("Attempt to use a type name as an expression"));
+       error (_("Attempt to use a type name as an expression"));
 
     case OP_AGGREGATE:
     case OP_CHOICES:
@@ -11130,41 +11241,6 @@ nosideret:
 }
 \f
 
-                                /* Fixed point */
-
-/* If TYPE encodes an Ada fixed-point type, return the suffix of the
-   type name that encodes the 'small and 'delta information.
-   Otherwise, return NULL.  */
-
-static const char *
-gnat_encoded_fixed_type_info (struct type *type)
-{
-  const char *name = ada_type_name (type);
-  enum type_code code = (type == NULL) ? TYPE_CODE_UNDEF : type->code ();
-
-  if ((code == TYPE_CODE_INT || code == TYPE_CODE_RANGE) && name != NULL)
-    {
-      const char *tail = strstr (name, "___XF_");
-
-      if (tail == NULL)
-        return NULL;
-      else
-        return tail + 5;
-    }
-  else if (code == TYPE_CODE_RANGE && TYPE_TARGET_TYPE (type) != type)
-    return gnat_encoded_fixed_type_info (TYPE_TARGET_TYPE (type));
-  else
-    return NULL;
-}
-
-/* Returns non-zero iff TYPE represents an Ada fixed-point type.  */
-
-int
-ada_is_gnat_encoded_fixed_point_type (struct type *type)
-{
-  return gnat_encoded_fixed_type_info (type) != NULL;
-}
-
 /* Return non-zero iff TYPE represents a System.Address type.  */
 
 int
@@ -11173,63 +11249,9 @@ ada_is_system_address_type (struct type *type)
   return (type->name () && strcmp (type->name (), "system__address") == 0);
 }
 
-/* Assuming that TYPE is the representation of an Ada fixed-point
-   type, return the target floating-point type to be used to represent
-   of this type during internal computation.  */
-
-static struct type *
-ada_scaling_type (struct type *type)
-{
-  return builtin_type (get_type_arch (type))->builtin_long_double;
-}
-
-/* Assuming that TYPE is the representation of an Ada fixed-point
-   type, return its delta, or NULL if the type is malformed and the
-   delta cannot be determined.  */
-
-struct value *
-gnat_encoded_fixed_point_delta (struct type *type)
-{
-  const char *encoding = gnat_encoded_fixed_type_info (type);
-  struct type *scale_type = ada_scaling_type (type);
-
-  long long num, den;
-
-  if (sscanf (encoding, "_%lld_%lld", &num, &den) < 2)
-    return nullptr;
-  else
-    return value_binop (value_from_longest (scale_type, num),
-                       value_from_longest (scale_type, den), BINOP_DIV);
-}
-
-/* Assuming that ada_is_gnat_encoded_fixed_point_type (TYPE), return
-   the scaling factor ('SMALL value) associated with the type.  */
-
-struct value *
-ada_scaling_factor (struct type *type)
-{
-  const char *encoding = gnat_encoded_fixed_type_info (type);
-  struct type *scale_type = ada_scaling_type (type);
-
-  long long num0, den0, num1, den1;
-  int n;
-
-  n = sscanf (encoding, "_%lld_%lld_%lld_%lld",
-             &num0, &den0, &num1, &den1);
-
-  if (n < 2)
-    return value_from_longest (scale_type, 1);
-  else if (n == 4)
-    return value_binop (value_from_longest (scale_type, num1),
-                       value_from_longest (scale_type, den1), BINOP_DIV);
-  else
-    return value_binop (value_from_longest (scale_type, num0),
-                       value_from_longest (scale_type, den0), BINOP_DIV);
-}
-
 \f
 
-                                /* Range types */
+                               /* 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
@@ -11239,10 +11261,9 @@ ada_scaling_factor (struct type *type)
 
 static int
 scan_discrim_bound (const char *str, int k, struct value *dval, LONGEST * px,
-                    int *pnew_k)
+                   int *pnew_k)
 {
-  static char *bound_buffer = NULL;
-  static size_t bound_buffer_len = 0;
+  static std::string storage;
   const char *pstart, *pend, *bound;
   struct value *bound_val;
 
@@ -11261,11 +11282,8 @@ scan_discrim_bound (const char *str, int k, struct value *dval, LONGEST * px,
       int len = pend - pstart;
 
       /* Strip __ and beyond.  */
-      GROW_VECT (bound_buffer, bound_buffer_len, len + 1);
-      strncpy (bound_buffer, pstart, len);
-      bound_buffer[len] = '\0';
-
-      bound = bound_buffer;
+      storage = std::string (pstart, len);
+      bound = storage.c_str ();
       k = pend - str;
     }
 
@@ -11279,26 +11297,28 @@ scan_discrim_bound (const char *str, int k, struct value *dval, LONGEST * px,
   return 1;
 }
 
-/* Value of variable named NAME in the current environment.  If
-   no such variable found, then if ERR_MSG is null, returns 0, and
+/* 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)
 {
-  lookup_name_info lookup_name (name, symbol_name_match_type::FULL);
+  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;
-  int nsyms = ada_lookup_symbol_list_worker (lookup_name,
-                                            get_selected_block (0),
-                                            VAR_DOMAIN, &syms, 1);
+  std::vector<struct block_symbol> syms
+    = ada_lookup_symbol_list_worker (lookup_name,
+                                    get_selected_block (0),
+                                    VAR_DOMAIN, 1);
 
-  if (nsyms != 1)
+  if (syms.size () != 1)
     {
       if (err_msg == NULL)
-        return 0;
+       return 0;
       else
-        error (("%s"), err_msg);
+       error (("%s"), err_msg);
     }
 
   return value_of_variable (syms[0].symbol, syms[0].block);
@@ -11360,64 +11380,58 @@ to_fixed_range_type (struct type *raw_type, struct value *dval)
     }
   else
     {
-      static char *name_buf = NULL;
-      static size_t name_len = 0;
       int prefix_len = subtype_info - name;
       LONGEST L, U;
       struct type *type;
       const char *bounds_str;
       int n;
 
-      GROW_VECT (name_buf, name_len, prefix_len + 5);
-      strncpy (name_buf, name, prefix_len);
-      name_buf[prefix_len] = '\0';
-
       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;
-        }
+       {
+         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
-        {
-          strcpy (name_buf + prefix_len, "___L");
-          if (!get_int_var_value (name_buf, L))
-            {
-              lim_warning (_("Unknown lower bound, using 1."));
-              L = 1;
-            }
-        }
+       {
+         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;
-        }
+       {
+         if (!ada_scan_number (bounds_str, n, &U, &n)
+             && !scan_discrim_bound (bounds_str, n, dval, &U, &n))
+           return raw_type;
+       }
       else
-        {
-          strcpy (name_buf + prefix_len, "___U");
-          if (!get_int_var_value (name_buf, U))
-            {
-              lim_warning (_("Unknown upper bound, using %ld."), (long) L);
-              U = L;
-            }
-        }
+       {
+         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.  */
+        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;
@@ -11433,7 +11447,7 @@ ada_is_range_type_name (const char *name)
 }
 \f
 
-                                /* Modular types */
+                               /* Modular types */
 
 /* True iff TYPE is an Ada modular type.  */
 
@@ -11443,8 +11457,8 @@ 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 ());
+         && subranged_type->code () == TYPE_CODE_INT
+         && subranged_type->is_unsigned ());
 }
 
 /* Assuming ada_is_modular_type (TYPE), the modulus of TYPE.  */
@@ -11762,10 +11776,10 @@ is_known_support_routine (struct frame_info *frame)
     {
       re_comp (known_runtime_file_name_patterns[i]);
       if (re_exec (lbasename (sal.symtab->filename)))
-        return 1;
+       return 1;
       if (SYMTAB_OBJFILE (sal.symtab) != NULL
-          && re_exec (objfile_name (SYMTAB_OBJFILE (sal.symtab))))
-        return 1;
+         && re_exec (objfile_name (SYMTAB_OBJFILE (sal.symtab))))
+       return 1;
     }
 
   /* Check whether the function is a GNAT-generated entity.  */
@@ -11794,10 +11808,10 @@ 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;
-        }
+       {
+         select_frame (fi);
+         break;
+       }
     }
 
 }
@@ -11843,7 +11857,7 @@ ada_unhandled_exception_name_addr_from_raise (void)
        = find_frame_funname (fi, &func_lang, NULL);
       if (func_name != NULL)
        {
-          if (strcmp (func_name.get (),
+         if (strcmp (func_name.get (),
                      data->exception_info->catch_exception_sym) == 0)
            break; /* We found the frame we were looking for...  */
        }
@@ -11867,32 +11881,32 @@ ada_unhandled_exception_name_addr_from_raise (void)
 
 static CORE_ADDR
 ada_exception_name_addr_1 (enum ada_exception_catchpoint_kind ex,
-                           struct breakpoint *b)
+                          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;
+       return (parse_and_eval_address ("e.full_name"));
+       break;
 
       case ada_catch_exception_unhandled:
-        return data->exception_info->unhandled_exception_name_addr ();
-        break;
+       return data->exception_info->unhandled_exception_name_addr ();
+       break;
 
       case ada_catch_handlers:
-        return 0;  /* The runtimes does not provide access to the exception
+       return 0;  /* The runtimes does not provide access to the exception
                      name.  */
-        break;
+       break;
 
       case ada_catch_assert:
-        return 0;  /* Exception name is not relevant in this case.  */
-        break;
+       return 0;  /* Exception name is not relevant in this case.  */
+       break;
 
       default:
-        internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
-        break;
+       internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
+       break;
     }
 
   return 0; /* Should never be reached.  */
@@ -11966,7 +11980,7 @@ ada_exception_message (void)
 
 static CORE_ADDR
 ada_exception_name_addr (enum ada_exception_catchpoint_kind ex,
-                         struct breakpoint *b)
+                        struct breakpoint *b)
 {
   CORE_ADDR result = 0;
 
@@ -12038,7 +12052,7 @@ struct ada_catchpoint : public breakpoint
 
 static void
 create_excep_cond_exprs (struct ada_catchpoint *c,
-                         enum ada_exception_catchpoint_kind ex)
+                        enum ada_exception_catchpoint_kind ex)
 {
   struct bp_location *bl;
 
@@ -12183,7 +12197,7 @@ should_stop_exception (const struct bp_location *bl)
 static void
 check_status_exception (bpstat bs)
 {
-  bs->stop = should_stop_exception (bs->bp_location_at);
+  bs->stop = should_stop_exception (bs->bp_location_at.get ());
 }
 
 /* Implement the PRINT_IT method in the breakpoint_ops structure
@@ -12295,40 +12309,40 @@ print_one_exception (struct breakpoint *b, struct bp_location **last_loc)
   switch (c->m_kind)
     {
       case ada_catch_exception:
-        if (!c->excep_string.empty ())
-          {
+       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;
+           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;
+       uiout->field_string ("what", "unhandled Ada exceptions");
+       break;
       
       case ada_catch_handlers:
-        if (!c->excep_string.empty ())
-          {
+       if (!c->excep_string.empty ())
+         {
            uiout->field_fmt ("what",
                              _("`%s' Ada exception handlers"),
                              c->excep_string.c_str ());
-          }
-        else
+         }
+       else
          uiout->field_string ("what", "all Ada exceptions handlers");
-        break;
+       break;
 
       case ada_catch_assert:
-        uiout->field_string ("what", "failed Ada assertions");
-        break;
+       uiout->field_string ("what", "failed Ada assertions");
+       break;
 
       default:
-        internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
-        break;
+       internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
+       break;
     }
 }
 
@@ -12342,46 +12356,46 @@ print_mention_exception (struct breakpoint *b)
   struct ui_out *uiout = current_uiout;
 
   uiout->text (b->disposition == disp_del ? _("Temporary catchpoint ")
-                                                 : _("Catchpoint "));
+                                                : _("Catchpoint "));
   uiout->field_signed ("bkptno", b->number);
   uiout->text (": ");
 
   switch (c->m_kind)
     {
       case ada_catch_exception:
-        if (!c->excep_string.empty ())
+       if (!c->excep_string.empty ())
          {
            std::string info = string_printf (_("`%s' Ada exception"),
                                              c->excep_string.c_str ());
            uiout->text (info.c_str ());
          }
-        else
-          uiout->text (_("all Ada exceptions"));
-        break;
+       else
+         uiout->text (_("all Ada exceptions"));
+       break;
 
       case ada_catch_exception_unhandled:
-        uiout->text (_("unhandled Ada exceptions"));
-        break;
+       uiout->text (_("unhandled Ada exceptions"));
+       break;
 
       case ada_catch_handlers:
-        if (!c->excep_string.empty ())
+       if (!c->excep_string.empty ())
          {
            std::string info
              = string_printf (_("`%s' Ada exception handlers"),
                               c->excep_string.c_str ());
            uiout->text (info.c_str ());
          }
-        else
-          uiout->text (_("all Ada exceptions handlers"));
-        break;
+       else
+         uiout->text (_("all Ada exceptions handlers"));
+       break;
 
       case ada_catch_assert:
-        uiout->text (_("failed Ada assertions"));
-        break;
+       uiout->text (_("failed Ada assertions"));
+       break;
 
       default:
-        internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
-        break;
+       internal_error (__FILE__, __LINE__, _("unexpected catchpoint type"));
+       break;
     }
 }
 
@@ -12449,7 +12463,7 @@ is_ada_exception_catchpoint (breakpoint *bp)
 static void
 catch_ada_exception_command_split (const char *args,
                                   bool is_catch_handlers_cmd,
-                                   enum ada_exception_catchpoint_kind *ex,
+                                  enum ada_exception_catchpoint_kind *ex,
                                   std::string *excep_string,
                                   std::string *cond_string)
 {
@@ -12475,7 +12489,7 @@ catch_ada_exception_command_split (const char *args,
       args = skip_spaces (args);
 
       if (args[0] == '\0')
-        error (_("Condition missing after `if' keyword"));
+       error (_("Condition missing after `if' keyword"));
       *cond_string = args;
 
       args += strlen (args);
@@ -12526,20 +12540,20 @@ ada_exception_sym_name (enum ada_exception_catchpoint_kind ex)
   switch (ex)
     {
       case ada_catch_exception:
-        return (data->exception_info->catch_exception_sym);
-        break;
+       return (data->exception_info->catch_exception_sym);
+       break;
       case ada_catch_exception_unhandled:
-        return (data->exception_info->catch_exception_unhandled_sym);
-        break;
+       return (data->exception_info->catch_exception_unhandled_sym);
+       break;
       case ada_catch_assert:
-        return (data->exception_info->catch_assert_sym);
-        break;
+       return (data->exception_info->catch_assert_sym);
+       break;
       case ada_catch_handlers:
-        return (data->exception_info->catch_handlers_sym);
-        break;
+       return (data->exception_info->catch_handlers_sym);
+       break;
       default:
-        internal_error (__FILE__, __LINE__,
-                        _("unexpected catchpoint kind (%d)"), ex);
+       internal_error (__FILE__, __LINE__,
+                       _("unexpected catchpoint kind (%d)"), ex);
     }
 }
 
@@ -12552,20 +12566,20 @@ ada_exception_breakpoint_ops (enum ada_exception_catchpoint_kind ex)
   switch (ex)
     {
       case ada_catch_exception:
-        return (&catch_exception_breakpoint_ops);
-        break;
+       return (&catch_exception_breakpoint_ops);
+       break;
       case ada_catch_exception_unhandled:
-        return (&catch_exception_unhandled_breakpoint_ops);
-        break;
+       return (&catch_exception_unhandled_breakpoint_ops);
+       break;
       case ada_catch_assert:
-        return (&catch_assert_breakpoint_ops);
-        break;
+       return (&catch_assert_breakpoint_ops);
+       break;
       case ada_catch_handlers:
-        return (&catch_handlers_breakpoint_ops);
-        break;
+       return (&catch_handlers_breakpoint_ops);
+       break;
       default:
-        internal_error (__FILE__, __LINE__,
-                        _("unexpected catchpoint kind (%d)"), ex);
+       internal_error (__FILE__, __LINE__,
+                       _("unexpected catchpoint kind (%d)"), ex);
     }
 }
 
@@ -12577,7 +12591,7 @@ ada_exception_breakpoint_ops (enum ada_exception_catchpoint_kind ex)
 
 static std::string
 ada_exception_catchpoint_cond_string (const char *excep_string,
-                                      enum ada_exception_catchpoint_kind ex)
+                                     enum ada_exception_catchpoint_kind ex)
 {
   int i;
   bool is_standard_exc = false;
@@ -12586,7 +12600,7 @@ ada_exception_catchpoint_cond_string (const char *excep_string,
   if (ex == ada_catch_handlers)
     {
       /* For exception handlers catchpoints, the condition string does
-         not use the same parameter as for the other exceptions.  */
+        not use the same parameter as for the other exceptions.  */
       result = ("long_integer (GNAT_GCC_exception_Access"
                "(gcc_exception).all.occurrence.id)");
     }
@@ -12702,7 +12716,7 @@ create_ada_exception_catchpoint (struct gdbarch *gdbarch,
   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);
+    set_breakpoint_condition (c.get (), cond_string.c_str (), from_tty, false);
   install_breakpoint (0, std::move (c), 1);
 }
 
@@ -12791,7 +12805,7 @@ catch_ada_assert_command_split (const char *args, std::string &cond_string)
       args += 2;
       args = skip_spaces (args);
       if (args[0] == '\0')
-        error (_("condition missing after `if' keyword"));
+       error (_("condition missing after `if' keyword"));
       cond_string.assign (args);
     }
 
@@ -12831,10 +12845,10 @@ 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);
+         && 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
@@ -13137,7 +13151,7 @@ info_exceptions_command (const char *regexp, int from_tty)
     printf_filtered ("%s: %s\n", info.name, paddress (gdbarch, info.addr));
 }
 
-                                /* Operators */
+                               /* Operators */
 /* Information about operators given special treatment in functions
    below.  */
 /* Format: OP_DEFN (<operator>, <operator length>, <# args>, <binop>).  */
@@ -13213,41 +13227,20 @@ ada_operator_check (struct expression *exp, int pos,
 
   /* Invoke callbacks for TYPE and OBJFILE if they were set as non-NULL.  */
 
-  if (type && TYPE_OBJFILE (type)
-      && (*objfile_func) (TYPE_OBJFILE (type), data))
+  if (type != nullptr && type->objfile_owner () != nullptr
+      && objfile_func (type->objfile_owner (), data))
     return 1;
 
   return 0;
 }
 
-static const char *
-ada_op_name (enum exp_opcode opcode)
-{
-  switch (opcode)
-    {
-    default:
-      return op_name_standard (opcode);
-
-#define OP_DEFN(op, len, args, binop) case op: return #op;
-      ADA_OPERATORS;
-#undef OP_DEFN
-
-    case OP_AGGREGATE:
-      return "OP_AGGREGATE";
-    case OP_CHOICES:
-      return "OP_CHOICES";
-    case OP_NAME:
-      return "OP_NAME";
-    }
-}
-
 /* As for operator_length, but assumes PC is pointing at the first
    element of the operator, and gives meaningful results only for the 
    Ada-specific operators, returning 0 for *OPLENP and *ARGSP otherwise.  */
 
 static void
 ada_forward_operator_length (struct expression *exp, int pc,
-                             int *oplenp, int *argsp)
+                            int *oplenp, int *argsp)
 {
   switch (exp->elts[pc].opcode)
     {
@@ -13356,7 +13349,7 @@ ada_dump_subexp_body (struct expression *exp, struct ui_file *stream, int elt)
 
 static void
 ada_print_subexp (struct expression *exp, int *pos,
-                  struct ui_file *stream, enum precedence prec)
+                 struct ui_file *stream, enum precedence prec)
 {
   int oplen, nargs, i;
   int pc = *pos;
@@ -13383,13 +13376,13 @@ ada_print_subexp (struct expression *exp, int *pos,
       print_subexp (exp, pos, stream, PREC_SUFFIX);
       fputs_filtered ("'range", stream);
       if (exp->elts[pc + 1].longconst > 1)
-        fprintf_filtered (stream, "(%ld)",
-                          (long) exp->elts[pc + 1].longconst);
+       fprintf_filtered (stream, "(%ld)",
+                         (long) exp->elts[pc + 1].longconst);
       return;
 
     case TERNOP_IN_RANGE:
       if (prec >= PREC_EQUAL)
-        fputs_filtered ("(", stream);
+       fputs_filtered ("(", stream);
       /* XXX: sprint_subexp */
       print_subexp (exp, pos, stream, PREC_SUFFIX);
       fputs_filtered (" in ", stream);
@@ -13397,7 +13390,7 @@ ada_print_subexp (struct expression *exp, int *pos,
       fputs_filtered (" .. ", stream);
       print_subexp (exp, pos, stream, PREC_EQUAL);
       if (prec >= PREC_EQUAL)
-        fputs_filtered (")", stream);
+       fputs_filtered (")", stream);
       return;
 
     case OP_ATR_FIRST:
@@ -13412,26 +13405,26 @@ ada_print_subexp (struct expression *exp, int *pos,
     case OP_ATR_TAG:
     case OP_ATR_VAL:
       if (exp->elts[*pos].opcode == OP_TYPE)
-        {
-          if (exp->elts[*pos + 1].type->code () != TYPE_CODE_VOID)
-            LA_PRINT_TYPE (exp->elts[*pos + 1].type, "", stream, 0, 0,
+       {
+         if (exp->elts[*pos + 1].type->code () != TYPE_CODE_VOID)
+           LA_PRINT_TYPE (exp->elts[*pos + 1].type, "", stream, 0, 0,
                           &type_print_raw_options);
-          *pos += 3;
-        }
+         *pos += 3;
+       }
       else
-        print_subexp (exp, pos, stream, PREC_SUFFIX);
+       print_subexp (exp, pos, stream, PREC_SUFFIX);
       fprintf_filtered (stream, "'%s", ada_attribute_name (op));
       if (nargs > 1)
-        {
-          int tem;
-
-          for (tem = 1; tem < nargs; tem += 1)
-            {
-              fputs_filtered ((tem == 1) ? " (" : ", ", stream);
-              print_subexp (exp, pos, stream, PREC_ABOVE_COMMA);
-            }
-          fputs_filtered (")", stream);
-        }
+       {
+         int tem;
+
+         for (tem = 1; tem < nargs; tem += 1)
+           {
+             fputs_filtered ((tem == 1) ? " (" : ", ", stream);
+             print_subexp (exp, pos, stream, PREC_ABOVE_COMMA);
+           }
+         fputs_filtered (")", stream);
+       }
       return;
 
     case UNOP_QUAL:
@@ -13525,24 +13518,6 @@ static const struct op_print ada_op_print_tab[] = {
   {"'size", OP_ATR_SIZE, PREC_SUFFIX, 1},
   {NULL, OP_NULL, PREC_SUFFIX, 0}
 };
-\f
-enum ada_primitive_types {
-  ada_primitive_type_int,
-  ada_primitive_type_long,
-  ada_primitive_type_short,
-  ada_primitive_type_char,
-  ada_primitive_type_float,
-  ada_primitive_type_double,
-  ada_primitive_type_void,
-  ada_primitive_type_long_long,
-  ada_primitive_type_long_double,
-  ada_primitive_type_natural,
-  ada_primitive_type_positive,
-  ada_primitive_type_system_address,
-  ada_primitive_type_storage_offset,
-  nr_ada_primitive_types
-};
-
 \f
                                /* Language vector */
 
@@ -13550,7 +13525,6 @@ static const struct exp_descriptor ada_exp_descriptor = {
   ada_print_subexp,
   ada_operator_length,
   ada_operator_check,
-  ada_op_name,
   ada_dump_subexp_body,
   ada_evaluate_subexp
 };
@@ -13572,7 +13546,47 @@ do_full_match (const char *symbol_search_name,
               const lookup_name_info &lookup_name,
               completion_match_result *comp_match_res)
 {
-  return full_match (symbol_search_name, ada_lookup_name (lookup_name));
+  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.  */
@@ -13591,7 +13605,7 @@ 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[0] == '<')
+  if (!user_name.empty () && user_name[0] == '<')
     {
       if (user_name.back () == '>')
        m_encoded_name
@@ -13613,10 +13627,8 @@ ada_lookup_name_info::ada_lookup_name_info (const lookup_name_info &lookup_name)
       if (!m_encoded_p)
        {
          const char *folded = ada_fold_name (user_name);
-         const char *encoded = ada_encode_1 (folded, false);
-         if (encoded != NULL)
-           m_encoded_name = encoded;
-         else
+         m_encoded_name = ada_encode_1 (folded, false);
+         if (m_encoded_name.empty ())
            m_encoded_name = gdb::to_string (user_name);
        }
       else
@@ -13704,28 +13716,13 @@ ada_get_symbol_name_matcher (const lookup_name_info &lookup_name)
     }
 }
 
-/* Constant data that describes the Ada language.  */
-
-extern const struct language_data ada_language_data =
-{
-  range_check_off,
-  case_sensitive_on,            /* Yes, Ada is case-insensitive, but
-                                   that's not quite what this means.  */
-  array_row_major,
-  macro_expansion_no,
-  &ada_exp_descriptor,
-  true,                         /* la_store_sym_names_in_linkage_form_p */
-  ada_op_print_tab,             /* expression operators for printing */
-  &ada_varobj_ops,
-};
-
 /* Class representing the Ada language.  */
 
 class ada_language : public language_defn
 {
 public:
   ada_language ()
-    : language_defn (language_ada, ada_language_data)
+    : language_defn (language_ada)
   { /* Nothing.  */ }
 
   /* See language.h.  */
@@ -13756,7 +13753,7 @@ public:
   {
     struct value *index_value = val_atr (index_type, index);
 
-    LA_VALUE_PRINT (index_value, stream, options);
+    value_print (index_value, stream, options);
     fprintf_filtered (stream, " => ");
   }
 
@@ -13786,63 +13783,51 @@ public:
   {
     const struct builtin_type *builtin = builtin_type (gdbarch);
 
-    lai->primitive_type_vector
-      = GDBARCH_OBSTACK_CALLOC (gdbarch, nr_ada_primitive_types + 1,
-                               struct type *);
-
-    lai->primitive_type_vector [ada_primitive_type_int]
-      = arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
-                          0, "integer");
-    lai->primitive_type_vector [ada_primitive_type_long]
-      = arch_integer_type (gdbarch, gdbarch_long_bit (gdbarch),
-                          0, "long_integer");
-    lai->primitive_type_vector [ada_primitive_type_short]
-      = arch_integer_type (gdbarch, gdbarch_short_bit (gdbarch),
-                          0, "short_integer");
-    lai->string_char_type
-      = lai->primitive_type_vector [ada_primitive_type_char]
-      = arch_character_type (gdbarch, TARGET_CHAR_BIT, 0, "character");
-    lai->primitive_type_vector [ada_primitive_type_float]
-      = arch_float_type (gdbarch, gdbarch_float_bit (gdbarch),
-                        "float", gdbarch_float_format (gdbarch));
-    lai->primitive_type_vector [ada_primitive_type_double]
-      = arch_float_type (gdbarch, gdbarch_double_bit (gdbarch),
-                        "long_float", gdbarch_double_format (gdbarch));
-    lai->primitive_type_vector [ada_primitive_type_long_long]
-      = arch_integer_type (gdbarch, gdbarch_long_long_bit (gdbarch),
-                          0, "long_long_integer");
-    lai->primitive_type_vector [ada_primitive_type_long_double]
-      = arch_float_type (gdbarch, gdbarch_long_double_bit (gdbarch),
-                        "long_long_float", gdbarch_long_double_format (gdbarch));
-    lai->primitive_type_vector [ada_primitive_type_natural]
-      = arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
-                          0, "natural");
-    lai->primitive_type_vector [ada_primitive_type_positive]
-      = arch_integer_type (gdbarch, gdbarch_int_bit (gdbarch),
-                          0, "positive");
-    lai->primitive_type_vector [ada_primitive_type_void]
-      = builtin->builtin_void;
-
-    lai->primitive_type_vector [ada_primitive_type_system_address]
+    /* 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"));
-    lai->primitive_type_vector [ada_primitive_type_system_address]
-      ->set_name ("system__address");
+    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
-       (lai->primitive_type_vector [ada_primitive_type_system_address]);
-
-      lai->primitive_type_vector [ada_primitive_type_storage_offset]
-       = arch_integer_type (gdbarch, addr_length * HOST_CHAR_BIT, 0,
-                            "storage_offset");
-    }
+    unsigned int addr_length = TYPE_LENGTH (system_addr_ptr);
+    add (arch_integer_type (gdbarch, addr_length * HOST_CHAR_BIT, 0,
+                           "storage_offset"));
 
-    lai->bool_type_symbol = NULL;
-    lai->bool_type_default = builtin->builtin_bool;
+    lai->set_bool_type (builtin->builtin_bool);
   }
 
   /* See language.h.  */
@@ -13852,9 +13837,8 @@ public:
         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, &results, 0);
+    std::vector<struct block_symbol> results
+      = ada_lookup_symbol_list_worker (name, block, domain, 0);
     for (block_symbol &sym : results)
       {
        if (!callback (&sym))
@@ -13904,7 +13888,7 @@ public:
 
   /* See language.h.  */
 
-  char *demangle (const char *mangled, int options) const override
+  char *demangle_symbol (const char *mangled, int options) const override
   {
     return ada_la_decode (mangled, options);
   }
@@ -14139,16 +14123,17 @@ public:
      A null CONTEXT_TYPE indicates that a non-void return type is
      preferred.  May change (expand) *EXP.  */
 
-  void post_parser (expression_up *expp, int void_context_p, int completing,
-                   innermost_block_tracker *tracker) const override
+  void post_parser (expression_up *expp, struct parser_state *ps)
+    const override
   {
     struct type *context_type = NULL;
     int pc = 0;
 
-    if (void_context_p)
+    if (ps->void_context_p)
       context_type = builtin_type ((*expp)->gdbarch)->builtin_void;
 
-    resolve_subexp (expp, &pc, 1, context_type, completing, tracker);
+    resolve_subexp (expp, &pc, 1, context_type, ps->parse_completion,
+                   ps->block_tracker);
   }
 
   /* See language.h.  */
@@ -14203,6 +14188,26 @@ public:
   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; }
+
+  /* See language.h.  */
+
+  const struct exp_descriptor *expression_ops () const override
+  { return &ada_exp_descriptor; }
+
+  /* See language.h.  */
+
+  const struct op_print *opcode_print_table () const override
+  { return ada_op_print_tab; }
+
 protected:
   /* See language.h.  */
 
@@ -14300,10 +14305,10 @@ _initialize_ada_language ()
                       &show_ada_list, "show ada ", 0, &showlist);
 
   add_setshow_boolean_cmd ("trust-PAD-over-XVS", class_obscure,
-                           &trust_pad_over_xvs, _("\
+                          &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\
@@ -14311,7 +14316,7 @@ 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);
+                           NULL, NULL, &set_ada_list, &show_ada_list);
 
   add_setshow_boolean_cmd ("print-signatures", class_vars,
                           &print_signatures, _("\
@@ -14345,7 +14350,7 @@ 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_ada_completer,
                     CATCH_PERMANENT,
                     CATCH_TEMPORARY);
   add_catch_command ("assert", _("\
@@ -14354,7 +14359,7 @@ 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,
+                    NULL,
                     CATCH_PERMANENT,
                     CATCH_TEMPORARY);
 
This page took 0.166681 seconds and 4 git commands to generate.