MIPS: Support `-gnuabi64' target triplet suffix for 64-bit Linux targets
[binutils-gdb.git] / binutils / stabs.c
index 4f1730896ac91a0a89be8c6fd8aac4e67ab4c85f..311b73b841859fabe33334a6f8d65431a9a4d079 100644 (file)
@@ -1,5 +1,5 @@
 /* stabs.c -- Parse stabs debugging information
-   Copyright (C) 1995-2015 Free Software Foundation, Inc.
+   Copyright (C) 1995-2023 Free Software Foundation, Inc.
    Written by Ian Lance Taylor <ian@cygnus.com>.
 
    This file is part of GNU Binutils.
@@ -47,7 +47,7 @@ struct stab_handle
   /* The BFD.  */
   bfd *abfd;
   /* TRUE if this is stabs in sections.  */
-  bfd_boolean sections;
+  bool sections;
   /* The symbol table.  */
   asymbol **syms;
   /* The number of symbols.  */
@@ -67,7 +67,7 @@ struct stab_handle
   int gcc_compiled;
   /* Whether an N_OPT symbol was seen that was not generated by gcc,
      so that we can detect the SunPRO compiler.  */
-  bfd_boolean n_opt_found;
+  bool n_opt_found;
   /* The main file name.  */
   char *main_filename;
   /* A stack of unfinished N_BINCL files.  */
@@ -75,7 +75,7 @@ struct stab_handle
   /* A list of finished N_BINCL files.  */
   struct bincl_file *bincl_list;
   /* Whether we are inside a function or not.  */
-  bfd_boolean within_function;
+  bool within_function;
   /* The address of the end of the function, used if we have seen an
      N_FUN symbol while in a function.  This is -1 if we have not seen
      an N_FUN (the normal case).  */
@@ -94,7 +94,7 @@ struct stab_handle
   struct stab_tag *tags;
   /* Set by parse_stab_type if it sees a structure defined as a cross
      reference to itself.  Reset by parse_stab_type otherwise.  */
-  bfd_boolean self_crossref;
+  bool self_crossref;
 };
 
 /* A list of these structures is used to hold pending variable
@@ -121,6 +121,8 @@ struct stab_types
 {
   /* Next set of slots for this file.  */
   struct stab_types *next;
+  /* Where the TYPES array starts.  */
+  unsigned int base_index;
   /* Types indexed by type number.  */
 #define STAB_TYPES_SLOTS (16)
   debug_type types[STAB_TYPES_SLOTS];
@@ -144,76 +146,85 @@ struct stab_tag
   debug_type type;
 };
 
-static char *savestring (const char *, int);
-static bfd_vma parse_number (const char **, bfd_boolean *);
 static void bad_stab (const char *);
 static void warn_stab (const char *, const char *);
-static bfd_boolean parse_stab_string
-  (void *, struct stab_handle *, int, int, bfd_vma, const char *);
+static bool parse_stab_string
+  (void *, struct stab_handle *, int, int, bfd_vma,
+   const char *, const char *);
 static debug_type parse_stab_type
-  (void *, struct stab_handle *, const char *, const char **, debug_type **);
-static bfd_boolean parse_stab_type_number (const char **, int *);
+  (void *, struct stab_handle *, const char *, const char **,
+   debug_type **, const char *);
+static bool parse_stab_type_number
+  (const char **, int *, const char *);
 static debug_type parse_stab_range_type
-  (void *, struct stab_handle *, const char *, const char **, const int *);
-static debug_type parse_stab_sun_builtin_type (void *, const char **);
-static debug_type parse_stab_sun_floating_type (void *, const char **);
-static debug_type parse_stab_enum_type (void *, const char **);
+  (void *, struct stab_handle *, const char *, const char **,
+   const int *, const char *);
+static debug_type parse_stab_sun_builtin_type
+  (void *, const char **, const char *);
+static debug_type parse_stab_sun_floating_type
+  (void *, const char **, const char *);
+static debug_type parse_stab_enum_type
+  (void *, const char **, const char *);
 static debug_type parse_stab_struct_type
   (void *, struct stab_handle *, const char *, const char **,
-   bfd_boolean, const int *);
-static bfd_boolean parse_stab_baseclasses
-  (void *, struct stab_handle *, const char **, debug_baseclass **);
-static bfd_boolean parse_stab_struct_fields
-  (void *, struct stab_handle *, const char **, debug_field **, bfd_boolean *);
-static bfd_boolean parse_stab_cpp_abbrev
-  (void *, struct stab_handle *, const char **, debug_field *);
-static bfd_boolean parse_stab_one_struct_field
+   bool, const int *, const char *);
+static bool parse_stab_baseclasses
+  (void *, struct stab_handle *, const char **, debug_baseclass **,
+   const char *);
+static bool parse_stab_struct_fields
+  (void *, struct stab_handle *, const char **, debug_field **,
+   bool *, const char *);
+static bool parse_stab_cpp_abbrev
+  (void *, struct stab_handle *, const char **, debug_field *, const char *);
+static bool parse_stab_one_struct_field
   (void *, struct stab_handle *, const char **, const char *,
-   debug_field *, bfd_boolean *);
-static bfd_boolean parse_stab_members
+   debug_field *, bool *, const char *);
+static bool parse_stab_members
   (void *, struct stab_handle *, const char *, const char **, const int *,
-   debug_method **);
+   debug_method **, const char *);
 static debug_type parse_stab_argtypes
   (void *, struct stab_handle *, debug_type, const char *, const char *,
-   debug_type, const char *, bfd_boolean, bfd_boolean, const char **);
-static bfd_boolean parse_stab_tilde_field
+   debug_type, const char *, bool, bool, const char **);
+static bool parse_stab_tilde_field
   (void *, struct stab_handle *, const char **, const int *, debug_type *,
-   bfd_boolean *);
+   bool *, const char *);
 static debug_type parse_stab_array_type
-  (void *, struct stab_handle *, const char **, bfd_boolean);
-static void push_bincl (struct stab_handle *, const char *, bfd_vma);
+  (void *, struct stab_handle *, const char **, bool, const char *);
+static void push_bincl (void *, struct stab_handle *, const char *, bfd_vma);
 static const char *pop_bincl (struct stab_handle *);
-static bfd_boolean find_excl (struct stab_handle *, const char *, bfd_vma);
-static bfd_boolean stab_record_variable
+static bool find_excl (struct stab_handle *, const char *, bfd_vma);
+static bool stab_record_variable
   (void *, struct stab_handle *, const char *, debug_type,
    enum debug_var_kind, bfd_vma);
-static bfd_boolean stab_emit_pending_vars (void *, struct stab_handle *);
-static debug_type *stab_find_slot (struct stab_handle *, const int *);
+static bool stab_emit_pending_vars (void *, struct stab_handle *);
+static debug_type *stab_find_slot (void *, struct stab_handle *, const int *);
 static debug_type stab_find_type (void *, struct stab_handle *, const int *);
-static bfd_boolean stab_record_type
+static bool stab_record_type
   (void *, struct stab_handle *, const int *, debug_type);
 static debug_type stab_xcoff_builtin_type
-  (void *, struct stab_handle *, int);
+  (void *, struct stab_handle *, unsigned int);
 static debug_type stab_find_tagged_type
   (void *, struct stab_handle *, const char *, int, enum debug_type_kind);
 static debug_type *stab_demangle_argtypes
-  (void *, struct stab_handle *, const char *, bfd_boolean *, unsigned int);
+  (void *, struct stab_handle *, const char *, bool *, unsigned int);
 static debug_type *stab_demangle_v3_argtypes
-  (void *, struct stab_handle *, const char *, bfd_boolean *);
+  (void *, struct stab_handle *, const char *, bool *);
 static debug_type *stab_demangle_v3_arglist
-  (void *, struct stab_handle *, struct demangle_component *, bfd_boolean *);
+  (void *, struct stab_handle *, struct demangle_component *, bool *);
 static debug_type stab_demangle_v3_arg
   (void *, struct stab_handle *, struct demangle_component *, debug_type,
-   bfd_boolean *);
+   bool *);
+
+static int demangle_flags = DMGL_ANSI;
 
 /* Save a string in memory.  */
 
 static char *
-savestring (const char *start, int len)
+savestring (void *dhandle, const char *start, size_t len)
 {
   char *ret;
 
-  ret = (char *) xmalloc (len + 1);
+  ret = debug_xalloc (dhandle, len + 1);
   memcpy (ret, start, len);
   ret[len] = '\0';
   return ret;
@@ -222,15 +233,21 @@ savestring (const char *start, int len)
 /* Read a number from a string.  */
 
 static bfd_vma
-parse_number (const char **pp, bfd_boolean *poverflow)
+parse_number (const char **pp, bool *poverflow, const char *p_end)
 {
   unsigned long ul;
   const char *orig;
 
   if (poverflow != NULL)
-    *poverflow = FALSE;
+    *poverflow = false;
 
   orig = *pp;
+  if (orig >= p_end)
+    return (bfd_vma) 0;
+
+  /* Stop early if we are passed an empty string.  */
+  if (*orig == 0)
+    return (bfd_vma) 0;
 
   errno = 0;
   ul = strtoul (*pp, (char **) pp, 0);
@@ -249,21 +266,21 @@ parse_number (const char **pp, bfd_boolean *poverflow)
   if (sizeof (bfd_vma) > sizeof (unsigned long))
     {
       const char *p;
-      bfd_boolean neg;
+      bool neg;
       int base;
       bfd_vma over, lastdig;
-      bfd_boolean overflow;
+      bool overflow;
       bfd_vma v;
 
       /* Our own version of strtoul, for a bfd_vma.  */
       p = orig;
 
-      neg = FALSE;
+      neg = false;
       if (*p == '+')
        ++p;
       else if (*p == '-')
        {
-         neg = TRUE;
+         neg = true;
          ++p;
        }
 
@@ -285,7 +302,7 @@ parse_number (const char **pp, bfd_boolean *poverflow)
       over = ((bfd_vma) (bfd_signed_vma) -1) / (bfd_vma) base;
       lastdig = ((bfd_vma) (bfd_signed_vma) -1) % (bfd_vma) base;
 
-      overflow = FALSE;
+      overflow = false;
       v = 0;
       while (1)
        {
@@ -306,7 +323,7 @@ parse_number (const char **pp, bfd_boolean *poverflow)
 
          if (v > over || (v == over && (bfd_vma) d > lastdig))
            {
-             overflow = TRUE;
+             overflow = true;
              break;
            }
        }
@@ -322,7 +339,7 @@ parse_number (const char **pp, bfd_boolean *poverflow)
   /* If we get here, the number is too large to represent in a
      bfd_vma.  */
   if (poverflow != NULL)
-    *poverflow = TRUE;
+    *poverflow = true;
   else
     warn_stab (orig, _("numeric overflow"));
 
@@ -348,64 +365,73 @@ warn_stab (const char *p, const char *err)
 /* Create a handle to parse stabs symbols with.  */
 
 void *
-start_stab (void *dhandle ATTRIBUTE_UNUSED, bfd *abfd, bfd_boolean sections,
+start_stab (void *dhandle ATTRIBUTE_UNUSED, bfd *abfd, bool sections,
            asymbol **syms, long symcount)
 {
   struct stab_handle *ret;
 
-  ret = (struct stab_handle *) xmalloc (sizeof *ret);
-  memset (ret, 0, sizeof *ret);
+  ret = xmalloc (sizeof (*ret));
+  memset (ret, 0, sizeof (*ret));
   ret->abfd = abfd;
   ret->sections = sections;
   ret->syms = syms;
   ret->symcount = symcount;
   ret->files = 1;
-  ret->file_types = (struct stab_types **) xmalloc (sizeof *ret->file_types);
+  ret->file_types = xmalloc (sizeof (*ret->file_types));
   ret->file_types[0] = NULL;
-  ret->function_end = (bfd_vma) -1;
-  return (void *) ret;
+  ret->function_end = -1;
+  return ret;
 }
 
 /* When we have processed all the stabs information, we need to go
    through and fill in all the undefined tags.  */
 
-bfd_boolean
-finish_stab (void *dhandle, void *handle)
+bool
+finish_stab (void *dhandle, void *handle, bool emit)
 {
   struct stab_handle *info = (struct stab_handle *) handle;
   struct stab_tag *st;
+  bool ret = true;
 
-  if (info->within_function)
+  if (emit && info->within_function)
     {
       if (! stab_emit_pending_vars (dhandle, info)
          || ! debug_end_function (dhandle, info->function_end))
-       return FALSE;
-      info->within_function = FALSE;
-      info->function_end = (bfd_vma) -1;
+       ret = false;
     }
 
-  for (st = info->tags; st != NULL; st = st->next)
-    {
-      enum debug_type_kind kind;
-
-      kind = st->kind;
-      if (kind == DEBUG_KIND_ILLEGAL)
-       kind = DEBUG_KIND_STRUCT;
-      st->slot = debug_make_undefined_tagged_type (dhandle, st->name, kind);
-      if (st->slot == DEBUG_TYPE_NULL)
-       return FALSE;
-    }
+  if (emit && ret)
+    for (st = info->tags; st != NULL; st = st->next)
+      {
+       enum debug_type_kind kind;
+
+       kind = st->kind;
+       if (kind == DEBUG_KIND_ILLEGAL)
+         kind = DEBUG_KIND_STRUCT;
+       st->slot = debug_make_undefined_tagged_type (dhandle, st->name, kind);
+       if (st->slot == DEBUG_TYPE_NULL)
+         {
+           ret = false;
+           break;
+         }
+      }
 
-  return TRUE;
+  free (info->file_types);
+  free (info->so_string);
+  free (info);
+  return ret;
 }
 
 /* Handle a single stabs symbol.  */
 
-bfd_boolean
+bool
 parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
            const char *string)
 {
+  const char * string_end;
   struct stab_handle *info = (struct stab_handle *) handle;
+  char *copy;
+  size_t len;
 
   /* gcc will emit two N_SO strings per compilation unit, one for the
      directory name and one for the file name.  We just collect N_SO
@@ -414,12 +440,18 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
   if (info->so_string != NULL
       && (type != N_SO || *string == '\0' || value != info->so_value))
     {
-      if (! debug_set_filename (dhandle, info->so_string))
-       return FALSE;
-      info->main_filename = info->so_string;
+      len = strlen (info->so_string) + 1;
+      copy = debug_xalloc (dhandle, len);
+      memcpy (copy, info->so_string, len);
+      if (! debug_set_filename (dhandle, copy))
+       return false;
+      info->main_filename = copy;
+
+      free (info->so_string);
+      info->so_string = NULL;
 
       info->gcc_compiled = 0;
-      info->n_opt_found = FALSE;
+      info->n_opt_found = false;
 
       /* Generally, for stabs in the symbol table, the N_LBRAC and
         N_RBRAC symbols are relative to the N_SO symbol value.  */
@@ -427,18 +459,17 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
        info->file_start_offset = info->so_value;
 
       /* We need to reset the mapping from type numbers to types.  We
-        can't free the old mapping, because of the use of
-        debug_make_indirect_type.  */
+        can only free the file_types array, not the stab_types
+        list entries due to the use of debug_make_indirect_type.  */
       info->files = 1;
-      info->file_types = ((struct stab_types **)
-                         xmalloc (sizeof *info->file_types));
+      info->file_types = xrealloc (info->file_types, sizeof (*info->file_types));
       info->file_types[0] = NULL;
 
-      info->so_string = NULL;
-
       /* Now process whatever type we just got.  */
     }
 
+  string_end = string + strlen (string);
+
   switch (type)
     {
     case N_FN:
@@ -453,7 +484,7 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
       if (! info->within_function)
        {
          fprintf (stderr, _("N_LBRAC not within function\n"));
-         return FALSE;
+         return false;
        }
 
       /* Start an inner lexical block.  */
@@ -461,11 +492,11 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
                               (value
                                + info->file_start_offset
                                + info->function_start_offset)))
-       return FALSE;
+       return false;
 
       /* Emit any pending variable definitions.  */
       if (! stab_emit_pending_vars (dhandle, info))
-       return FALSE;
+       return false;
 
       ++info->block_depth;
       break;
@@ -479,20 +510,20 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
          if we do, we probably need to emit them before closing the
          block.  */
       if (! stab_emit_pending_vars (dhandle, info))
-       return FALSE;
+       return false;
 
       /* End an inner lexical block.  */
       if (! debug_end_block (dhandle,
                             (value
                              + info->file_start_offset
                              + info->function_start_offset)))
-       return FALSE;
+       return false;
 
       --info->block_depth;
       if (info->block_depth < 0)
        {
          fprintf (stderr, _("Too many N_RBRACs\n"));
-         return FALSE;
+         return false;
        }
       break;
 
@@ -509,15 +540,15 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
            endval = info->function_end;
          if (! stab_emit_pending_vars (dhandle, info)
              || ! debug_end_function (dhandle, endval))
-           return FALSE;
-         info->within_function = FALSE;
+           return false;
+         info->within_function = false;
          info->function_end = (bfd_vma) -1;
        }
 
       /* An empty string is emitted by gcc at the end of a compilation
          unit.  */
       if (*string == '\0')
-       return TRUE;
+       return true;
 
       /* Just accumulate strings until we see a non N_SO symbol.  If
          the string starts with a directory separator or some other
@@ -545,45 +576,51 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
 
     case N_SOL:
       /* Start an include file.  */
-      if (! debug_start_source (dhandle, string))
-       return FALSE;
+      len = strlen (string) + 1;
+      copy = debug_xalloc (dhandle, len);
+      memcpy (copy, string, len);
+      if (! debug_start_source (dhandle, copy))
+       return false;
       break;
 
     case N_BINCL:
       /* Start an include file which may be replaced.  */
-      push_bincl (info, string, value);
-      if (! debug_start_source (dhandle, string))
-       return FALSE;
+      len = strlen (string) + 1;
+      copy = debug_xalloc (dhandle, len);
+      memcpy (copy, string, len);
+      push_bincl (dhandle, info, copy, value);
+      if (! debug_start_source (dhandle, copy))
+       return false;
       break;
 
     case N_EINCL:
       /* End an N_BINCL include.  */
       if (! debug_start_source (dhandle, pop_bincl (info)))
-       return FALSE;
+       return false;
       break;
 
     case N_EXCL:
       /* This is a duplicate of a header file named by N_BINCL which
          was eliminated by the linker.  */
       if (! find_excl (info, string, value))
-       return FALSE;
+       return false;
       break;
 
     case N_SLINE:
       if (! debug_record_line (dhandle, desc,
                               value + (info->within_function
                                        ? info->function_start_offset : 0)))
-       return FALSE;
+       return false;
       break;
 
     case N_BCOMM:
       if (! debug_start_common_block (dhandle, string))
-       return FALSE;
+       return false;
       break;
 
     case N_ECOMM:
       if (! debug_end_common_block (dhandle, string))
-       return FALSE;
+       return false;
       break;
 
     case N_FUN:
@@ -597,8 +634,8 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
                value += info->function_start_offset;
              if (! stab_emit_pending_vars (dhandle, info)
                  || ! debug_end_function (dhandle, value))
-               return FALSE;
-             info->within_function = FALSE;
+               return false;
+             info->within_function = false;
              info->function_end = (bfd_vma) -1;
            }
          break;
@@ -638,18 +675,18 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
                  endval = info->function_end;
                if (! stab_emit_pending_vars (dhandle, info)
                    || ! debug_end_function (dhandle, endval))
-                 return FALSE;
+                 return false;
                info->function_end = (bfd_vma) -1;
              }
            /* For stabs in sections, line numbers and block addresses
                are offsets from the start of the function.  */
            if (info->sections)
              info->function_start_offset = value;
-           info->within_function = TRUE;
+           info->within_function = true;
          }
 
-       if (! parse_stab_string (dhandle, info, type, desc, value, string))
-         return FALSE;
+       if (! parse_stab_string (dhandle, info, type, desc, value, string, string_end))
+         return false;
       }
       break;
 
@@ -659,7 +696,7 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
       else if (string != NULL && strcmp (string, "gcc_compiled.") == 0)
        info->gcc_compiled = 1;
       else
-       info->n_opt_found = TRUE;
+       info->n_opt_found = true;
       break;
 
     case N_OBJ:
@@ -669,26 +706,27 @@ parse_stab (void *dhandle, void *handle, int type, int desc, bfd_vma value,
       break;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Parse the stabs string.  */
 
-static bfd_boolean
+static bool
 parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
-                  int desc ATTRIBUTE_UNUSED, bfd_vma value, const char *string)
+                  int desc ATTRIBUTE_UNUSED, bfd_vma value,
+                  const char *string, const char * string_end)
 {
   const char *p;
   char *name;
   int type;
   debug_type dtype;
-  bfd_boolean synonym;
-  bfd_boolean self_crossref;
+  bool synonym;
+  bool self_crossref;
   debug_type *slot;
 
   p = strchr (string, ':');
   if (p == NULL)
-    return TRUE;
+    return true;
 
   while (p[1] == ':')
     {
@@ -697,7 +735,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
       if (p == NULL)
        {
          bad_stab (string);
-         return FALSE;
+         return false;
        }
     }
 
@@ -733,12 +771,17 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
       if (p == string || (string[0] == ' ' && p == string + 1))
        name = NULL;
       else
-       name = savestring (string, p - string);
+       name = savestring (dhandle, string, p - string);
     }
 
   ++p;
   if (ISDIGIT (*p) || *p == '(' || *p == '-')
     type = 'l';
+  else if (*p == 0)
+    {
+      bad_stab (string);
+      return false;
+    }
   else
     type = *p++;
 
@@ -754,7 +797,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
       if (*p != '=')
        {
          bad_stab (string);
-         return FALSE;
+         return false;
        }
       ++p;
       switch (*p++)
@@ -762,7 +805,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
        case 'r':
          /* Floating point constant.  */
          if (! debug_record_float_const (dhandle, name, atof (p)))
-           return FALSE;
+           return false;
          break;
        case 'i':
          /* Integer constant.  */
@@ -773,7 +816,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
             other languages probably should have at least unsigned as
             well as signed constants.  */
          if (! debug_record_int_const (dhandle, name, atoi (p)))
-           return FALSE;
+           return false;
          break;
        case 'e':
          /* SYMBOL:c=eTYPE,INTVALUE for a constant symbol whose value
@@ -781,20 +824,20 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
             e.g. "b:c=e6,0" for "const b = blob1"
             (where type 6 is defined by "blobs:t6=eblob1:0,blob2:1,;").  */
          dtype = parse_stab_type (dhandle, info, (const char *) NULL,
-                                  &p, (debug_type **) NULL);
+                                  &p, (debug_type **) NULL, string_end);
          if (dtype == DEBUG_TYPE_NULL)
-           return FALSE;
+           return false;
          if (*p != ',')
            {
              bad_stab (string);
-             return FALSE;
+             return false;
            }
          if (! debug_record_typed_const (dhandle, name, dtype, atoi (p)))
-           return FALSE;
+           return false;
          break;
        default:
          bad_stab (string);
-         return FALSE;
+         return false;
        }
 
       break;
@@ -802,22 +845,22 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
     case 'C':
       /* The name of a caught exception.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL,
-                              &p, (debug_type **) NULL);
+                              &p, (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_label (dhandle, name, dtype, value))
-       return FALSE;
+       return false;
       break;
 
     case 'f':
     case 'F':
       /* A function definition.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_function (dhandle, name, dtype, type == 'F', value))
-       return FALSE;
+       return false;
 
       /* Sun acc puts declared types of arguments here.  We don't care
         about their actual types (FIXME -- we should remember the whole
@@ -827,9 +870,9 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
        {
          ++p;
          if (parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL)
+                              (debug_type **) NULL, string_end)
              == DEBUG_TYPE_NULL)
-           return FALSE;
+           return false;
        }
 
       break;
@@ -841,9 +884,9 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
        /* A global symbol.  The value must be extracted from the
           symbol table.  */
        dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                                (debug_type **) NULL);
+                                (debug_type **) NULL, string_end);
        if (dtype == DEBUG_TYPE_NULL)
-         return FALSE;
+         return false;
        if (name != NULL)
          {
            char leading;
@@ -867,7 +910,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
 
        if (! stab_record_variable (dhandle, info, name, dtype, DEBUG_GLOBAL,
                                    value))
-         return FALSE;
+         return false;
       }
       break;
 
@@ -877,19 +920,19 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
     case 'l':
     case 's':
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! stab_record_variable (dhandle, info, name, dtype, DEBUG_LOCAL,
                                  value))
-       return FALSE;
+       return false;
       break;
 
     case 'p':
       /* A function parameter.  */
       if (*p != 'F')
        dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                                (debug_type **) NULL);
+                                (debug_type **) NULL, string_end);
       else
        {
        /* pF is a two-letter code that means a function parameter in
@@ -897,21 +940,21 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
           value.  Translate it into a pointer-to-function type.  */
          ++p;
          dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                                  (debug_type **) NULL);
+                                  (debug_type **) NULL, string_end);
          if (dtype != DEBUG_TYPE_NULL)
            {
              debug_type ftype;
 
              ftype = debug_make_function_type (dhandle, dtype,
-                                               (debug_type *) NULL, FALSE);
+                                               (debug_type *) NULL, false);
              dtype = debug_make_pointer_type (dhandle, ftype);
            }
        }
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_parameter (dhandle, name, dtype, DEBUG_PARM_STACK,
                                    value))
-       return FALSE;
+       return false;
 
       /* FIXME: At this point gdb considers rearranging the parameter
         address on a big endian machine if it is smaller than an int.
@@ -927,9 +970,9 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
            {
              ++p;
              if (parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                                  (debug_type **) NULL)
+                                  (debug_type **) NULL, string_end)
                  == DEBUG_TYPE_NULL)
-               return FALSE;
+               return false;
            }
          break;
        }
@@ -937,23 +980,23 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
     case 'R':
       /* Parameter which is in a register.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_parameter (dhandle, name, dtype, DEBUG_PARM_REG,
                                    value))
-       return FALSE;
+       return false;
       break;
 
     case 'r':
       /* Register variable (either global or local).  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! stab_record_variable (dhandle, info, name, dtype, DEBUG_REGISTER,
                                  value))
-       return FALSE;
+       return false;
 
       /* FIXME: At this point gdb checks to combine pairs of 'p' and
         'r' stabs into a single 'P' stab.  */
@@ -962,28 +1005,28 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
     case 'S':
       /* Static symbol at top level of file.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! stab_record_variable (dhandle, info, name, dtype, DEBUG_STATIC,
                                  value))
-       return FALSE;
+       return false;
       break;
 
     case 't':
       /* A typedef.  */
-      dtype = parse_stab_type (dhandle, info, name, &p, &slot);
+      dtype = parse_stab_type (dhandle, info, name, &p, &slot, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (name == NULL)
        {
          /* A nameless type.  Nothing to do.  */
-         return TRUE;
+         return true;
        }
 
       dtype = debug_name_type (dhandle, name, dtype);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
 
       if (slot != NULL)
        *slot = dtype;
@@ -991,25 +1034,25 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
       break;
 
     case 'T':
-      /* Struct, union, or enum tag.  For GNU C++, this can be be followed
+      /* Struct, union, or enum tag.  For GNU C++, this can be followed
         by 't' which means we are typedef'ing it as well.  */
       if (*p != 't')
        {
-         synonym = FALSE;
+         synonym = false;
          /* FIXME: gdb sets synonym to TRUE if the current language
              is C++.  */
        }
       else
        {
-         synonym = TRUE;
+         synonym = true;
          ++p;
        }
 
-      dtype = parse_stab_type (dhandle, info, name, &p, &slot);
+      dtype = parse_stab_type (dhandle, info, name, &p, &slot, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (name == NULL)
-       return TRUE;
+       return true;
 
       /* INFO->SELF_CROSSREF is set by parse_stab_type if this type is
          a cross reference to itself.  These are generated by some
@@ -1018,7 +1061,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
 
       dtype = debug_tag_type (dhandle, name, dtype);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (slot != NULL)
        *slot = dtype;
 
@@ -1045,7 +1088,7 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
        {
          dtype = debug_name_type (dhandle, name, dtype);
          if (dtype == DEBUG_TYPE_NULL)
-           return FALSE;
+           return false;
 
          if (slot != NULL)
            *slot = dtype;
@@ -1056,35 +1099,35 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
     case 'V':
       /* Static symbol of local scope */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       /* FIXME: gdb checks os9k_stabs here.  */
       if (! stab_record_variable (dhandle, info, name, dtype,
                                  DEBUG_LOCAL_STATIC, value))
-       return FALSE;
+       return false;
       break;
 
     case 'v':
       /* Reference parameter.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_parameter (dhandle, name, dtype, DEBUG_PARM_REFERENCE,
                                    value))
-       return FALSE;
+       return false;
       break;
 
     case 'a':
       /* Reference parameter which is in a register.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! debug_record_parameter (dhandle, name, dtype, DEBUG_PARM_REF_REG,
                                    value))
-       return FALSE;
+       return false;
       break;
 
     case 'X':
@@ -1093,24 +1136,24 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
         that Pascal uses it too, but when I tried it Pascal used
         "x:3" (local symbol) instead.  */
       dtype = parse_stab_type (dhandle, info, (const char *) NULL, &p,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, string_end);
       if (dtype == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
       if (! stab_record_variable (dhandle, info, name, dtype, DEBUG_LOCAL,
                                  value))
-       return FALSE;
+       return false;
       break;
 
     case 'Y':
       /* SUNPro C++ Namespace =Yn0.  */
       /* Skip the namespace mapping, as it is not used now.  */
-      if (*(++p) == 'n' && *(++p) == '0')
+      if (*p++ != 0 && *p++ == 'n' && *p++ == '0')
        {
          /* =Yn0name; */
-         while (*p != ';')
+         while (*p && *p != ';')
            ++p;
-         ++p;
-         return TRUE;
+         if (*p)
+           return true;
        }
       /* TODO SUNPro C++ support:
          Support default arguments after F,P parameters
@@ -1123,13 +1166,13 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
 
     default:
       bad_stab (string);
-      return FALSE;
+      return false;
     }
 
   /* FIXME: gdb converts structure values to structure pointers in a
      couple of cases, depending upon the target.  */
 
-  return TRUE;
+  return true;
 }
 
 /* Parse a stabs type.  The typename argument is non-NULL if this is a
@@ -1138,12 +1181,17 @@ parse_stab_string (void *dhandle, struct stab_handle *info, int stabtype,
    store the slot used if the type is being defined.  */
 
 static debug_type
-parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name, const char **pp, debug_type **slotp)
+parse_stab_type (void *                dhandle,
+                struct stab_handle *  info,
+                const char *          type_name,
+                const char **         pp,
+                debug_type **         slotp,
+                const char *          p_end)
 {
   const char *orig;
   int typenums[2];
   int size;
-  bfd_boolean stringp;
+  bool stringp;
   int descriptor;
   debug_type dtype;
 
@@ -1151,11 +1199,13 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
     *slotp = NULL;
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   size = -1;
-  stringp = FALSE;
+  stringp = false;
 
-  info->self_crossref = FALSE;
+  info->self_crossref = false;
 
   /* Read type number if present.  The type number may be omitted.
      for instance in a two-dimensional array declared with type
@@ -1168,7 +1218,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
     }
   else
     {
-      if (! parse_stab_type_number (pp, typenums))
+      if (! parse_stab_type_number (pp, typenums, p_end))
        return DEBUG_TYPE_NULL;
 
       if (**pp != '=')
@@ -1190,7 +1240,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
         the stabs information records both i and j as having the same
         type.  This could be fixed by patching the compiler.  */
       if (slotp != NULL && typenums[0] >= 0 && typenums[1] >= 0)
-       *slotp = stab_find_slot (info, typenums);
+       *slotp = stab_find_slot (dhandle, info, typenums);
 
       /* Type is being defined here.  */
       /* Skip the '='.  */
@@ -1228,9 +1278,13 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
              break;
 
            case 'S':
-             stringp = TRUE;
+             stringp = true;
              break;
 
+           case 0:
+             bad_stab (orig);
+             return DEBUG_TYPE_NULL;
+
            default:
              /* Ignore unrecognized type attributes, so future
                 compilers can invent new ones.  */
@@ -1261,6 +1315,10 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
          case 'e':
            code = DEBUG_KIND_ENUM;
            break;
+         case 0:
+             bad_stab (orig);
+             return DEBUG_TYPE_NULL;
+           
          default:
            /* Complain and keep going, so compilers can invent new
               cross-reference types.  */
@@ -1305,7 +1363,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
        if (type_name != NULL
            && strncmp (type_name, *pp, p - *pp) == 0
            && type_name[p - *pp] == '\0')
-         info->self_crossref = TRUE;
+         info->self_crossref = true;
 
        dtype = stab_find_tagged_type (dhandle, info, *pp, p - *pp, code);
 
@@ -1334,7 +1392,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
        hold = *pp;
 
        /* Peek ahead at the number to detect void.  */
-       if (! parse_stab_type_number (pp, xtypenums))
+       if (! parse_stab_type_number (pp, xtypenums, p_end))
          return DEBUG_TYPE_NULL;
 
        if (typenums[0] == xtypenums[0] && typenums[1] == xtypenums[1])
@@ -1351,7 +1409,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
               This means that we can deal with something like
               t(1,2)=(3,4)=... which the Lucid compiler uses.  */
            dtype = parse_stab_type (dhandle, info, (const char *) NULL,
-                                    pp, (debug_type **) NULL);
+                                    pp, (debug_type **) NULL, p_end);
            if (dtype == DEBUG_TYPE_NULL)
              return DEBUG_TYPE_NULL;
          }
@@ -1370,7 +1428,8 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
                                       parse_stab_type (dhandle, info,
                                                        (const char *) NULL,
                                                        pp,
-                                                       (debug_type **) NULL));
+                                                       (debug_type **) NULL,
+                                                       p_end));
       break;
 
     case '&':
@@ -1378,7 +1437,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
       dtype = (debug_make_reference_type
               (dhandle,
                parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                (debug_type **) NULL)));
+                                (debug_type **) NULL, p_end)));
       break;
 
     case 'f':
@@ -1387,8 +1446,8 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
       dtype = (debug_make_function_type
               (dhandle,
                parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                (debug_type **) NULL),
-               (debug_type *) NULL, FALSE));
+                                (debug_type **) NULL, p_end),
+               (debug_type *) NULL, false));
       break;
 
     case 'k':
@@ -1398,7 +1457,8 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
                                     parse_stab_type (dhandle, info,
                                                      (const char *) NULL,
                                                      pp,
-                                                     (debug_type **) NULL));
+                                                     (debug_type **) NULL,
+                                                     p_end));
       break;
 
     case 'B':
@@ -1407,7 +1467,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
       dtype = (debug_make_volatile_type
               (dhandle,
                parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                (debug_type **) NULL)));
+                                (debug_type **) NULL, p_end)));
       break;
 
     case '@':
@@ -1420,7 +1480,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
        /* Member type.  */
 
        domain = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                 (debug_type **) NULL);
+                                 (debug_type **) NULL, p_end);
        if (domain == DEBUG_TYPE_NULL)
          return DEBUG_TYPE_NULL;
 
@@ -1432,7 +1492,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
        ++*pp;
 
        memtype = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                  (debug_type **) NULL);
+                                  (debug_type **) NULL, p_end);
        if (memtype == DEBUG_TYPE_NULL)
          return DEBUG_TYPE_NULL;
 
@@ -1448,7 +1508,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
 
          ++*pp;
          return_type = parse_stab_type (dhandle, info, (const char *) NULL,
-                                        pp, (debug_type **) NULL);
+                                        pp, (debug_type **) NULL, p_end);
          if (return_type == DEBUG_TYPE_NULL)
            return DEBUG_TYPE_NULL;
          if (**pp != ';')
@@ -1459,19 +1519,19 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
          ++*pp;
          dtype = debug_make_method_type (dhandle, return_type,
                                          DEBUG_TYPE_NULL,
-                                         (debug_type *) NULL, FALSE);
+                                         (debug_type *) NULL, false);
        }
       else
        {
          debug_type domain;
          debug_type return_type;
-         debug_type *args;
+         debug_type *args, *xargs;
          unsigned int n;
          unsigned int alloc;
-         bfd_boolean varargs;
+         bool varargs;
 
          domain = parse_stab_type (dhandle, info, (const char *) NULL,
-                                   pp, (debug_type **) NULL);
+                                   pp, (debug_type **) NULL, p_end);
          if (domain == DEBUG_TYPE_NULL)
            return DEBUG_TYPE_NULL;
 
@@ -1483,18 +1543,19 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
          ++*pp;
 
          return_type = parse_stab_type (dhandle, info, (const char *) NULL,
-                                        pp, (debug_type **) NULL);
+                                        pp, (debug_type **) NULL, p_end);
          if (return_type == DEBUG_TYPE_NULL)
            return DEBUG_TYPE_NULL;
 
          alloc = 10;
-         args = (debug_type *) xmalloc (alloc * sizeof *args);
+         args = xmalloc (alloc * sizeof (*args));
          n = 0;
          while (**pp != ';')
            {
              if (**pp != ',')
                {
                  bad_stab (orig);
+                 free (args);
                  return DEBUG_TYPE_NULL;
                }
              ++*pp;
@@ -1502,14 +1563,16 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
              if (n + 1 >= alloc)
                {
                  alloc += 10;
-                 args = ((debug_type *)
-                         xrealloc (args, alloc * sizeof *args));
+                 args = xrealloc (args, alloc * sizeof (*args));
                }
 
              args[n] = parse_stab_type (dhandle, info, (const char *) NULL,
-                                        pp, (debug_type **) NULL);
+                                        pp, (debug_type **) NULL, p_end);
              if (args[n] == DEBUG_TYPE_NULL)
-               return DEBUG_TYPE_NULL;
+               {
+                 free (args);
+                 return DEBUG_TYPE_NULL;
+               }
              ++n;
            }
          ++*pp;
@@ -1519,46 +1582,49 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
             the void type.  */
          if (n == 0
              || debug_get_type_kind (dhandle, args[n - 1]) != DEBUG_KIND_VOID)
-           varargs = TRUE;
+           varargs = true;
          else
            {
              --n;
-             varargs = FALSE;
+             varargs = false;
            }
 
          args[n] = DEBUG_TYPE_NULL;
+         xargs = debug_xalloc (dhandle, (n + 1) * sizeof (*args));
+         memcpy (xargs, args, (n + 1) * sizeof (*args));
+         free (args);
 
-         dtype = debug_make_method_type (dhandle, return_type, domain, args,
+         dtype = debug_make_method_type (dhandle, return_type, domain, xargs,
                                          varargs);
        }
       break;
 
     case 'r':
       /* Range type.  */
-      dtype = parse_stab_range_type (dhandle, info, type_name, pp, typenums);
+      dtype = parse_stab_range_type (dhandle, info, type_name, pp, typenums, p_end);
       break;
 
     case 'b':
       /* FIXME: gdb checks os9k_stabs here.  */
       /* Sun ACC builtin int type.  */
-      dtype = parse_stab_sun_builtin_type (dhandle, pp);
+      dtype = parse_stab_sun_builtin_type (dhandle, pp, p_end);
       break;
 
     case 'R':
       /* Sun ACC builtin float type.  */
-      dtype = parse_stab_sun_floating_type (dhandle, pp);
+      dtype = parse_stab_sun_floating_type (dhandle, pp, p_end);
       break;
 
     case 'e':
       /* Enumeration type.  */
-      dtype = parse_stab_enum_type (dhandle, pp);
+      dtype = parse_stab_enum_type (dhandle, pp, p_end);
       break;
 
     case 's':
     case 'u':
       /* Struct or union type.  */
       dtype = parse_stab_struct_type (dhandle, info, type_name, pp,
-                                     descriptor == 's', typenums);
+                                     descriptor == 's', typenums, p_end);
       break;
 
     case 'a':
@@ -1570,7 +1636,7 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
        }
       ++*pp;
 
-      dtype = parse_stab_array_type (dhandle, info, pp, stringp);
+      dtype = parse_stab_array_type (dhandle, info, pp, stringp, p_end);
       break;
 
     case 'S':
@@ -1578,7 +1644,8 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
                                   parse_stab_type (dhandle, info,
                                                    (const char *) NULL,
                                                    pp,
-                                                   (debug_type **) NULL),
+                                                   (debug_type **) NULL,
+                                                   p_end),
                                   stringp);
       break;
 
@@ -1610,8 +1677,8 @@ parse_stab_type (void *dhandle, struct stab_handle *info, const char *type_name,
    single number N is equivalent to (0,N).  Return the two numbers by
    storing them in the vector TYPENUMS.  */
 
-static bfd_boolean
-parse_stab_type_number (const char **pp, int *typenums)
+static bool
+parse_stab_type_number (const char **pp, int *typenums, const char *p_end)
 {
   const char *orig;
 
@@ -1620,50 +1687,57 @@ parse_stab_type_number (const char **pp, int *typenums)
   if (**pp != '(')
     {
       typenums[0] = 0;
-      typenums[1] = (int) parse_number (pp, (bfd_boolean *) NULL);
+      typenums[1] = (int) parse_number (pp, (bool *) NULL, p_end);
+      return true;
     }
-  else
+
+  ++*pp;
+  typenums[0] = (int) parse_number (pp, (bool *) NULL, p_end);
+  if (**pp != ',')
     {
-      ++*pp;
-      typenums[0] = (int) parse_number (pp, (bfd_boolean *) NULL);
-      if (**pp != ',')
-       {
-         bad_stab (orig);
-         return FALSE;
-       }
-      ++*pp;
-      typenums[1] = (int) parse_number (pp, (bfd_boolean *) NULL);
-      if (**pp != ')')
-       {
-         bad_stab (orig);
-         return FALSE;
-       }
-      ++*pp;
+      bad_stab (orig);
+      return false;
     }
 
-  return TRUE;
+  ++*pp;
+  typenums[1] = (int) parse_number (pp, (bool *) NULL, p_end);
+  if (**pp != ')')
+    {
+      bad_stab (orig);
+      return false;
+    }
+
+  ++*pp;
+  return true;
 }
 
 /* Parse a range type.  */
 
 static debug_type
-parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type_name, const char **pp, const int *typenums)
+parse_stab_range_type (void *                dhandle,
+                      struct stab_handle *  info,
+                      const char *          type_name,
+                      const char **         pp,
+                      const int *           typenums,
+                      const char *          p_end)
 {
   const char *orig;
   int rangenums[2];
-  bfd_boolean self_subrange;
+  bool self_subrange;
   debug_type index_type;
   const char *s2, *s3;
   bfd_signed_vma n2, n3;
-  bfd_boolean ov2, ov3;
+  bool ov2, ov3;
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   index_type = DEBUG_TYPE_NULL;
 
   /* First comes a type we are a subrange of.
      In C it is usually 0, 1 or the type being defined.  */
-  if (! parse_stab_type_number (pp, rangenums))
+  if (! parse_stab_type_number (pp, rangenums, p_end))
     return DEBUG_TYPE_NULL;
 
   self_subrange = (rangenums[0] == typenums[0]
@@ -1673,7 +1747,7 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
     {
       *pp = orig;
       index_type = parse_stab_type (dhandle, info, (const char *) NULL,
-                                   pp, (debug_type **) NULL);
+                                   pp, (debug_type **) NULL, p_end);
       if (index_type == DEBUG_TYPE_NULL)
        return DEBUG_TYPE_NULL;
     }
@@ -1684,7 +1758,7 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
   /* The remaining two operands are usually lower and upper bounds of
      the range.  But in some special cases they mean something else.  */
   s2 = *pp;
-  n2 = parse_number (pp, &ov2);
+  n2 = parse_number (pp, &ov2, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1693,7 +1767,7 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
   ++*pp;
 
   s3 = *pp;
-  n3 = parse_number (pp, &ov3);
+  n3 = parse_number (pp, &ov3, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1710,13 +1784,13 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
 #define ULLHIGH "01777777777777777777777;"
       if (index_type == DEBUG_TYPE_NULL)
        {
-         if (CONST_STRNEQ (s2, LLLOW)
-             && CONST_STRNEQ (s3, LLHIGH))
-           return debug_make_int_type (dhandle, 8, FALSE);
+         if (startswith (s2, LLLOW)
+             && startswith (s3, LLHIGH))
+           return debug_make_int_type (dhandle, 8, false);
          if (! ov2
              && n2 == 0
-             && CONST_STRNEQ (s3, ULLHIGH))
-           return debug_make_int_type (dhandle, 8, TRUE);
+             && startswith (s3, ULLHIGH))
+           return debug_make_int_type (dhandle, 8, true);
        }
 
       warn_stab (orig, _("numeric overflow"));
@@ -1749,50 +1823,50 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
          if (type_name != NULL)
            {
              if (strcmp (type_name, "long long int") == 0)
-               return debug_make_int_type (dhandle, 8, FALSE);
+               return debug_make_int_type (dhandle, 8, false);
              else if (strcmp (type_name, "long long unsigned int") == 0)
-               return debug_make_int_type (dhandle, 8, TRUE);
+               return debug_make_int_type (dhandle, 8, true);
            }
          /* FIXME: The size here really depends upon the target.  */
-         return debug_make_int_type (dhandle, 4, TRUE);
+         return debug_make_int_type (dhandle, 4, true);
        }
 
       /* A range of 0 to 127 is char.  */
       if (self_subrange && n2 == 0 && n3 == 127)
-       return debug_make_int_type (dhandle, 1, FALSE);
+       return debug_make_int_type (dhandle, 1, false);
 
       /* FIXME: gdb checks for the language CHILL here.  */
 
       if (n2 == 0)
        {
          if (n3 < 0)
-           return debug_make_int_type (dhandle, - n3, TRUE);
+           return debug_make_int_type (dhandle, - n3, true);
          else if (n3 == 0xff)
-           return debug_make_int_type (dhandle, 1, TRUE);
+           return debug_make_int_type (dhandle, 1, true);
          else if (n3 == 0xffff)
-           return debug_make_int_type (dhandle, 2, TRUE);
+           return debug_make_int_type (dhandle, 2, true);
          else if (n3 == (bfd_signed_vma) 0xffffffff)
-           return debug_make_int_type (dhandle, 4, TRUE);
+           return debug_make_int_type (dhandle, 4, true);
 #ifdef BFD64
-         else if (n3 == ((((bfd_signed_vma) 0xffffffff) << 32) | 0xffffffff))
-           return debug_make_int_type (dhandle, 8, TRUE);
+         else if (n3 == (bfd_signed_vma) 0xffffffffffffffffLL)
+           return debug_make_int_type (dhandle, 8, true);
 #endif
        }
       else if (n3 == 0
               && n2 < 0
               && (self_subrange || n2 == -8))
-       return debug_make_int_type (dhandle, - n2, TRUE);
+       return debug_make_int_type (dhandle, - n2, true);
       else if (n2 == - n3 - 1 || n2 == n3 + 1)
        {
          if (n3 == 0x7f)
-           return debug_make_int_type (dhandle, 1, FALSE);
+           return debug_make_int_type (dhandle, 1, false);
          else if (n3 == 0x7fff)
-           return debug_make_int_type (dhandle, 2, FALSE);
+           return debug_make_int_type (dhandle, 2, false);
          else if (n3 == 0x7fffffff)
-           return debug_make_int_type (dhandle, 4, FALSE);
+           return debug_make_int_type (dhandle, 4, false);
 #ifdef BFD64
          else if (n3 == ((((bfd_vma) 0x7fffffff) << 32) | 0xffffffff))
-           return debug_make_int_type (dhandle, 8, FALSE);
+           return debug_make_int_type (dhandle, 8, false);
 #endif
        }
     }
@@ -1812,7 +1886,7 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
       /* Does this actually ever happen?  Is that why we are worrying
          about dealing with it rather than just calling error_type?  */
       warn_stab (orig, _("missing index type"));
-      index_type = debug_make_int_type (dhandle, 4, FALSE);
+      index_type = debug_make_int_type (dhandle, 4, false);
     }
 
   return debug_make_range_type (dhandle, index_type, n2, n3);
@@ -1831,21 +1905,23 @@ parse_stab_range_type (void *dhandle, struct stab_handle *info, const char *type
    FIXME.  */
 
 static debug_type
-parse_stab_sun_builtin_type (void *dhandle, const char **pp)
+parse_stab_sun_builtin_type (void *dhandle, const char **pp, const char * p_end)
 {
   const char *orig;
-  bfd_boolean unsignedp;
+  bool unsignedp;
   bfd_vma bits;
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   switch (**pp)
     {
     case 's':
-      unsignedp = FALSE;
+      unsignedp = false;
       break;
     case 'u':
-      unsignedp = TRUE;
+      unsignedp = true;
       break;
     default:
       bad_stab (orig);
@@ -1866,7 +1942,7 @@ parse_stab_sun_builtin_type (void *dhandle, const char **pp)
      by this type, except that unsigned short is 4 instead of 2.
      Since this information is redundant with the third number,
      we will ignore it.  */
-  (void) parse_number (pp, (bfd_boolean *) NULL);
+  (void) parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1875,7 +1951,7 @@ parse_stab_sun_builtin_type (void *dhandle, const char **pp)
   ++*pp;
 
   /* The second number is always 0, so ignore it too.  */
-  (void) parse_number (pp, (bfd_boolean *) NULL);
+  (void) parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1884,7 +1960,7 @@ parse_stab_sun_builtin_type (void *dhandle, const char **pp)
   ++*pp;
 
   /* The third number is the number of bits for this type.  */
-  bits = parse_number (pp, (bfd_boolean *) NULL);
+  bits = parse_number (pp, (bool *) NULL, p_end);
 
   /* The type *should* end with a semicolon.  If it are embedded
      in a larger type the semicolon may be the only way to know where
@@ -1904,17 +1980,19 @@ parse_stab_sun_builtin_type (void *dhandle, const char **pp)
 /* Parse a builtin floating type generated by the Sun compiler.  */
 
 static debug_type
-parse_stab_sun_floating_type (void *dhandle, const char **pp)
+parse_stab_sun_floating_type (void *dhandle, const char **pp, const char *p_end)
 {
   const char *orig;
   bfd_vma details;
   bfd_vma bytes;
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   /* The first number has more details about the type, for example
      FN_COMPLEX.  */
-  details = parse_number (pp, (bfd_boolean *) NULL);
+  details = parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1922,7 +2000,7 @@ parse_stab_sun_floating_type (void *dhandle, const char **pp)
     }
 
   /* The second number is the number of bytes occupied by this type */
-  bytes = parse_number (pp, (bfd_boolean *) NULL);
+  bytes = parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -1940,15 +2018,17 @@ parse_stab_sun_floating_type (void *dhandle, const char **pp)
 /* Handle an enum type.  */
 
 static debug_type
-parse_stab_enum_type (void *dhandle, const char **pp)
+parse_stab_enum_type (void *dhandle, const char **pp, const char * p_end)
 {
   const char *orig;
-  const char **names;
-  bfd_signed_vma *values;
+  const char **names, **xnames;
+  bfd_signed_vma *values, *xvalues;
   unsigned int n;
   unsigned int alloc;
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   /* FIXME: gdb checks os9k_stabs here.  */
 
@@ -1956,8 +2036,14 @@ parse_stab_enum_type (void *dhandle, const char **pp)
      my guess is it's a type of some sort.  Just ignore it.  */
   if (**pp == '-')
     {
-      while (**pp != ':')
+      while (**pp != ':' && **pp != 0)
        ++*pp;
+
+      if (**pp == 0)
+       {
+         bad_stab (orig);
+         return DEBUG_TYPE_NULL;
+       }
       ++*pp;
     }
 
@@ -1965,8 +2051,8 @@ parse_stab_enum_type (void *dhandle, const char **pp)
      The input syntax is NAME:VALUE,NAME:VALUE, and so on.
      A semicolon or comma instead of a NAME means the end.  */
   alloc = 10;
-  names = (const char **) xmalloc (alloc * sizeof *names);
-  values = (bfd_signed_vma *) xmalloc (alloc * sizeof *values);
+  names = xmalloc (alloc * sizeof (*names));
+  values = xmalloc (alloc * sizeof (*values));
   n = 0;
   while (**pp != '\0' && **pp != ';' && **pp != ',')
     {
@@ -1975,17 +2061,24 @@ parse_stab_enum_type (void *dhandle, const char **pp)
       bfd_signed_vma val;
 
       p = *pp;
-      while (*p != ':')
+      while (*p != ':' && *p != 0)
        ++p;
 
-      name = savestring (*pp, p - *pp);
+      if (*p == 0)
+       {
+         bad_stab (orig);
+         free (names);
+         free (values);
+         return DEBUG_TYPE_NULL;
+       }
+
+      name = savestring (dhandle, *pp, p - *pp);
 
       *pp = p + 1;
-      val = (bfd_signed_vma) parse_number (pp, (bfd_boolean *) NULL);
+      val = (bfd_signed_vma) parse_number (pp, (bool *) NULL, p_end);
       if (**pp != ',')
        {
          bad_stab (orig);
-         free (name);
          free (names);
          free (values);
          return DEBUG_TYPE_NULL;
@@ -1995,10 +2088,8 @@ parse_stab_enum_type (void *dhandle, const char **pp)
       if (n + 1 >= alloc)
        {
          alloc += 10;
-         names = ((const char **)
-                  xrealloc (names, alloc * sizeof *names));
-         values = ((bfd_signed_vma *)
-                   xrealloc (values, alloc * sizeof *values));
+         names = xrealloc (names, alloc * sizeof (*names));
+         values = xrealloc (values, alloc * sizeof (*values));
        }
 
       names[n] = name;
@@ -2008,11 +2099,17 @@ parse_stab_enum_type (void *dhandle, const char **pp)
 
   names[n] = NULL;
   values[n] = 0;
+  xnames = debug_xalloc (dhandle, (n + 1) * sizeof (*names));
+  memcpy (xnames, names, (n + 1) * sizeof (*names));
+  free (names);
+  xvalues = debug_xalloc (dhandle, (n + 1) * sizeof (*names));
+  memcpy (xvalues, values, (n + 1) * sizeof (*names));
+  free (values);
 
   if (**pp == ';')
     ++*pp;
 
-  return debug_make_enum_type (dhandle, names, values);
+  return debug_make_enum_type (dhandle, xnames, xvalues);
 }
 
 /* Read the description of a structure (or union type) and return an object
@@ -2023,32 +2120,32 @@ parse_stab_enum_type (void *dhandle, const char **pp)
    *PP will point to "4a:1,0,32;;".  */
 
 static debug_type
-parse_stab_struct_type (void *dhandle, struct stab_handle *info,
-                       const char *tagname, const char **pp,
-                       bfd_boolean structp, const int *typenums)
+parse_stab_struct_type (void *dhandle,
+                       struct stab_handle *info,
+                       const char *tagname,
+                       const char **pp,
+                       bool structp,
+                       const int *typenums,
+                       const char *p_end)
 {
   bfd_vma size;
   debug_baseclass *baseclasses;
   debug_field *fields = NULL;
-  bfd_boolean statics;
+  bool statics;
   debug_method *methods;
   debug_type vptrbase;
-  bfd_boolean ownvptr;
+  bool ownvptr;
 
   /* Get the size.  */
-  size = parse_number (pp, (bfd_boolean *) NULL);
+  size = parse_number (pp, (bool *) NULL, p_end);
 
   /* Get the other information.  */
-  if (! parse_stab_baseclasses (dhandle, info, pp, &baseclasses)
-      || ! parse_stab_struct_fields (dhandle, info, pp, &fields, &statics)
-      || ! parse_stab_members (dhandle, info, tagname, pp, typenums, &methods)
+  if (! parse_stab_baseclasses (dhandle, info, pp, &baseclasses, p_end)
+      || ! parse_stab_struct_fields (dhandle, info, pp, &fields, &statics, p_end)
+      || ! parse_stab_members (dhandle, info, tagname, pp, typenums, &methods, p_end)
       || ! parse_stab_tilde_field (dhandle, info, pp, typenums, &vptrbase,
-                                  &ownvptr))
-    {
-      if (fields != NULL)
-       free (fields);
-      return DEBUG_TYPE_NULL;
-    }
+                                  &ownvptr, p_end))
+    return DEBUG_TYPE_NULL;
 
   if (! statics
       && baseclasses == NULL
@@ -2085,9 +2182,12 @@ parse_stab_struct_type (void *dhandle, struct stab_handle *info,
 
   Return TRUE for success, FALSE for failure.  */
 
-static bfd_boolean
-parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
-                       const char **pp, debug_baseclass **retp)
+static bool
+parse_stab_baseclasses (void *                dhandle,
+                       struct stab_handle *  info,
+                       const char **         pp,
+                       debug_baseclass **    retp,
+                       const char *          p_end)
 {
   const char *orig;
   unsigned int c, i;
@@ -2096,28 +2196,30 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
   *retp = NULL;
 
   orig = *pp;
+  if (orig >= p_end)
+    return false;
 
   if (**pp != '!')
     {
       /* No base classes.  */
-      return TRUE;
+      return true;
     }
   ++*pp;
 
-  c = (unsigned int) parse_number (pp, (bfd_boolean *) NULL);
+  c = (unsigned int) parse_number (pp, (bool *) NULL, p_end);
 
   if (**pp != ',')
     {
       bad_stab (orig);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
-  classes = (debug_baseclass *) xmalloc ((c + 1) * sizeof (**retp));
+  classes = debug_xalloc (dhandle, (c + 1) * sizeof (*classes));
 
   for (i = 0; i < c; i++)
     {
-      bfd_boolean is_virtual;
+      bool is_virtual;
       enum debug_visibility visibility;
       bfd_vma bitpos;
       debug_type type;
@@ -2125,14 +2227,17 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
       switch (**pp)
        {
        case '0':
-         is_virtual = FALSE;
+         is_virtual = false;
          break;
        case '1':
-         is_virtual = TRUE;
+         is_virtual = true;
          break;
+       case 0:
+         bad_stab (orig);
+         return false;
        default:
          warn_stab (orig, _("unknown virtual character for baseclass"));
-         is_virtual = FALSE;
+         is_virtual = false;
          break;
        }
       ++*pp;
@@ -2148,6 +2253,9 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
        case '2':
          visibility = DEBUG_VISIBILITY_PUBLIC;
          break;
+       case 0:
+         bad_stab (orig);
+         return false;
        default:
          warn_stab (orig, _("unknown visibility character for baseclass"));
          visibility = DEBUG_VISIBILITY_PUBLIC;
@@ -2158,26 +2266,26 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
       /* The remaining value is the bit offset of the portion of the
         object corresponding to this baseclass.  Always zero in the
         absence of multiple inheritance.  */
-      bitpos = parse_number (pp, (bfd_boolean *) NULL);
+      bitpos = parse_number (pp, (bool *) NULL, p_end);
       if (**pp != ',')
        {
          bad_stab (orig);
-         return FALSE;
+         return false;
        }
       ++*pp;
 
       type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                             (debug_type **) NULL);
+                             (debug_type **) NULL, p_end);
       if (type == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
 
       classes[i] = debug_make_baseclass (dhandle, type, bitpos, is_virtual,
                                         visibility);
       if (classes[i] == DEBUG_BASECLASS_NULL)
-       return FALSE;
+       return false;
 
       if (**pp != ';')
-       return FALSE;
+       return false;
       ++*pp;
     }
 
@@ -2185,7 +2293,7 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
 
   *retp = classes;
 
-  return TRUE;
+  return true;
 }
 
 /* Read struct or class data fields.  They have the form:
@@ -2208,25 +2316,30 @@ parse_stab_baseclasses (void *dhandle, struct stab_handle *info,
 
    Returns 1 for success, 0 for failure.  */
 
-static bfd_boolean
-parse_stab_struct_fields (void *dhandle, struct stab_handle *info,
-                         const char **pp, debug_field **retp,
-                         bfd_boolean *staticsp)
+static bool
+parse_stab_struct_fields (void *dhandle,
+                         struct stab_handle *info,
+                         const char **pp,
+                         debug_field **retp,
+                         bool *staticsp,
+                         const char * p_end)
 {
   const char *orig;
   const char *p;
-  debug_field *fields;
+  debug_field *fields, *xfields;
   unsigned int c;
   unsigned int alloc;
 
   *retp = NULL;
-  *staticsp = FALSE;
+  *staticsp = false;
 
   orig = *pp;
+  if (orig >= p_end)
+    return false;
 
   c = 0;
   alloc = 10;
-  fields = (debug_field *) xmalloc (alloc * sizeof *fields);
+  fields = xmalloc (alloc * sizeof (*fields));
   while (**pp != ';')
     {
       /* FIXME: gdb checks os9k_stabs here.  */
@@ -2237,8 +2350,7 @@ parse_stab_struct_fields (void *dhandle, struct stab_handle *info,
       if (c + 1 >= alloc)
        {
          alloc += 10;
-         fields = ((debug_field *)
-                   xrealloc (fields, alloc * sizeof *fields));
+         fields = xrealloc (fields, alloc * sizeof (*fields));
        }
 
       /* If it starts with CPLUS_MARKER it is a special abbreviation,
@@ -2251,10 +2363,10 @@ parse_stab_struct_fields (void *dhandle, struct stab_handle *info,
       if ((*p == '$' || *p == '.') && p[1] != '_')
        {
          ++*pp;
-         if (! parse_stab_cpp_abbrev (dhandle, info, pp, fields + c))
+         if (! parse_stab_cpp_abbrev (dhandle, info, pp, fields + c, p_end))
            {
              free (fields);
-             return FALSE;
+             return false;
            }
          ++c;
          continue;
@@ -2270,31 +2382,40 @@ parse_stab_struct_fields (void *dhandle, struct stab_handle *info,
        {
          bad_stab (orig);
          free (fields);
-         return FALSE;
+         return false;
        }
 
       if (p[1] == ':')
        break;
 
       if (! parse_stab_one_struct_field (dhandle, info, pp, p, fields + c,
-                                        staticsp))
-       return FALSE;
+                                        staticsp, p_end))
+       {
+         free (fields);
+         return false;
+       }
 
       ++c;
     }
 
   fields[c] = DEBUG_FIELD_NULL;
+  xfields = debug_xalloc (dhandle, (c + 1) * sizeof (*fields));
+  memcpy (xfields, fields, (c + 1) * sizeof (*fields));
+  free (fields);
 
-  *retp = fields;
+  *retp = xfields;
 
-  return TRUE;
+  return true;
 }
 
 /* Special GNU C++ name.  */
 
-static bfd_boolean
-parse_stab_cpp_abbrev (void *dhandle, struct stab_handle *info,
-                      const char **pp, debug_field *retp)
+static bool
+parse_stab_cpp_abbrev (void *                dhandle,
+                      struct stab_handle *  info,
+                      const char **         pp,
+                      debug_field *         retp,
+                      const char *          p_end)
 {
   const char *orig;
   int cpp_abbrev;
@@ -2303,19 +2424,27 @@ parse_stab_cpp_abbrev (void *dhandle, struct stab_handle *info,
   const char *type_name;
   debug_type type;
   bfd_vma bitpos;
+  size_t len;
 
   *retp = DEBUG_FIELD_NULL;
 
   orig = *pp;
+  if (orig >= p_end)
+    return false;
 
   if (**pp != 'v')
     {
       bad_stab (*pp);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
   cpp_abbrev = **pp;
+  if (cpp_abbrev == 0)
+    {
+      bad_stab (orig);
+      return false;
+    }
   ++*pp;
 
   /* At this point, *pp points to something like "22:23=*22...", where
@@ -2324,9 +2453,9 @@ parse_stab_cpp_abbrev (void *dhandle, struct stab_handle *info,
      name, and construct the field name.  */
 
   context = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                            (debug_type **) NULL);
+                            (debug_type **) NULL, p_end);
   if (context == DEBUG_TYPE_NULL)
-    return FALSE;
+    return false;
 
   switch (cpp_abbrev)
     {
@@ -2342,7 +2471,10 @@ parse_stab_cpp_abbrev (void *dhandle, struct stab_handle *info,
          warn_stab (orig, _("unnamed $vb type"));
          type_name = "FOO";
        }
-      name = concat ("_vb$", type_name, (const char *) NULL);
+      len = strlen (type_name);
+      name = debug_xalloc (dhandle, len + sizeof ("_vb$"));
+      memcpy ((char *) name, "_vb$", sizeof ("_vb$") - 1);
+      memcpy ((char *) name + sizeof ("_vb$") - 1, type_name, len + 1);
       break;
     default:
       warn_stab (orig, _("unrecognized C++ abbreviation"));
@@ -2353,41 +2485,45 @@ parse_stab_cpp_abbrev (void *dhandle, struct stab_handle *info,
   if (**pp != ':')
     {
       bad_stab (orig);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
   type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                         (debug_type **) NULL);
+                         (debug_type **) NULL, p_end);
   if (**pp != ',')
     {
       bad_stab (orig);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
-  bitpos = parse_number (pp, (bfd_boolean *) NULL);
+  bitpos = parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
   *retp = debug_make_field (dhandle, name, type, bitpos, 0,
                            DEBUG_VISIBILITY_PRIVATE);
   if (*retp == DEBUG_FIELD_NULL)
-    return FALSE;
+    return false;
 
-  return TRUE;
+  return true;
 }
 
 /* Parse a single field in a struct or union.  */
 
-static bfd_boolean
-parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
-                            const char **pp, const char *p,
-                            debug_field *retp, bfd_boolean *staticsp)
+static bool
+parse_stab_one_struct_field (void *dhandle,
+                            struct stab_handle *info,
+                            const char **pp,
+                            const char *p,
+                            debug_field *retp,
+                            bool *staticsp,
+                            const char *p_end)
 {
   const char *orig;
   char *name;
@@ -2397,10 +2533,12 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
   bfd_vma bitsize;
 
   orig = *pp;
+  if (orig >= p_end)
+    return false;
 
   /* FIXME: gdb checks ARM_DEMANGLING here.  */
 
-  name = savestring (*pp, p - *pp);
+  name = savestring (dhandle, *pp, p - *pp);
 
   *pp = p + 1;
 
@@ -2420,6 +2558,9 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
        case '2':
          visibility = DEBUG_VISIBILITY_PUBLIC;
          break;
+       case 0:
+         bad_stab (orig);
+         return false;
        default:
          warn_stab (orig, _("unknown visibility character for field"));
          visibility = DEBUG_VISIBILITY_PUBLIC;
@@ -2429,12 +2570,9 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
     }
 
   type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                         (debug_type **) NULL);
+                         (debug_type **) NULL, p_end);
   if (type == DEBUG_TYPE_NULL)
-    {
-      free (name);
-      return FALSE;
-    }
+    return false;
 
   if (**pp == ':')
     {
@@ -2446,44 +2584,40 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
       if (p == NULL)
        {
          bad_stab (orig);
-         free (name);
-         return FALSE;
+         return false;
        }
 
-      varname = savestring (*pp, p - *pp);
+      varname = savestring (dhandle, *pp, p - *pp);
 
       *pp = p + 1;
 
       *retp = debug_make_static_member (dhandle, name, type, varname,
                                        visibility);
-      *staticsp = TRUE;
+      *staticsp = true;
 
-      return TRUE;
+      return true;
     }
 
   if (**pp != ',')
     {
       bad_stab (orig);
-      free (name);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
-  bitpos = parse_number (pp, (bfd_boolean *) NULL);
+  bitpos = parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ',')
     {
       bad_stab (orig);
-      free (name);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
-  bitsize = parse_number (pp, (bfd_boolean *) NULL);
+  bitsize = parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
-      free (name);
-      return FALSE;
+      return false;
     }
   ++*pp;
 
@@ -2509,7 +2643,7 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
 
   *retp = debug_make_field (dhandle, name, type, bitpos, bitsize, visibility);
 
-  return TRUE;
+  return true;
 }
 
 /* Read member function stabs info for C++ classes.  The form of each member
@@ -2525,22 +2659,28 @@ parse_stab_one_struct_field (void *dhandle, struct stab_handle *info,
    $ is the CPLUS_MARKER (usually '$'), `*' holds the place for an operator
    name (such as `+=') and `.' marks the end of the operator name.  */
 
-static bfd_boolean
-parse_stab_members (void *dhandle, struct stab_handle *info,
-                   const char *tagname, const char **pp,
-                   const int *typenums, debug_method **retp)
+static bool
+parse_stab_members (void *                dhandle,
+                   struct stab_handle *  info,
+                   const char *          tagname,
+                   const char **         pp,
+                   const int *           typenums,
+                   debug_method **       retp,
+                   const char *          p_end)
 {
   const char *orig;
-  debug_method *methods;
+  debug_method *methods, *xmethods;
   unsigned int c;
   unsigned int alloc;
   char *name = NULL;
-  debug_method_variant *variants = NULL;
+  debug_method_variant *variants = NULL, *xvariants;
   char *argtypes = NULL;
 
   *retp = NULL;
 
   orig = *pp;
+  if (orig >= p_end)
+    return false;
 
   alloc = 0;
   methods = NULL;
@@ -2560,7 +2700,7 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
       /* FIXME: Some systems use something other than '$' here.  */
       if ((*pp)[0] != 'o' || (*pp)[1] != 'p' || (*pp)[2] != '$')
        {
-         name = savestring (*pp, p - *pp);
+         name = savestring (dhandle, *pp, p - *pp);
          *pp = p + 2;
        }
       else
@@ -2579,13 +2719,12 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
              bad_stab (orig);
              goto fail;
            }
-         name = savestring (*pp, p - *pp);
+         name = savestring (dhandle, *pp, p - *pp);
          *pp = p + 1;
        }
 
       allocvars = 10;
-      variants = ((debug_method_variant *)
-                 xmalloc (allocvars * sizeof *variants));
+      variants = xmalloc (allocvars * sizeof (*variants));
       cvars = 0;
 
       look_ahead_type = DEBUG_TYPE_NULL;
@@ -2593,13 +2732,13 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
       do
        {
          debug_type type;
-         bfd_boolean stub;
+         bool stub;
          enum debug_visibility visibility;
-         bfd_boolean constp, volatilep, staticp;
+         bool constp, volatilep, staticp;
          bfd_vma voffset;
          debug_type context;
          const char *physname;
-         bfd_boolean varargs;
+         bool varargs;
 
          if (look_ahead_type != DEBUG_TYPE_NULL)
            {
@@ -2610,7 +2749,7 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
          else
            {
              type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                     (debug_type **) NULL);
+                                     (debug_type **) NULL, p_end);
              if (type == DEBUG_TYPE_NULL)
                goto fail;
 
@@ -2629,12 +2768,12 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
              goto fail;
            }
 
-         stub = FALSE;
+         stub = false;
          if (debug_get_type_kind (dhandle, type) == DEBUG_KIND_METHOD
              && debug_get_parameter_types (dhandle, type, &varargs) == NULL)
-           stub = TRUE;
+           stub = true;
 
-         argtypes = savestring (*pp, p - *pp);
+         argtypes = savestring (dhandle, *pp, p - *pp);
          *pp = p + 1;
 
          switch (**pp)
@@ -2645,14 +2784,17 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
            case '1':
              visibility = DEBUG_VISIBILITY_PROTECTED;
              break;
+           case 0:
+             bad_stab (orig);
+             goto fail;
            default:
              visibility = DEBUG_VISIBILITY_PUBLIC;
              break;
            }
          ++*pp;
 
-         constp = FALSE;
-         volatilep = FALSE;
+         constp = false;
+         volatilep = false;
          switch (**pp)
            {
            case 'A':
@@ -2661,18 +2803,18 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
              break;
            case 'B':
              /* const member function.  */
-             constp = TRUE;
+             constp = true;
              ++*pp;
              break;
            case 'C':
              /* volatile member function.  */
-             volatilep = TRUE;
+             volatilep = true;
              ++*pp;
              break;
            case 'D':
              /* const volatile member function.  */
-             constp = TRUE;
-             volatilep = TRUE;
+             constp = true;
+             volatilep = true;
              ++*pp;
              break;
            case '*':
@@ -2685,15 +2827,15 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
              break;
            }
 
-         staticp = FALSE;
+         staticp = false;
          switch (**pp)
            {
            case '*':
              /* virtual member function, followed by index.  The sign
                 bit is supposedly set to distinguish
-                pointers-to-methods from virtual function indicies.  */
+                pointers-to-methods from virtual function indices.  */
              ++*pp;
-             voffset = parse_number (pp, (bfd_boolean *) NULL);
+             voffset = parse_number (pp, (bool *) NULL, p_end);
              if (**pp != ';')
                {
                  bad_stab (orig);
@@ -2702,7 +2844,7 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
              ++*pp;
              voffset &= 0x7fffffff;
 
-             if (**pp == ';' || *pp == '\0')
+             if (**pp == ';' || **pp == '\0')
                {
                  /* Must be g++ version 1.  */
                  context = DEBUG_TYPE_NULL;
@@ -2715,7 +2857,8 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
                  look_ahead_type = parse_stab_type (dhandle, info,
                                                     (const char *) NULL,
                                                     pp,
-                                                    (debug_type **) NULL);
+                                                    (debug_type **) NULL,
+                                                    p_end);
                  if (**pp == ':')
                    {
                      /* g++ version 1 overloaded methods.  */
@@ -2738,11 +2881,11 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
            case '?':
              /* static member function.  */
              ++*pp;
-             staticp = TRUE;
+             staticp = true;
              voffset = 0;
              context = DEBUG_TYPE_NULL;
              if (strncmp (argtypes, name, strlen (name)) != 0)
-               stub = TRUE;
+               stub = true;
              break;
 
            default:
@@ -2787,9 +2930,7 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
          if (cvars + 1 >= allocvars)
            {
              allocvars += 10;
-             variants = ((debug_method_variant *)
-                         xrealloc (variants,
-                                   allocvars * sizeof *variants));
+             variants = xrealloc (variants, allocvars * sizeof (*variants));
            }
 
          if (! staticp)
@@ -2812,6 +2953,9 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
       while (**pp != ';' && **pp != '\0');
 
       variants[cvars] = DEBUG_METHOD_VARIANT_NULL;
+      xvariants = debug_xalloc (dhandle, (cvars + 1) * sizeof (*variants));
+      memcpy (xvariants, variants, (cvars + 1) * sizeof (*variants));
+      free (variants);
 
       if (**pp != '\0')
        ++*pp;
@@ -2819,30 +2963,31 @@ parse_stab_members (void *dhandle, struct stab_handle *info,
       if (c + 1 >= alloc)
        {
          alloc += 10;
-         methods = ((debug_method *)
-                    xrealloc (methods, alloc * sizeof *methods));
+         methods = xrealloc (methods, alloc * sizeof (*methods));
        }
 
-      methods[c] = debug_make_method (dhandle, name, variants);
+      methods[c] = debug_make_method (dhandle, name, xvariants);
 
       ++c;
     }
 
+  xmethods = methods;
   if (methods != NULL)
-    methods[c] = DEBUG_METHOD_NULL;
+    {
+      methods[c] = DEBUG_METHOD_NULL;
+      xmethods = debug_xalloc (dhandle, (c + 1) * sizeof (*methods));
+      memcpy (xmethods, methods, (c + 1) * sizeof (*methods));
+      free (methods);
+    }
 
-  *retp = methods;
+  *retp = xmethods;
 
-  return TRUE;
+  return true;
 
  fail:
-  if (name != NULL)
-    free (name);
-  if (variants != NULL)
-    free (variants);
-  if (argtypes != NULL)
-    free (argtypes);
-  return FALSE;
+  free (variants);
+  free (methods);
+  return false;
 }
 
 /* Parse a string representing argument types for a method.  Stabs
@@ -2855,15 +3000,15 @@ static debug_type
 parse_stab_argtypes (void *dhandle, struct stab_handle *info,
                     debug_type class_type, const char *fieldname,
                     const char *tagname, debug_type return_type,
-                    const char *argtypes, bfd_boolean constp,
-                    bfd_boolean volatilep, const char **pphysname)
+                    const char *argtypes, bool constp,
+                    bool volatilep, const char **pphysname)
 {
-  bfd_boolean is_full_physname_constructor;
-  bfd_boolean is_constructor;
-  bfd_boolean is_destructor;
-  bfd_boolean is_v3;
+  bool is_full_physname_constructor;
+  bool is_constructor;
+  bool is_destructor;
+  bool is_v3;
   debug_type *args;
-  bfd_boolean varargs;
+  bool varargs;
   unsigned int physname_len = 0;
 
   /* Constructors are sometimes handled specially.  */
@@ -2872,7 +3017,7 @@ parse_stab_argtypes (void *dhandle, struct stab_handle *info,
                                   && (ISDIGIT (argtypes[2])
                                       || argtypes[2] == 'Q'
                                       || argtypes[2] == 't'))
-                                 || CONST_STRNEQ (argtypes, "__ct"));
+                                 || startswith (argtypes, "__ct"));
 
   is_constructor = (is_full_physname_constructor
                    || (tagname != NULL
@@ -2880,7 +3025,7 @@ parse_stab_argtypes (void *dhandle, struct stab_handle *info,
   is_destructor = ((argtypes[0] == '_'
                    && (argtypes[1] == '$' || argtypes[1] == '.')
                    && argtypes[2] == '_')
-                  || CONST_STRNEQ (argtypes, "__dt"));
+                  || startswith (argtypes, "__dt"));
   is_v3 = argtypes[0] == '_' && argtypes[1] == 'Z';
 
   if (!(is_destructor || is_full_physname_constructor || is_v3))
@@ -2918,27 +3063,15 @@ parse_stab_argtypes (void *dhandle, struct stab_handle *info,
          && fieldname[1] == 'p'
          && (fieldname[2] == '$' || fieldname[2] == '.'))
        {
-         const char *opname;
-
-         opname = cplus_mangle_opname (fieldname + 3, 0);
-         if (opname == NULL)
-           {
-             fprintf (stderr, _("No mangling for \"%s\"\n"), fieldname);
-             return DEBUG_TYPE_NULL;
-           }
-         mangled_name_len += strlen (opname);
-         physname = (char *) xmalloc (mangled_name_len);
-         strncpy (physname, fieldname, 3);
-         strcpy (physname + 3, opname);
+         /* Opname selection is no longer supported by libiberty's demangler.  */
+         return DEBUG_TYPE_NULL;
        }
+
+      physname = debug_xalloc (dhandle, mangled_name_len);
+      if (is_constructor)
+       physname[0] = '\0';
       else
-       {
-         physname = (char *) xmalloc (mangled_name_len);
-         if (is_constructor)
-           physname[0] = '\0';
-         else
-           strcpy (physname, fieldname);
-       }
+       strcpy (physname, fieldname);
 
       physname_len = strlen (physname);
       strcat (physname, buf);
@@ -2951,10 +3084,10 @@ parse_stab_argtypes (void *dhandle, struct stab_handle *info,
 
   if (*argtypes == '\0' || is_destructor)
     {
-      args = (debug_type *) xmalloc (sizeof *args);
+      args = debug_xalloc (dhandle, sizeof (*args));
       *args = NULL;
       return debug_make_method_type (dhandle, return_type, class_type, args,
-                                    FALSE);
+                                    false);
     }
 
   args = stab_demangle_argtypes (dhandle, info, *pphysname, &varargs, physname_len);
@@ -2973,27 +3106,32 @@ parse_stab_argtypes (void *dhandle, struct stab_handle *info,
    This function is called when we have parsed all the method declarations,
    so we can look for the vptr base class info.  */
 
-static bfd_boolean
-parse_stab_tilde_field (void *dhandle, struct stab_handle *info,
-                       const char **pp, const int *typenums,
-                       debug_type *retvptrbase, bfd_boolean *retownvptr)
+static bool
+parse_stab_tilde_field (void *dhandle,
+                       struct stab_handle *info,
+                       const char **pp,
+                       const int *typenums,
+                       debug_type *retvptrbase,
+                       bool *retownvptr,
+                       const char *p_end)
 {
   const char *orig;
   const char *hold;
   int vtypenums[2];
 
   *retvptrbase = DEBUG_TYPE_NULL;
-  *retownvptr = FALSE;
+  *retownvptr = false;
 
   orig = *pp;
-
+  if (orig >= p_end)
+    return false;
+  
   /* If we are positioned at a ';', then skip it.  */
   if (**pp == ';')
     ++*pp;
 
   if (**pp != '~')
-    return TRUE;
-
+    return true;
   ++*pp;
 
   if (**pp == '=' || **pp == '+' || **pp == '-')
@@ -3004,20 +3142,19 @@ parse_stab_tilde_field (void *dhandle, struct stab_handle *info,
     }
 
   if (**pp != '%')
-    return TRUE;
-
+    return true;
   ++*pp;
 
   hold = *pp;
 
   /* The next number is the type number of the base class (possibly
      our own class) which supplies the vtable for this class.  */
-  if (! parse_stab_type_number (pp, vtypenums))
-    return FALSE;
+  if (! parse_stab_type_number (pp, vtypenums, p_end))
+    return false;
 
   if (vtypenums[0] == typenums[0]
       && vtypenums[1] == typenums[1])
-    *retownvptr = TRUE;
+    *retownvptr = true;
   else
     {
       debug_type vtype;
@@ -3026,13 +3163,13 @@ parse_stab_tilde_field (void *dhandle, struct stab_handle *info,
       *pp = hold;
 
       vtype = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                              (debug_type **) NULL);
+                              (debug_type **) NULL, p_end);
       for (p = *pp; *p != ';' && *p != '\0'; p++)
        ;
       if (*p != ';')
        {
          bad_stab (orig);
-         return FALSE;
+         return false;
        }
 
       *retvptrbase = vtype;
@@ -3040,20 +3177,23 @@ parse_stab_tilde_field (void *dhandle, struct stab_handle *info,
       *pp = p + 1;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Read a definition of an array type.  */
 
 static debug_type
-parse_stab_array_type (void *dhandle, struct stab_handle *info,
-                      const char **pp, bfd_boolean stringp)
+parse_stab_array_type (void *dhandle,
+                      struct stab_handle *info,
+                      const char **pp,
+                      bool stringp,
+                      const char *p_end)
 {
   const char *orig;
   const char *p;
   int typenums[2];
   debug_type index_type;
-  bfd_boolean adjustable;
+  bool adjustable;
   bfd_signed_vma lower, upper;
   debug_type element_type;
 
@@ -3065,19 +3205,22 @@ parse_stab_array_type (void *dhandle, struct stab_handle *info,
      for these, produce a type like float[][].  */
 
   orig = *pp;
+  if (orig >= p_end)
+    return DEBUG_TYPE_NULL;
 
   /* FIXME: gdb checks os9k_stabs here.  */
 
   /* If the index type is type 0, we take it as int.  */
   p = *pp;
-  if (! parse_stab_type_number (&p, typenums))
+  if (! parse_stab_type_number (&p, typenums, p_end))
     return DEBUG_TYPE_NULL;
+
   if (typenums[0] == 0 && typenums[1] == 0 && **pp != '=')
     {
       index_type = debug_find_named_type (dhandle, "int");
       if (index_type == DEBUG_TYPE_NULL)
        {
-         index_type = debug_make_int_type (dhandle, 4, FALSE);
+         index_type = debug_make_int_type (dhandle, 4, false);
          if (index_type == DEBUG_TYPE_NULL)
            return DEBUG_TYPE_NULL;
        }
@@ -3086,7 +3229,7 @@ parse_stab_array_type (void *dhandle, struct stab_handle *info,
   else
     {
       index_type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                   (debug_type **) NULL);
+                                   (debug_type **) NULL, p_end);
     }
 
   if (**pp != ';')
@@ -3096,15 +3239,15 @@ parse_stab_array_type (void *dhandle, struct stab_handle *info,
     }
   ++*pp;
 
-  adjustable = FALSE;
+  adjustable = false;
 
-  if (! ISDIGIT (**pp) && **pp != '-')
+  if (! ISDIGIT (**pp) && **pp != '-' && **pp != 0)
     {
       ++*pp;
-      adjustable = TRUE;
+      adjustable = true;
     }
 
-  lower = (bfd_signed_vma) parse_number (pp, (bfd_boolean *) NULL);
+  lower = (bfd_signed_vma) parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -3112,13 +3255,13 @@ parse_stab_array_type (void *dhandle, struct stab_handle *info,
     }
   ++*pp;
 
-  if (! ISDIGIT (**pp) && **pp != '-')
+  if (! ISDIGIT (**pp) && **pp != '-' && **pp != 0)
     {
       ++*pp;
-      adjustable = TRUE;
+      adjustable = true;
     }
 
-  upper = (bfd_signed_vma) parse_number (pp, (bfd_boolean *) NULL);
+  upper = (bfd_signed_vma) parse_number (pp, (bool *) NULL, p_end);
   if (**pp != ';')
     {
       bad_stab (orig);
@@ -3127,7 +3270,7 @@ parse_stab_array_type (void *dhandle, struct stab_handle *info,
   ++*pp;
 
   element_type = parse_stab_type (dhandle, info, (const char *) NULL, pp,
-                                 (debug_type **) NULL);
+                                 (debug_type **) NULL, p_end);
   if (element_type == DEBUG_TYPE_NULL)
     return DEBUG_TYPE_NULL;
 
@@ -3163,11 +3306,12 @@ struct bincl_file
 /* Start a new N_BINCL file, pushing it onto the stack.  */
 
 static void
-push_bincl (struct stab_handle *info, const char *name, bfd_vma hash)
+push_bincl (void *dhandle, struct stab_handle *info, const char *name,
+           bfd_vma hash)
 {
   struct bincl_file *n;
 
-  n = (struct bincl_file *) xmalloc (sizeof *n);
+  n = debug_xalloc (dhandle, sizeof *n);
   n->next = info->bincl_list;
   n->next_stack = info->bincl_stack;
   n->name = name;
@@ -3178,10 +3322,8 @@ push_bincl (struct stab_handle *info, const char *name, bfd_vma hash)
   info->bincl_stack = n;
 
   ++info->files;
-  info->file_types = ((struct stab_types **)
-                     xrealloc (info->file_types,
-                               (info->files
-                                * sizeof *info->file_types)));
+  info->file_types = xrealloc (info->file_types,
+                              info->files * sizeof (*info->file_types));
   info->file_types[n->file] = NULL;
 }
 
@@ -3198,6 +3340,9 @@ pop_bincl (struct stab_handle *info)
     return info->main_filename;
   info->bincl_stack = o->next_stack;
 
+  if (o->file >= info->files)
+    return info->main_filename;
+
   o->file_types = info->file_types[o->file];
 
   if (info->bincl_stack == NULL)
@@ -3207,16 +3352,14 @@ pop_bincl (struct stab_handle *info)
 
 /* Handle an N_EXCL: get the types from the corresponding N_BINCL.  */
 
-static bfd_boolean
+static bool
 find_excl (struct stab_handle *info, const char *name, bfd_vma hash)
 {
   struct bincl_file *l;
 
   ++info->files;
-  info->file_types = ((struct stab_types **)
-                     xrealloc (info->file_types,
-                               (info->files
-                                * sizeof *info->file_types)));
+  info->file_types = xrealloc (info->file_types,
+                              info->files * sizeof (*info->file_types));
 
   for (l = info->bincl_list; l != NULL; l = l->next)
     if (l->hash == hash && strcmp (l->name, name) == 0)
@@ -3225,12 +3368,12 @@ find_excl (struct stab_handle *info, const char *name, bfd_vma hash)
     {
       warn_stab (name, _("Undefined N_EXCL"));
       info->file_types[info->files - 1] = NULL;
-      return TRUE;
+      return true;
     }
 
   info->file_types[info->files - 1] = l->file_types;
 
-  return TRUE;
+  return true;
 }
 
 /* Handle a variable definition.  gcc emits variable definitions for a
@@ -3238,7 +3381,7 @@ find_excl (struct stab_handle *info, const char *name, bfd_vma hash)
    it.  The SunPRO compiler emits variable definitions after the
    N_LBRAC, so we can call debug_record_variable immediately.  */
 
-static bfd_boolean
+static bool
 stab_record_variable (void *dhandle, struct stab_handle *info,
                      const char *name, debug_type type,
                      enum debug_var_kind kind, bfd_vma val)
@@ -3250,8 +3393,7 @@ stab_record_variable (void *dhandle, struct stab_handle *info,
       || (info->gcc_compiled == 0 && info->n_opt_found))
     return debug_record_variable (dhandle, name, type, kind, val);
 
-  v = (struct stab_pending_var *) xmalloc (sizeof *v);
-  memset (v, 0, sizeof *v);
+  v = debug_xzalloc (dhandle, sizeof (*v));
 
   v->next = info->pending;
   v->name = name;
@@ -3260,13 +3402,13 @@ stab_record_variable (void *dhandle, struct stab_handle *info,
   v->val = val;
   info->pending = v;
 
-  return TRUE;
+  return true;
 }
 
 /* Emit pending variable definitions.  This is called after we see the
    N_LBRAC that starts the block.  */
 
-static bfd_boolean
+static bool
 stab_emit_pending_vars (void *dhandle, struct stab_handle *info)
 {
   struct stab_pending_var *v;
@@ -3274,60 +3416,48 @@ stab_emit_pending_vars (void *dhandle, struct stab_handle *info)
   v = info->pending;
   while (v != NULL)
     {
-      struct stab_pending_var *next;
-
       if (! debug_record_variable (dhandle, v->name, v->type, v->kind, v->val))
-       return FALSE;
+       return false;
 
-      next = v->next;
-      free (v);
-      v = next;
+      v = v->next;
     }
 
   info->pending = NULL;
 
-  return TRUE;
+  return true;
 }
 
 /* Find the slot for a type in the database.  */
 
 static debug_type *
-stab_find_slot (struct stab_handle *info, const int *typenums)
+stab_find_slot (void *dhandle, struct stab_handle *info, const int *typenums)
 {
-  int filenum;
-  int tindex;
+  unsigned int filenum;
+  unsigned int tindex;
+  unsigned int base_index;
   struct stab_types **ps;
 
   filenum = typenums[0];
   tindex = typenums[1];
 
-  if (filenum < 0 || (unsigned int) filenum >= info->files)
+  if (filenum >= info->files)
     {
       fprintf (stderr, _("Type file number %d out of range\n"), filenum);
       return NULL;
     }
-  if (tindex < 0)
-    {
-      fprintf (stderr, _("Type index number %d out of range\n"), tindex);
-      return NULL;
-    }
 
   ps = info->file_types + filenum;
+  base_index = tindex / STAB_TYPES_SLOTS * STAB_TYPES_SLOTS;
+  tindex -= base_index;
+  while (*ps && (*ps)->base_index < base_index)
+    ps = &(*ps)->next;
 
-  while (tindex >= STAB_TYPES_SLOTS)
-    {
-      if (*ps == NULL)
-       {
-         *ps = (struct stab_types *) xmalloc (sizeof **ps);
-         memset (*ps, 0, sizeof **ps);
-       }
-      ps = &(*ps)->next;
-      tindex -= STAB_TYPES_SLOTS;
-    }
-  if (*ps == NULL)
+  if (*ps == NULL || (*ps)->base_index != base_index)
     {
-      *ps = (struct stab_types *) xmalloc (sizeof **ps);
-      memset (*ps, 0, sizeof **ps);
+      struct stab_types *n = debug_xzalloc (dhandle, sizeof (*n));
+      n->next = *ps;
+      n->base_index = base_index;
+      *ps = n;
     }
 
   return (*ps)->types + tindex;
@@ -3347,7 +3477,7 @@ stab_find_type (void *dhandle, struct stab_handle *info, const int *typenums)
       return stab_xcoff_builtin_type (dhandle, info, typenums[1]);
     }
 
-  slot = stab_find_slot (info, typenums);
+  slot = stab_find_slot (dhandle, info, typenums);
   if (slot == NULL)
     return DEBUG_TYPE_NULL;
 
@@ -3359,197 +3489,197 @@ stab_find_type (void *dhandle, struct stab_handle *info, const int *typenums)
 
 /* Record that a given type number refers to a given type.  */
 
-static bfd_boolean
-stab_record_type (void *dhandle ATTRIBUTE_UNUSED, struct stab_handle *info,
+static bool
+stab_record_type (void *dhandle, struct stab_handle *info,
                  const int *typenums, debug_type type)
 {
   debug_type *slot;
 
-  slot = stab_find_slot (info, typenums);
+  slot = stab_find_slot (dhandle, info, typenums);
   if (slot == NULL)
-    return FALSE;
+    return false;
 
   /* gdb appears to ignore type redefinitions, so we do as well.  */
 
   *slot = type;
 
-  return TRUE;
+  return true;
 }
 
 /* Return an XCOFF builtin type.  */
 
 static debug_type
 stab_xcoff_builtin_type (void *dhandle, struct stab_handle *info,
-                        int typenum)
+                        unsigned int typenum)
 {
   debug_type rettype;
   const char *name;
 
-  if (typenum >= 0 || typenum < -XCOFF_TYPE_COUNT)
+  typenum = -typenum - 1;
+  if (typenum >= XCOFF_TYPE_COUNT)
     {
-      fprintf (stderr, _("Unrecognized XCOFF type %d\n"), typenum);
+      fprintf (stderr, _("Unrecognized XCOFF type %d\n"), -typenum - 1);
       return DEBUG_TYPE_NULL;
     }
-  if (info->xcoff_types[-typenum] != NULL)
-    return info->xcoff_types[-typenum];
+  if (info->xcoff_types[typenum] != NULL)
+    return info->xcoff_types[typenum];
 
-  switch (-typenum)
+  switch (typenum)
     {
-    case 1:
+    case 0:
       /* The size of this and all the other types are fixed, defined
         by the debugging format.  */
       name = "int";
-      rettype = debug_make_int_type (dhandle, 4, FALSE);
+      rettype = debug_make_int_type (dhandle, 4, false);
       break;
-    case 2:
+    case 1:
       name = "char";
-      rettype = debug_make_int_type (dhandle, 1, FALSE);
+      rettype = debug_make_int_type (dhandle, 1, false);
       break;
-    case 3:
+    case 2:
       name = "short";
-      rettype = debug_make_int_type (dhandle, 2, FALSE);
+      rettype = debug_make_int_type (dhandle, 2, false);
       break;
-    case 4:
+    case 3:
       name = "long";
-      rettype = debug_make_int_type (dhandle, 4, FALSE);
+      rettype = debug_make_int_type (dhandle, 4, false);
       break;
-    case 5:
+    case 4:
       name = "unsigned char";
-      rettype = debug_make_int_type (dhandle, 1, TRUE);
+      rettype = debug_make_int_type (dhandle, 1, true);
       break;
-    case 6:
+    case 5:
       name = "signed char";
-      rettype = debug_make_int_type (dhandle, 1, FALSE);
+      rettype = debug_make_int_type (dhandle, 1, false);
       break;
-    case 7:
+    case 6:
       name = "unsigned short";
-      rettype = debug_make_int_type (dhandle, 2, TRUE);
+      rettype = debug_make_int_type (dhandle, 2, true);
       break;
-    case 8:
+    case 7:
       name = "unsigned int";
-      rettype = debug_make_int_type (dhandle, 4, TRUE);
+      rettype = debug_make_int_type (dhandle, 4, true);
       break;
-    case 9:
+    case 8:
       name = "unsigned";
-      rettype = debug_make_int_type (dhandle, 4, TRUE);
-    case 10:
+      rettype = debug_make_int_type (dhandle, 4, true);
+      break;
+    case 9:
       name = "unsigned long";
-      rettype = debug_make_int_type (dhandle, 4, TRUE);
+      rettype = debug_make_int_type (dhandle, 4, true);
       break;
-    case 11:
+    case 10:
       name = "void";
       rettype = debug_make_void_type (dhandle);
       break;
-    case 12:
+    case 11:
       /* IEEE single precision (32 bit).  */
       name = "float";
       rettype = debug_make_float_type (dhandle, 4);
       break;
-    case 13:
+    case 12:
       /* IEEE double precision (64 bit).  */
       name = "double";
       rettype = debug_make_float_type (dhandle, 8);
       break;
-    case 14:
+    case 13:
       /* This is an IEEE double on the RS/6000, and different machines
         with different sizes for "long double" should use different
         negative type numbers.  See stabs.texinfo.  */
       name = "long double";
       rettype = debug_make_float_type (dhandle, 8);
       break;
-    case 15:
+    case 14:
       name = "integer";
-      rettype = debug_make_int_type (dhandle, 4, FALSE);
+      rettype = debug_make_int_type (dhandle, 4, false);
       break;
-    case 16:
+    case 15:
       name = "boolean";
       rettype = debug_make_bool_type (dhandle, 4);
       break;
-    case 17:
+    case 16:
       name = "short real";
       rettype = debug_make_float_type (dhandle, 4);
       break;
-    case 18:
+    case 17:
       name = "real";
       rettype = debug_make_float_type (dhandle, 8);
       break;
-    case 19:
+    case 18:
       /* FIXME */
       name = "stringptr";
       rettype = NULL;
       break;
-    case 20:
+    case 19:
       /* FIXME */
       name = "character";
-      rettype = debug_make_int_type (dhandle, 1, TRUE);
+      rettype = debug_make_int_type (dhandle, 1, true);
       break;
-    case 21:
+    case 20:
       name = "logical*1";
       rettype = debug_make_bool_type (dhandle, 1);
       break;
-    case 22:
+    case 21:
       name = "logical*2";
       rettype = debug_make_bool_type (dhandle, 2);
       break;
-    case 23:
+    case 22:
       name = "logical*4";
       rettype = debug_make_bool_type (dhandle, 4);
       break;
-    case 24:
+    case 23:
       name = "logical";
       rettype = debug_make_bool_type (dhandle, 4);
       break;
-    case 25:
+    case 24:
       /* Complex type consisting of two IEEE single precision values.  */
       name = "complex";
       rettype = debug_make_complex_type (dhandle, 8);
       break;
-    case 26:
+    case 25:
       /* Complex type consisting of two IEEE double precision values.  */
       name = "double complex";
       rettype = debug_make_complex_type (dhandle, 16);
       break;
-    case 27:
+    case 26:
       name = "integer*1";
-      rettype = debug_make_int_type (dhandle, 1, FALSE);
+      rettype = debug_make_int_type (dhandle, 1, false);
       break;
-    case 28:
+    case 27:
       name = "integer*2";
-      rettype = debug_make_int_type (dhandle, 2, FALSE);
+      rettype = debug_make_int_type (dhandle, 2, false);
       break;
-    case 29:
+    case 28:
       name = "integer*4";
-      rettype = debug_make_int_type (dhandle, 4, FALSE);
+      rettype = debug_make_int_type (dhandle, 4, false);
       break;
-    case 30:
+    case 29:
       /* FIXME */
       name = "wchar";
-      rettype = debug_make_int_type (dhandle, 2, FALSE);
+      rettype = debug_make_int_type (dhandle, 2, false);
       break;
-    case 31:
+    case 30:
       name = "long long";
-      rettype = debug_make_int_type (dhandle, 8, FALSE);
+      rettype = debug_make_int_type (dhandle, 8, false);
       break;
-    case 32:
+    case 31:
       name = "unsigned long long";
-      rettype = debug_make_int_type (dhandle, 8, TRUE);
+      rettype = debug_make_int_type (dhandle, 8, true);
       break;
-    case 33:
+    case 32:
       name = "logical*8";
       rettype = debug_make_bool_type (dhandle, 8);
       break;
-    case 34:
+    case 33:
       name = "integer*8";
-      rettype = debug_make_int_type (dhandle, 8, FALSE);
+      rettype = debug_make_int_type (dhandle, 8, false);
       break;
     default:
       abort ();
     }
 
   rettype = debug_name_type (dhandle, name, rettype);
-
-  info->xcoff_types[-typenum] = rettype;
-
+  info->xcoff_types[typenum] = rettype;
   return rettype;
 }
 
@@ -3563,17 +3693,14 @@ stab_find_tagged_type (void *dhandle, struct stab_handle *info,
   debug_type dtype;
   struct stab_tag *st;
 
-  name = savestring (p, len);
+  name = savestring (dhandle, p, len);
 
   /* We pass DEBUG_KIND_ILLEGAL because we want all tags in the same
      namespace.  This is right for C, and I don't know how to handle
      other languages.  FIXME.  */
   dtype = debug_find_tagged_type (dhandle, name, DEBUG_KIND_ILLEGAL);
   if (dtype != DEBUG_TYPE_NULL)
-    {
-      free (name);
-      return dtype;
-    }
+    return dtype;
 
   /* We need to allocate an entry on the undefined tag list.  */
   for (st = info->tags; st != NULL; st = st->next)
@@ -3583,14 +3710,12 @@ stab_find_tagged_type (void *dhandle, struct stab_handle *info,
        {
          if (st->kind == DEBUG_KIND_ILLEGAL)
            st->kind = kind;
-         free (name);
          break;
        }
     }
   if (st == NULL)
     {
-      st = (struct stab_tag *) xmalloc (sizeof *st);
-      memset (st, 0, sizeof *st);
+      st = debug_xzalloc (dhandle, sizeof (*st));
 
       st->next = info->tags;
       st->name = name;
@@ -3638,7 +3763,7 @@ struct stab_demangle_info
   /* The array of arguments we are building.  */
   debug_type *args;
   /* Whether the method takes a variable number of arguments.  */
-  bfd_boolean varargs;
+  bool varargs;
   /* The array of types we have remembered.  */
   struct stab_demangle_typestring *typestrings;
   /* The number of typestrings.  */
@@ -3649,29 +3774,29 @@ struct stab_demangle_info
 
 static void stab_bad_demangle (const char *);
 static unsigned int stab_demangle_count (const char **);
-static bfd_boolean stab_demangle_get_count (const char **, unsigned int *);
-static bfd_boolean stab_demangle_prefix
+static bool stab_demangle_get_count (const char **, unsigned int *);
+static bool stab_demangle_prefix
   (struct stab_demangle_info *, const char **, unsigned int);
-static bfd_boolean stab_demangle_function_name
+static bool stab_demangle_function_name
   (struct stab_demangle_info *, const char **, const char *);
-static bfd_boolean stab_demangle_signature
+static bool stab_demangle_signature
   (struct stab_demangle_info *, const char **);
-static bfd_boolean stab_demangle_qualified
+static bool stab_demangle_qualified
   (struct stab_demangle_info *, const char **, debug_type *);
-static bfd_boolean stab_demangle_template
+static bool stab_demangle_template
   (struct stab_demangle_info *, const char **, char **);
-static bfd_boolean stab_demangle_class
+static bool stab_demangle_class
   (struct stab_demangle_info *, const char **, const char **);
-static bfd_boolean stab_demangle_args
-  (struct stab_demangle_info *, const char **, debug_type **, bfd_boolean *);
-static bfd_boolean stab_demangle_arg
+static bool stab_demangle_args
+  (struct stab_demangle_info *, const char **, debug_type **, bool *);
+static bool stab_demangle_arg
   (struct stab_demangle_info *, const char **, debug_type **,
    unsigned int *, unsigned int *);
-static bfd_boolean stab_demangle_type
+static bool stab_demangle_type
   (struct stab_demangle_info *, const char **, debug_type *);
-static bfd_boolean stab_demangle_fund_type
+static bool stab_demangle_fund_type
   (struct stab_demangle_info *, const char **, debug_type *);
-static bfd_boolean stab_demangle_remember_type
+static bool stab_demangle_remember_type
   (struct stab_demangle_info *, const char *, int);
 
 /* Warn about a bad demangling.  */
@@ -3702,11 +3827,11 @@ stab_demangle_count (const char **pp)
 /* Require a count in a string.  The count may be multiple digits, in
    which case it must end in an underscore.  */
 
-static bfd_boolean
+static bool
 stab_demangle_get_count (const char **pp, unsigned int *pi)
 {
   if (! ISDIGIT (**pp))
-    return FALSE;
+    return false;
 
   *pi = **pp - '0';
   ++*pp;
@@ -3731,7 +3856,7 @@ stab_demangle_get_count (const char **pp, unsigned int *pi)
        }
     }
 
-  return TRUE;
+  return true;
 }
 
 /* This function demangles a physical name, returning a NULL
@@ -3739,7 +3864,7 @@ stab_demangle_get_count (const char **pp, unsigned int *pi)
 
 static debug_type *
 stab_demangle_argtypes (void *dhandle, struct stab_handle *info,
-                       const char *physname, bfd_boolean *pvarargs,
+                       const char *physname, bool *pvarargs,
                        unsigned int physname_len)
 {
   struct stab_demangle_info minfo;
@@ -3751,11 +3876,10 @@ stab_demangle_argtypes (void *dhandle, struct stab_handle *info,
   minfo.dhandle = dhandle;
   minfo.info = info;
   minfo.args = NULL;
-  minfo.varargs = FALSE;
+  minfo.varargs = false;
   minfo.typestring_alloc = 10;
-  minfo.typestrings = ((struct stab_demangle_typestring *)
-                      xmalloc (minfo.typestring_alloc
-                               * sizeof *minfo.typestrings));
+  minfo.typestrings
+    = xmalloc (minfo.typestring_alloc * sizeof (*minfo.typestrings));
   minfo.typestring_count = 0;
 
   /* cplus_demangle checks for special GNU mangled forms, but we can't
@@ -3771,7 +3895,6 @@ stab_demangle_argtypes (void *dhandle, struct stab_handle *info,
     }
 
   free (minfo.typestrings);
-  minfo.typestrings = NULL;
 
   if (minfo.args == NULL)
     fprintf (stderr, _("no argument types in mangled string\n"));
@@ -3780,14 +3903,13 @@ stab_demangle_argtypes (void *dhandle, struct stab_handle *info,
   return minfo.args;
 
  error_return:
-  if (minfo.typestrings != NULL)
-    free (minfo.typestrings);
+  free (minfo.typestrings);
   return NULL;
 }
 
 /* Demangle the prefix of the mangled name.  */
 
-static bfd_boolean
+static bool
 stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
                      unsigned int physname_len)
 {
@@ -3810,7 +3932,7 @@ stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
       if (scan == NULL)
        {
          stab_bad_demangle (*pp);
-         return FALSE;
+         return false;
        }
 
       --scan;
@@ -3828,7 +3950,7 @@ stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
     {
       /* This is a GNU style constructor name.  */
       *pp = scan + 2;
-      return TRUE;
+      return true;
     }
   else if (scan == *pp
           && ! ISDIGIT (scan[2])
@@ -3842,7 +3964,7 @@ stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
       if (scan == NULL || scan[2] == '\0')
        {
          stab_bad_demangle (*pp);
-         return FALSE;
+         return false;
        }
 
       return stab_demangle_function_name (minfo, pp, scan);
@@ -3855,7 +3977,7 @@ stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
   else
     {
       stab_bad_demangle (*pp);
-      return FALSE;
+      return false;
     }
   /*NOTREACHED*/
 }
@@ -3864,7 +3986,7 @@ stab_demangle_prefix (struct stab_demangle_info *minfo, const char **pp,
    double underscore which separates the function name from the
    signature.  */
 
-static bfd_boolean
+static bool
 stab_demangle_function_name (struct stab_demangle_info *minfo,
                             const char **pp, const char *scan)
 {
@@ -3879,7 +4001,7 @@ stab_demangle_function_name (struct stab_demangle_info *minfo,
   *pp = scan + 2;
 
   if (*pp - name >= 5
-          && CONST_STRNEQ (name, "type")
+          && startswith (name, "type")
           && (name[4] == '$' || name[4] == '.'))
     {
       const char *tem;
@@ -3887,7 +4009,7 @@ stab_demangle_function_name (struct stab_demangle_info *minfo,
       /* This is a type conversion operator.  */
       tem = name + 5;
       if (! stab_demangle_type (minfo, &tem, (debug_type *) NULL))
-       return FALSE;
+       return false;
     }
   else if (name[0] == '_'
           && name[1] == '_'
@@ -3899,26 +4021,26 @@ stab_demangle_function_name (struct stab_demangle_info *minfo,
       /* This is a type conversion operator.  */
       tem = name + 4;
       if (! stab_demangle_type (minfo, &tem, (debug_type *) NULL))
-       return FALSE;
+       return false;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle the signature.  This is where the argument types are
    found.  */
 
-static bfd_boolean
+static bool
 stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
 {
   const char *orig;
-  bfd_boolean expect_func, func_done;
+  bool expect_func, func_done;
   const char *hold;
 
   orig = *pp;
 
-  expect_func = FALSE;
-  func_done = FALSE;
+  expect_func = false;
+  func_done = false;
   hold = NULL;
 
   while (**pp != '\0')
@@ -3929,8 +4051,8 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
          hold = *pp;
          if (! stab_demangle_qualified (minfo, pp, (debug_type *) NULL)
              || ! stab_demangle_remember_type (minfo, hold, *pp - hold))
-           return FALSE;
-         expect_func = TRUE;
+           return false;
+         expect_func = true;
          hold = NULL;
          break;
 
@@ -3954,8 +4076,8 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
            hold = *pp;
          if (! stab_demangle_class (minfo, pp, (const char **) NULL)
              || ! stab_demangle_remember_type (minfo, hold, *pp - hold))
-           return FALSE;
-         expect_func = TRUE;
+           return false;
+         expect_func = true;
          hold = NULL;
          break;
 
@@ -3963,10 +4085,10 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
          /* Function.  I don't know if this actually happens with g++
              output.  */
          hold = NULL;
-         func_done = TRUE;
+         func_done = true;
          ++*pp;
          if (! stab_demangle_args (minfo, pp, &minfo->args, &minfo->varargs))
-           return FALSE;
+           return false;
          break;
 
        case 't':
@@ -3975,9 +4097,9 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
            hold = *pp;
          if (! stab_demangle_template (minfo, pp, (char **) NULL)
              || ! stab_demangle_remember_type (minfo, hold, *pp - hold))
-           return FALSE;
+           return false;
          hold = NULL;
-         expect_func = TRUE;
+         expect_func = true;
          break;
 
        case '_':
@@ -3987,22 +4109,22 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
             has been mangled by some algorithm we don't know how to
             deal with.  So just reject the entire demangling.  */
          stab_bad_demangle (orig);
-         return FALSE;
+         return false;
 
        default:
          /* Assume we have stumbled onto the first outermost function
             argument token, and start processing args.  */
-         func_done = TRUE;
+         func_done = true;
          if (! stab_demangle_args (minfo, pp, &minfo->args, &minfo->varargs))
-           return FALSE;
+           return false;
          break;
        }
 
       if (expect_func)
        {
-         func_done = TRUE;
+         func_done = true;
          if (! stab_demangle_args (minfo, pp, &minfo->args, &minfo->varargs))
-           return FALSE;
+           return false;
        }
     }
 
@@ -4013,16 +4135,16 @@ stab_demangle_signature (struct stab_demangle_info *minfo, const char **pp)
         first case, and need to ensure that the '(void)' gets added
         to the current declp.  */
       if (! stab_demangle_args (minfo, pp, &minfo->args, &minfo->varargs))
-       return FALSE;
+       return false;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle a qualified name, such as "Q25Outer5Inner" which is the
    mangled form of "Outer::Inner".  */
 
-static bfd_boolean
+static bool
 stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
                         debug_type *ptype)
 {
@@ -4043,7 +4165,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
       if (! ISDIGIT (*p) || *p == '0')
        {
          stab_bad_demangle (orig);
-         return FALSE;
+         return false;
        }
       qualifiers = atoi (p);
       while (ISDIGIT (*p))
@@ -4051,7 +4173,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
       if (*p != '_')
        {
          stab_bad_demangle (orig);
-         return FALSE;
+         return false;
        }
       *pp = p + 1;
       break;
@@ -4068,7 +4190,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
     case '0':
     default:
       stab_bad_demangle (orig);
-      return FALSE;
+      return false;
     }
 
   context = DEBUG_TYPE_NULL;
@@ -4084,16 +4206,15 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
 
          if (! stab_demangle_template (minfo, pp,
                                        ptype != NULL ? &name : NULL))
-           return FALSE;
+           return false;
 
          if (ptype != NULL)
            {
              context = stab_find_tagged_type (minfo->dhandle, minfo->info,
                                               name, strlen (name),
                                               DEBUG_KIND_CLASS);
-             free (name);
              if (context == DEBUG_TYPE_NULL)
-               return FALSE;
+               return false;
            }
        }
       else
@@ -4104,7 +4225,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
          if (strlen (*pp) < len)
            {
              stab_bad_demangle (orig);
-             return FALSE;
+             return false;
            }
 
          if (ptype != NULL)
@@ -4129,7 +4250,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
                      not give us enough information to figure out the
                      latter case.  */
 
-                 name = savestring (*pp, len);
+                 name = savestring (minfo->dhandle, *pp, len);
 
                  for (; *fields != DEBUG_FIELD_NULL; fields++)
                    {
@@ -4138,10 +4259,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
 
                      ft = debug_get_field_type (minfo->dhandle, *fields);
                      if (ft == NULL)
-                       {
-                         free (name);
-                         return FALSE;
-                       }
+                       return false;
                      dn = debug_get_type_name (minfo->dhandle, ft);
                      if (dn != NULL && strcmp (dn, name) == 0)
                        {
@@ -4149,8 +4267,6 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
                          break;
                        }
                    }
-
-                 free (name);
                }
 
              if (context == DEBUG_TYPE_NULL)
@@ -4163,10 +4279,9 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
                    {
                      char *name;
 
-                     name = savestring (*pp, len);
+                     name = savestring (minfo->dhandle, *pp, len);
                      context = debug_find_named_type (minfo->dhandle,
                                                       name);
-                     free (name);
                    }
 
                  if (context == DEBUG_TYPE_NULL)
@@ -4178,7 +4293,7 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
                                                        ? DEBUG_KIND_ILLEGAL
                                                        : DEBUG_KIND_CLASS));
                      if (context == DEBUG_TYPE_NULL)
-                       return FALSE;
+                       return false;
                    }
                }
            }
@@ -4190,13 +4305,13 @@ stab_demangle_qualified (struct stab_demangle_info *minfo, const char **pp,
   if (ptype != NULL)
     *ptype = context;
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle a template.  If PNAME is not NULL, this sets *PNAME to a
    string representation of the template.  */
 
-static bfd_boolean
+static bool
 stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
                        char **pname)
 {
@@ -4212,7 +4327,7 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
   if (r == 0 || strlen (*pp) < r)
     {
       stab_bad_demangle (orig);
-      return FALSE;
+      return false;
     }
   *pp += r;
 
@@ -4220,7 +4335,7 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
   if (stab_demangle_get_count (pp, &r) == 0)
     {
       stab_bad_demangle (orig);
-      return FALSE;
+      return false;
     }
 
   for (i = 0; i < r; i++)
@@ -4230,26 +4345,26 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
          /* This is a type parameter.  */
          ++*pp;
          if (! stab_demangle_type (minfo, pp, (debug_type *) NULL))
-           return FALSE;
+           return false;
        }
       else
        {
          const char *old_p;
-         bfd_boolean pointerp, realp, integralp, charp, boolp;
-         bfd_boolean done;
+         bool pointerp, realp, integralp, charp, boolp;
+         bool done;
 
          old_p = *pp;
-         pointerp = FALSE;
-         realp = FALSE;
-         integralp = FALSE;
-         charp = FALSE;
-         boolp = FALSE;
-         done = FALSE;
+         pointerp = false;
+         realp = false;
+         integralp = false;
+         charp = false;
+         boolp = false;
+         done = false;
 
          /* This is a value parameter.  */
 
          if (! stab_demangle_type (minfo, pp, (debug_type *) NULL))
-           return FALSE;
+           return false;
 
          while (*old_p != '\0' && ! done)
            {
@@ -4258,8 +4373,8 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
                case 'P':
                case 'p':
                case 'R':
-                 pointerp = TRUE;
-                 done = TRUE;
+                 pointerp = true;
+                 done = true;
                  break;
                case 'C':       /* Const.  */
                case 'S':       /* Signed.  */
@@ -4271,8 +4386,8 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
                  ++old_p;
                  break;
                case 'Q':       /* Qualified name.  */
-                 integralp = TRUE;
-                 done = TRUE;
+                 integralp = true;
+                 done = true;
                  break;
                case 'T':       /* Remembered type.  */
                  abort ();
@@ -4283,27 +4398,27 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
                case 'i':       /* Int.  */
                case 's':       /* Short.  */
                case 'w':       /* Wchar_t.  */
-                 integralp = TRUE;
-                 done = TRUE;
+                 integralp = true;
+                 done = true;
                  break;
                case 'b':       /* Bool.  */
-                 boolp = TRUE;
-                 done = TRUE;
+                 boolp = true;
+                 done = true;
                  break;
                case 'c':       /* Char.  */
-                 charp = TRUE;
-                 done = TRUE;
+                 charp = true;
+                 done = true;
                  break;
                case 'r':       /* Long double.  */
                case 'd':       /* Double.  */
                case 'f':       /* Float.  */
-                 realp = TRUE;
-                 done = TRUE;
+                 realp = true;
+                 done = true;
                  break;
                default:
                  /* Assume it's a user defined integral type.  */
-                 integralp = TRUE;
-                 done = TRUE;
+                 integralp = true;
+                 done = true;
                  break;
                }
            }
@@ -4325,7 +4440,7 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
              if (val == 0)
                {
                  stab_bad_demangle (orig);
-                 return FALSE;
+                 return false;
                }
            }
          else if (boolp)
@@ -4336,7 +4451,7 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
              if (val != 0 && val != 1)
                {
                  stab_bad_demangle (orig);
-                 return FALSE;
+                 return false;
                }
            }
          else if (realp)
@@ -4366,7 +4481,7 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
              if (len == 0)
                {
                  stab_bad_demangle (orig);
-                 return FALSE;
+                 return false;
                }
              *pp += len;
            }
@@ -4380,13 +4495,11 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
       char *s1, *s2, *s3, *s4 = NULL;
       char *from, *to;
 
-      s1 = savestring (orig, *pp - orig);
+      s1 = savestring (minfo->dhandle, orig, *pp - orig);
 
       s2 = concat ("NoSuchStrinG__", s1, (const char *) NULL);
 
-      free (s1);
-
-      s3 = cplus_demangle (s2, DMGL_ANSI);
+      s3 = cplus_demangle (s2, demangle_flags);
 
       free (s2);
 
@@ -4395,9 +4508,8 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
       if (s3 == NULL || s4 == NULL)
        {
          stab_bad_demangle (orig);
-         if (s3 != NULL)
-           free (s3);
-         return FALSE;
+         free (s3);
+         return false;
        }
 
       /* Eliminating all spaces, except those between > characters,
@@ -4408,17 +4520,17 @@ stab_demangle_template (struct stab_demangle_info *minfo, const char **pp,
            || (from[1] == '>' && from > s3 && from[-1] == '>'))
          *to++ = *from;
 
-      *pname = savestring (s3, to - s3);
+      *pname = savestring (minfo->dhandle, s3, to - s3);
 
       free (s3);
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle a class name.  */
 
-static bfd_boolean
+static bool
 stab_demangle_class (struct stab_demangle_info *minfo ATTRIBUTE_UNUSED,
                     const char **pp, const char **pstart)
 {
@@ -4431,7 +4543,7 @@ stab_demangle_class (struct stab_demangle_info *minfo ATTRIBUTE_UNUSED,
   if (strlen (*pp) < n)
     {
       stab_bad_demangle (orig);
-      return FALSE;
+      return false;
     }
 
   if (pstart != NULL)
@@ -4439,15 +4551,15 @@ stab_demangle_class (struct stab_demangle_info *minfo ATTRIBUTE_UNUSED,
 
   *pp += n;
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle function arguments.  If the pargs argument is not NULL, it
    is set to a NULL terminated array holding the arguments.  */
 
-static bfd_boolean
+static bool
 stab_demangle_args (struct stab_demangle_info *minfo, const char **pp,
-                   debug_type **pargs, bfd_boolean *pvarargs)
+                   debug_type **pargs, bool *pvarargs)
 {
   const char *orig;
   unsigned int alloc, count;
@@ -4456,10 +4568,9 @@ stab_demangle_args (struct stab_demangle_info *minfo, const char **pp,
 
   alloc = 10;
   if (pargs != NULL)
-    {
-      *pargs = (debug_type *) xmalloc (alloc * sizeof **pargs);
-      *pvarargs = FALSE;
-    }
+    *pargs = xmalloc (alloc * sizeof (**pargs));
+  if (pvarargs != NULL)
+    *pvarargs = false;
   count = 0;
 
   while (**pp != '_' && **pp != '\0' && **pp != 'e')
@@ -4477,55 +4588,61 @@ stab_demangle_args (struct stab_demangle_info *minfo, const char **pp,
          else
            {
              if (! stab_demangle_get_count (pp, &r))
-               {
-                 stab_bad_demangle (orig);
-                 return FALSE;
-               }
+               goto bad;
            }
 
-         if (! stab_demangle_get_count (pp, &t))
-           {
-             stab_bad_demangle (orig);
-             return FALSE;
-           }
+         if (!stab_demangle_get_count (pp, &t)
+             || t >= minfo->typestring_count)
+           goto bad;
 
-         if (t >= minfo->typestring_count)
-           {
-             stab_bad_demangle (orig);
-             return FALSE;
-           }
          while (r-- > 0)
            {
              const char *tem;
 
              tem = minfo->typestrings[t].typestring;
              if (! stab_demangle_arg (minfo, &tem, pargs, &count, &alloc))
-               return FALSE;
+               goto fail;
            }
        }
       else
        {
          if (! stab_demangle_arg (minfo, pp, pargs, &count, &alloc))
-           return FALSE;
+           goto fail;
        }
     }
 
   if (pargs != NULL)
-    (*pargs)[count] = DEBUG_TYPE_NULL;
+    {
+      debug_type *xargs;
+      (*pargs)[count] = DEBUG_TYPE_NULL;
+       xargs = debug_xalloc (minfo->dhandle, (count + 1) * sizeof (*xargs));
+       memcpy (xargs, *pargs, (count + 1) * sizeof (*xargs));
+       free (*pargs);
+       *pargs = xargs;
+    }
 
   if (**pp == 'e')
     {
-      if (pargs != NULL)
-       *pvarargs = TRUE;
+      if (pvarargs != NULL)
+       *pvarargs = true;
       ++*pp;
     }
+  return true;
 
-  return TRUE;
+ bad:
+  stab_bad_demangle (orig);
+ fail:
+  if (pargs != NULL)
+    {
+      free (*pargs);
+      *pargs = NULL;
+    }
+  return false;
 }
 
 /* Demangle a single argument.  */
 
-static bfd_boolean
+static bool
 stab_demangle_arg (struct stab_demangle_info *minfo, const char **pp,
                   debug_type **pargs, unsigned int *pcount,
                   unsigned int *palloc)
@@ -4537,30 +4654,29 @@ stab_demangle_arg (struct stab_demangle_info *minfo, const char **pp,
   if (! stab_demangle_type (minfo, pp,
                            pargs == NULL ? (debug_type *) NULL : &type)
       || ! stab_demangle_remember_type (minfo, start, *pp - start))
-    return FALSE;
+    return false;
 
   if (pargs != NULL)
     {
       if (type == DEBUG_TYPE_NULL)
-       return FALSE;
+       return false;
 
       if (*pcount + 1 >= *palloc)
        {
          *palloc += 10;
-         *pargs = ((debug_type *)
-                   xrealloc (*pargs, *palloc * sizeof **pargs));
+         *pargs = xrealloc (*pargs, *palloc * sizeof (**pargs));
        }
       (*pargs)[*pcount] = type;
       ++*pcount;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle a type.  If the ptype argument is not NULL, *ptype is set
    to the newly allocated type.  */
 
-static bfd_boolean
+static bool
 stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
                    debug_type *ptype)
 {
@@ -4575,7 +4691,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
       /* A pointer type.  */
       ++*pp;
       if (! stab_demangle_type (minfo, pp, ptype))
-       return FALSE;
+       return false;
       if (ptype != NULL)
        *ptype = debug_make_pointer_type (minfo->dhandle, *ptype);
       break;
@@ -4584,7 +4700,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
       /* A reference type.  */
       ++*pp;
       if (! stab_demangle_type (minfo, pp, ptype))
-       return FALSE;
+       return false;
       if (ptype != NULL)
        *ptype = debug_make_reference_type (minfo->dhandle, *ptype);
       break;
@@ -4601,7 +4717,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
            if (! ISDIGIT (**pp))
              {
                stab_bad_demangle (orig);
-               return FALSE;
+               return false;
              }
            high *= 10;
            high += **pp - '0';
@@ -4610,21 +4726,21 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
        if (**pp != '_')
          {
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
        ++*pp;
 
        if (! stab_demangle_type (minfo, pp, ptype))
-         return FALSE;
+         return false;
        if (ptype != NULL)
          {
            debug_type int_type;
 
            int_type = debug_find_named_type (minfo->dhandle, "int");
            if (int_type == NULL)
-             int_type = debug_make_int_type (minfo->dhandle, 4, FALSE);
+             int_type = debug_make_int_type (minfo->dhandle, 4, false);
            *ptype = debug_make_array_type (minfo->dhandle, *ptype, int_type,
-                                           0, high, FALSE);
+                                           0, high, false);
          }
       }
       break;
@@ -4639,16 +4755,16 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
        if (! stab_demangle_get_count (pp, &i))
          {
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
        if (i >= minfo->typestring_count)
          {
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
        p = minfo->typestrings[i].typestring;
        if (! stab_demangle_type (minfo, &p, ptype))
-         return FALSE;
+         return false;
       }
       break;
 
@@ -4656,7 +4772,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
       /* A function.  */
       {
        debug_type *args;
-       bfd_boolean varargs;
+       bool varargs;
 
        ++*pp;
        if (! stab_demangle_args (minfo, pp,
@@ -4664,20 +4780,20 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
                                   ? (debug_type **) NULL
                                   : &args),
                                  (ptype == NULL
-                                  ? (bfd_boolean *) NULL
+                                  ? (bool *) NULL
                                   : &varargs)))
-         return FALSE;
+         return false;
        if (**pp != '_')
          {
            /* cplus_demangle will accept a function without a return
               type, but I don't know when that will happen, or what
               to do if it does.  */
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
        ++*pp;
        if (! stab_demangle_type (minfo, pp, ptype))
-         return FALSE;
+         return false;
        if (ptype != NULL)
          *ptype = debug_make_function_type (minfo->dhandle, *ptype, args,
                                             varargs);
@@ -4688,16 +4804,16 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
     case 'M':
     case 'O':
       {
-       bfd_boolean memberp;
+       bool memberp;
        debug_type class_type = DEBUG_TYPE_NULL;
        debug_type *args;
-       bfd_boolean varargs;
+       bool varargs;
        unsigned int n;
        const char *name;
 
        memberp = **pp == 'M';
        args = NULL;
-       varargs = FALSE;
+       varargs = false;
 
        ++*pp;
        if (ISDIGIT (**pp))
@@ -4706,7 +4822,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
            if (strlen (*pp) < n)
              {
                stab_bad_demangle (orig);
-               return FALSE;
+               return false;
              }
            name = *pp;
            *pp += n;
@@ -4718,7 +4834,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
                                                    name, (int) n,
                                                    DEBUG_KIND_CLASS);
                if (class_type == DEBUG_TYPE_NULL)
-                 return FALSE;
+                 return false;
              }
          }
        else if (**pp == 'Q')
@@ -4727,12 +4843,12 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
                                           (ptype == NULL
                                            ? (debug_type *) NULL
                                            : &class_type)))
-             return FALSE;
+             return false;
          }
        else
          {
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
 
        if (memberp)
@@ -4748,7 +4864,7 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
            if (**pp != 'F')
              {
                stab_bad_demangle (orig);
-               return FALSE;
+               return false;
              }
            ++*pp;
            if (! stab_demangle_args (minfo, pp,
@@ -4756,20 +4872,20 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
                                       ? (debug_type **) NULL
                                       : &args),
                                      (ptype == NULL
-                                      ? (bfd_boolean *) NULL
+                                      ? (bool *) NULL
                                       : &varargs)))
-             return FALSE;
+             return false;
          }
 
        if (**pp != '_')
          {
            stab_bad_demangle (orig);
-           return FALSE;
+           return false;
          }
        ++*pp;
 
        if (! stab_demangle_type (minfo, pp, ptype))
-         return FALSE;
+         return false;
 
        if (ptype != NULL)
          {
@@ -4790,13 +4906,13 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
     case 'G':
       ++*pp;
       if (! stab_demangle_type (minfo, pp, ptype))
-       return FALSE;
+       return false;
       break;
 
     case 'C':
       ++*pp;
       if (! stab_demangle_type (minfo, pp, ptype))
-       return FALSE;
+       return false;
       if (ptype != NULL)
        *ptype = debug_make_const_type (minfo->dhandle, *ptype);
       break;
@@ -4804,64 +4920,64 @@ stab_demangle_type (struct stab_demangle_info *minfo, const char **pp,
     case 'Q':
       {
        if (! stab_demangle_qualified (minfo, pp, ptype))
-         return FALSE;
+         return false;
       }
       break;
 
     default:
       if (! stab_demangle_fund_type (minfo, pp, ptype))
-       return FALSE;
+       return false;
       break;
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Demangle a fundamental type.  If the ptype argument is not NULL,
    *ptype is set to the newly allocated type.  */
 
-static bfd_boolean
+static bool
 stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
                         debug_type *ptype)
 {
   const char *orig;
-  bfd_boolean constp, volatilep, unsignedp, signedp;
-  bfd_boolean done;
+  bool constp, volatilep, unsignedp, signedp;
+  bool done;
 
   orig = *pp;
 
-  constp = FALSE;
-  volatilep = FALSE;
-  unsignedp = FALSE;
-  signedp = FALSE;
+  constp = false;
+  volatilep = false;
+  unsignedp = false;
+  signedp = false;
 
-  done = FALSE;
+  done = false;
   while (! done)
     {
       switch (**pp)
        {
        case 'C':
-         constp = TRUE;
+         constp = true;
          ++*pp;
          break;
 
        case 'U':
-         unsignedp = TRUE;
+         unsignedp = true;
          ++*pp;
          break;
 
        case 'S':
-         signedp = TRUE;
+         signedp = true;
          ++*pp;
          break;
 
        case 'V':
-         volatilep = TRUE;
+         volatilep = true;
          ++*pp;
          break;
 
        default:
-         done = TRUE;
+         done = true;
          break;
        }
     }
@@ -4966,7 +5082,7 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
        {
          *ptype = debug_find_named_type (minfo->dhandle, "__wchar_t");
          if (*ptype == DEBUG_TYPE_NULL)
-           *ptype = debug_make_int_type (minfo->dhandle, 2, TRUE);
+           *ptype = debug_make_int_type (minfo->dhandle, 2, true);
        }
       ++*pp;
       break;
@@ -5006,7 +5122,7 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
       if (! ISDIGIT (**pp))
        {
          stab_bad_demangle (orig);
-         return FALSE;
+         return false;
        }
       /* Fall through.  */
     case '0': case '1': case '2': case '3': case '4':
@@ -5015,14 +5131,13 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
        const char *hold;
 
        if (! stab_demangle_class (minfo, pp, &hold))
-         return FALSE;
+         return false;
        if (ptype != NULL)
          {
            char *name;
 
-           name = savestring (hold, *pp - hold);
+           name = savestring (minfo->dhandle, hold, *pp - hold);
            *ptype = debug_find_named_type (minfo->dhandle, name);
-           free (name);
            if (*ptype == DEBUG_TYPE_NULL)
              {
                /* FIXME: It is probably incorrect to assume that
@@ -5031,7 +5146,7 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
                                                hold, *pp - hold,
                                                DEBUG_KIND_ILLEGAL);
                if (*ptype == DEBUG_TYPE_NULL)
-                 return FALSE;
+                 return false;
              }
          }
       }
@@ -5043,22 +5158,21 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
 
        if (! stab_demangle_template (minfo, pp,
                                      ptype != NULL ? &name : NULL))
-         return FALSE;
+         return false;
        if (ptype != NULL)
          {
            *ptype = stab_find_tagged_type (minfo->dhandle, minfo->info,
                                            name, strlen (name),
                                            DEBUG_KIND_CLASS);
-           free (name);
            if (*ptype == DEBUG_TYPE_NULL)
-             return FALSE;
+             return false;
          }
       }
       break;
 
     default:
       stab_bad_demangle (orig);
-      return FALSE;
+      return false;
     }
 
   if (ptype != NULL)
@@ -5069,29 +5183,28 @@ stab_demangle_fund_type (struct stab_demangle_info *minfo, const char **pp,
        *ptype = debug_make_volatile_type (minfo->dhandle, *ptype);
     }
 
-  return TRUE;
+  return true;
 }
 
 /* Remember a type string in a demangled string.  */
 
-static bfd_boolean
+static bool
 stab_demangle_remember_type (struct stab_demangle_info *minfo,
                             const char *p, int len)
 {
   if (minfo->typestring_count >= minfo->typestring_alloc)
     {
       minfo->typestring_alloc += 10;
-      minfo->typestrings = ((struct stab_demangle_typestring *)
-                           xrealloc (minfo->typestrings,
-                                     (minfo->typestring_alloc
-                                      * sizeof *minfo->typestrings)));
+      minfo->typestrings
+       = xrealloc (minfo->typestrings,
+                   minfo->typestring_alloc * sizeof (*minfo->typestrings));
     }
 
   minfo->typestrings[minfo->typestring_count].typestring = p;
   minfo->typestrings[minfo->typestring_count].len = (unsigned int) len;
   ++minfo->typestring_count;
 
-  return TRUE;
+  return true;
 }
 \f
 /* Demangle names encoded using the g++ V3 ABI.  The newer versions of
@@ -5106,13 +5219,13 @@ stab_demangle_remember_type (struct stab_demangle_info *minfo,
 
 static debug_type *
 stab_demangle_v3_argtypes (void *dhandle, struct stab_handle *info,
-                          const char *physname, bfd_boolean *pvarargs)
+                          const char *physname, bool *pvarargs)
 {
   struct demangle_component *dc;
   void *mem;
   debug_type *pargs;
 
-  dc = cplus_demangle_v3_components (physname, DMGL_PARAMS | DMGL_ANSI, &mem);
+  dc = cplus_demangle_v3_components (physname, DMGL_PARAMS | demangle_flags, &mem);
   if (dc == NULL)
     {
       stab_bad_demangle (physname);
@@ -5145,15 +5258,15 @@ stab_demangle_v3_argtypes (void *dhandle, struct stab_handle *info,
 static debug_type *
 stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
                          struct demangle_component *arglist,
-                         bfd_boolean *pvarargs)
+                         bool *pvarargs)
 {
   struct demangle_component *dc;
   unsigned int alloc, count;
-  debug_type *pargs;
+  debug_type *pargs, *xargs;
 
   alloc = 10;
-  pargs = (debug_type *) xmalloc (alloc * sizeof *pargs);
-  *pvarargs = FALSE;
+  pargs = xmalloc (alloc * sizeof (*pargs));
+  *pvarargs = false;
 
   count = 0;
 
@@ -5162,7 +5275,7 @@ stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
        dc = dc->u.s_binary.right)
     {
       debug_type arg;
-      bfd_boolean varargs;
+      bool varargs;
 
       if (dc->type != DEMANGLE_COMPONENT_ARGLIST)
        {
@@ -5175,14 +5288,14 @@ stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
         context for a function with no arguments.  */
       if (dc->u.s_binary.left == NULL)
        break;
+
       arg = stab_demangle_v3_arg (dhandle, info, dc->u.s_binary.left,
                                  NULL, &varargs);
       if (arg == NULL)
        {
          if (varargs)
            {
-             *pvarargs = TRUE;
+             *pvarargs = true;
              continue;
            }
          free (pargs);
@@ -5192,7 +5305,7 @@ stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
       if (count + 1 >= alloc)
        {
          alloc += 10;
-         pargs = (debug_type *) xrealloc (pargs, alloc * sizeof *pargs);
+         pargs = xrealloc (pargs, alloc * sizeof (*pargs));
        }
 
       pargs[count] = arg;
@@ -5200,8 +5313,11 @@ stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
     }
 
   pargs[count] = DEBUG_TYPE_NULL;
+  xargs = debug_xalloc (dhandle, (count + 1) * sizeof (*pargs));
+  memcpy (xargs, pargs, (count + 1) * sizeof (*pargs));
+  free (pargs);
 
-  return pargs;
+  return xargs;
 }
 
 /* Convert a struct demangle_component tree describing an argument
@@ -5210,12 +5326,12 @@ stab_demangle_v3_arglist (void *dhandle, struct stab_handle *info,
 static debug_type
 stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
                      struct demangle_component *dc, debug_type context,
-                     bfd_boolean *pvarargs)
+                     bool *pvarargs)
 {
   debug_type dt;
 
   if (pvarargs != NULL)
-    *pvarargs = FALSE;
+    *pvarargs = false;
 
   switch (dc->type)
     {
@@ -5287,7 +5403,7 @@ stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
        /* We print this component to get a class name which we can
           use.  FIXME: This probably won't work if the template uses
           template parameters which refer to an outer template.  */
-       p = cplus_demangle_print (DMGL_PARAMS | DMGL_ANSI, dc, 20, &alc);
+       p = cplus_demangle_print (DMGL_PARAMS | demangle_flags, dc, 20, &alc);
        if (p == NULL)
          {
            fprintf (stderr, _("Failed to print demangled template\n"));
@@ -5333,7 +5449,7 @@ stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
     case DEMANGLE_COMPONENT_FUNCTION_TYPE:
       {
        debug_type *pargs;
-       bfd_boolean varargs;
+       bool varargs;
 
        if (dc->u.s_binary.left == NULL)
          {
@@ -5367,7 +5483,7 @@ stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
        /* We print this component in order to find out the type name.
           FIXME: Should we instead expose the
           demangle_builtin_type_info structure?  */
-       p = cplus_demangle_print (DMGL_PARAMS | DMGL_ANSI, dc, 20, &alc);
+       p = cplus_demangle_print (DMGL_PARAMS | demangle_flags, dc, 20, &alc);
        if (p == NULL)
          {
            fprintf (stderr, _("Couldn't get demangled builtin type\n"));
@@ -5377,11 +5493,11 @@ stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
        /* The mangling is based on the type, but does not itself
           indicate what the sizes are.  So we have to guess.  */
        if (strcmp (p, "signed char") == 0)
-         ret = debug_make_int_type (dhandle, 1, FALSE);
+         ret = debug_make_int_type (dhandle, 1, false);
        else if (strcmp (p, "bool") == 0)
          ret = debug_make_bool_type (dhandle, 1);
        else if (strcmp (p, "char") == 0)
-         ret = debug_make_int_type (dhandle, 1, FALSE);
+         ret = debug_make_int_type (dhandle, 1, false);
        else if (strcmp (p, "double") == 0)
          ret = debug_make_float_type (dhandle, 8);
        else if (strcmp (p, "long double") == 0)
@@ -5391,37 +5507,37 @@ stab_demangle_v3_arg (void *dhandle, struct stab_handle *info,
        else if (strcmp (p, "__float128") == 0)
          ret = debug_make_float_type (dhandle, 16);
        else if (strcmp (p, "unsigned char") == 0)
-         ret = debug_make_int_type (dhandle, 1, TRUE);
+         ret = debug_make_int_type (dhandle, 1, true);
        else if (strcmp (p, "int") == 0)
-         ret = debug_make_int_type (dhandle, 4, FALSE);
+         ret = debug_make_int_type (dhandle, 4, false);
        else if (strcmp (p, "unsigned int") == 0)
-         ret = debug_make_int_type (dhandle, 4, TRUE);
+         ret = debug_make_int_type (dhandle, 4, true);
        else if (strcmp (p, "long") == 0)
-         ret = debug_make_int_type (dhandle, 4, FALSE);
+         ret = debug_make_int_type (dhandle, 4, false);
        else if (strcmp (p, "unsigned long") == 0)
-         ret = debug_make_int_type (dhandle, 4, TRUE);
+         ret = debug_make_int_type (dhandle, 4, true);
        else if (strcmp (p, "__int128") == 0)
-         ret = debug_make_int_type (dhandle, 16, FALSE);
+         ret = debug_make_int_type (dhandle, 16, false);
        else if (strcmp (p, "unsigned __int128") == 0)
-         ret = debug_make_int_type (dhandle, 16, TRUE);
+         ret = debug_make_int_type (dhandle, 16, true);
        else if (strcmp (p, "short") == 0)
-         ret = debug_make_int_type (dhandle, 2, FALSE);
+         ret = debug_make_int_type (dhandle, 2, false);
        else if (strcmp (p, "unsigned short") == 0)
-         ret = debug_make_int_type (dhandle, 2, TRUE);
+         ret = debug_make_int_type (dhandle, 2, true);
        else if (strcmp (p, "void") == 0)
          ret = debug_make_void_type (dhandle);
        else if (strcmp (p, "wchar_t") == 0)
-         ret = debug_make_int_type (dhandle, 4, TRUE);
+         ret = debug_make_int_type (dhandle, 4, true);
        else if (strcmp (p, "long long") == 0)
-         ret = debug_make_int_type (dhandle, 8, FALSE);
+         ret = debug_make_int_type (dhandle, 8, false);
        else if (strcmp (p, "unsigned long long") == 0)
-         ret = debug_make_int_type (dhandle, 8, TRUE);
+         ret = debug_make_int_type (dhandle, 8, true);
        else if (strcmp (p, "...") == 0)
          {
            if (pvarargs == NULL)
              fprintf (stderr, _("Unexpected demangled varargs\n"));
            else
-             *pvarargs = TRUE;
+             *pvarargs = true;
            ret = NULL;
          }
        else