/* Demangler for the Rust programming language
   Copyright (C) 2016-2021 Free Software Foundation, Inc.
   Written by David Tolnay (dtolnay@gmail.com).
   Rewritten by Eduard-Mihai Burtescu (eddyb@lyken.rs) for v0 support.

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

In addition to the permissions in the GNU Library General Public
License, the Free Software Foundation gives you unlimited permission
to link the compiled version of this file into combinations with other
programs, and to distribute those combinations without any restriction
coming from the use of this file.  (The Library Public License
restrictions do apply in other respects; for example, they cover
modification of the file, and distribution when not linked into a
combined executable.)

Libiberty is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
Library General Public License for more details.

You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB.
If not, see <http://www.gnu.org/licenses/>.  */


#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include "safe-ctype.h"

#include <inttypes.h>
#include <sys/types.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>

#ifdef HAVE_STRING_H
#include <string.h>
#else
extern size_t strlen(const char *s);
extern int strncmp(const char *s1, const char *s2, size_t n);
extern void *memset(void *s, int c, size_t n);
#endif

#include <demangle.h>
#include "libiberty.h"

struct rust_demangler
{
  const char *sym;
  size_t sym_len;

  void *callback_opaque;
  demangle_callbackref callback;

  /* Position of the next character to read from the symbol. */
  size_t next;

  /* Non-zero if any error occurred. */
  int errored;

  /* Non-zero if nothing should be printed. */
  int skipping_printing;

  /* Non-zero if printing should be verbose (e.g. include hashes). */
  int verbose;

  /* Rust mangling version, with legacy mangling being -1. */
  int version;

  uint64_t bound_lifetime_depth;
};

/* Parsing functions. */

static char
peek (const struct rust_demangler *rdm)
{
  if (rdm->next < rdm->sym_len)
    return rdm->sym[rdm->next];
  return 0;
}

static int
eat (struct rust_demangler *rdm, char c)
{
  if (peek (rdm) == c)
    {
      rdm->next++;
      return 1;
    }
  else
    return 0;
}

static char
next (struct rust_demangler *rdm)
{
  char c = peek (rdm);
  if (!c)
    rdm->errored = 1;
  else
    rdm->next++;
  return c;
}

static uint64_t
parse_integer_62 (struct rust_demangler *rdm)
{
  char c;
  uint64_t x;

  if (eat (rdm, '_'))
    return 0;

  x = 0;
  while (!eat (rdm, '_'))
    {
      c = next (rdm);
      x *= 62;
      if (ISDIGIT (c))
        x += c - '0';
      else if (ISLOWER (c))
        x += 10 + (c - 'a');
      else if (ISUPPER (c))
        x += 10 + 26 + (c - 'A');
      else
        {
          rdm->errored = 1;
          return 0;
        }
    }
  return x + 1;
}

static uint64_t
parse_opt_integer_62 (struct rust_demangler *rdm, char tag)
{
  if (!eat (rdm, tag))
    return 0;
  return 1 + parse_integer_62 (rdm);
}

static uint64_t
parse_disambiguator (struct rust_demangler *rdm)
{
  return parse_opt_integer_62 (rdm, 's');
}

static size_t
parse_hex_nibbles (struct rust_demangler *rdm, uint64_t *value)
{
  char c;
  size_t hex_len;

  hex_len = 0;
  *value = 0;

  while (!eat (rdm, '_'))
    {
      *value <<= 4;

      c = next (rdm);
      if (ISDIGIT (c))
        *value |= c - '0';
      else if (c >= 'a' && c <= 'f')
        *value |= 10 + (c - 'a');
      else
        {
          rdm->errored = 1;
          return 0;
        }
      hex_len++;
    }

  return hex_len;
}

struct rust_mangled_ident
{
  /* ASCII part of the identifier. */
  const char *ascii;
  size_t ascii_len;

  /* Punycode insertion codes for Unicode codepoints, if any. */
  const char *punycode;
  size_t punycode_len;
};

static struct rust_mangled_ident
parse_ident (struct rust_demangler *rdm)
{
  char c;
  size_t start, len;
  int is_punycode = 0;
  struct rust_mangled_ident ident;

  ident.ascii = NULL;
  ident.ascii_len = 0;
  ident.punycode = NULL;
  ident.punycode_len = 0;

  if (rdm->version != -1)
    is_punycode = eat (rdm, 'u');

  c = next (rdm);
  if (!ISDIGIT (c))
    {
      rdm->errored = 1;
      return ident;
    }
  len = c - '0';

  if (c != '0')
    while (ISDIGIT (peek (rdm)))
      len = len * 10 + (next (rdm) - '0');

  /* Skip past the optional `_` separator (v0). */
  if (rdm->version != -1)
    eat (rdm, '_');

  start = rdm->next;
  rdm->next += len;
  /* Check for overflows. */
  if ((start > rdm->next) || (rdm->next > rdm->sym_len))
    {
      rdm->errored = 1;
      return ident;
    }

  ident.ascii = rdm->sym + start;
  ident.ascii_len = len;

  if (is_punycode)
    {
      ident.punycode_len = 0;
      while (ident.ascii_len > 0)
        {
          ident.ascii_len--;

          /* The last '_' is a separator between ascii & punycode. */
          if (ident.ascii[ident.ascii_len] == '_')
            break;

          ident.punycode_len++;
        }
      if (!ident.punycode_len)
        {
          rdm->errored = 1;
          return ident;
        }
      ident.punycode = ident.ascii + (len - ident.punycode_len);
    }

  if (ident.ascii_len == 0)
    ident.ascii = NULL;

  return ident;
}

/* Printing functions. */

static void
print_str (struct rust_demangler *rdm, const char *data, size_t len)
{
  if (!rdm->errored && !rdm->skipping_printing)
    rdm->callback (data, len, rdm->callback_opaque);
}

#define PRINT(s) print_str (rdm, s, strlen (s))

static void
print_uint64 (struct rust_demangler *rdm, uint64_t x)
{
  char s[21];
  snprintf (s, 21, "%" PRIu64, x);
  PRINT (s);
}

static void
print_uint64_hex (struct rust_demangler *rdm, uint64_t x)
{
  char s[17];
  snprintf (s, 17, "%" PRIx64, x);
  PRINT (s);
}

/* Return a 0x0-0xf value if the char is 0-9a-f, and -1 otherwise. */
static int
decode_lower_hex_nibble (char nibble)
{
  if ('0' <= nibble && nibble <= '9')
    return nibble - '0';
  if ('a' <= nibble && nibble <= 'f')
    return 0xa + (nibble - 'a');
  return -1;
}

/* Return the unescaped character for a "$...$" escape, or 0 if invalid. */
static char
decode_legacy_escape (const char *e, size_t len, size_t *out_len)
{
  char c = 0;
  size_t escape_len = 0;
  int lo_nibble = -1, hi_nibble = -1;

  if (len < 3 || e[0] != '$')
    return 0;

  e++;
  len--;

  if (e[0] == 'C')
    {
      escape_len = 1;

      c = ',';
    }
  else if (len > 2)
    {
      escape_len = 2;

      if (e[0] == 'S' && e[1] == 'P')
        c = '@';
      else if (e[0] == 'B' && e[1] == 'P')
        c = '*';
      else if (e[0] == 'R' && e[1] == 'F')
        c = '&';
      else if (e[0] == 'L' && e[1] == 'T')
        c = '<';
      else if (e[0] == 'G' && e[1] == 'T')
        c = '>';
      else if (e[0] == 'L' && e[1] == 'P')
        c = '(';
      else if (e[0] == 'R' && e[1] == 'P')
        c = ')';
      else if (e[0] == 'u' && len > 3)
        {
          escape_len = 3;

          hi_nibble = decode_lower_hex_nibble (e[1]);
          if (hi_nibble < 0)
            return 0;
          lo_nibble = decode_lower_hex_nibble (e[2]);
          if (lo_nibble < 0)
            return 0;

          /* Only allow non-control ASCII characters. */
          if (hi_nibble > 7)
            return 0;
          c = (hi_nibble << 4) | lo_nibble;
          if (c < 0x20)
            return 0;
        }
    }

  if (!c || len <= escape_len || e[escape_len] != '$')
    return 0;

  *out_len = 2 + escape_len;
  return c;
}

static void
print_ident (struct rust_demangler *rdm, struct rust_mangled_ident ident)
{
  char unescaped;
  uint8_t *out, *p, d;
  size_t len, cap, punycode_pos, j;
  /* Punycode parameters and state. */
  uint32_t c;
  size_t base, t_min, t_max, skew, damp, bias, i;
  size_t delta, w, k, t;

  if (rdm->errored || rdm->skipping_printing)
    return;

  if (rdm->version == -1)
    {
      /* Ignore leading underscores preceding escape sequences.
         The mangler inserts an underscore to make sure the
         identifier begins with a XID_Start character. */
      if (ident.ascii_len >= 2 && ident.ascii[0] == '_'
          && ident.ascii[1] == '$')
        {
          ident.ascii++;
          ident.ascii_len--;
        }

      while (ident.ascii_len > 0)
        {
          /* Handle legacy escape sequences ("$...$", ".." or "."). */
          if (ident.ascii[0] == '$')
            {
              unescaped
                  = decode_legacy_escape (ident.ascii, ident.ascii_len, &len);
              if (unescaped)
                print_str (rdm, &unescaped, 1);
              else
                {
                  /* Unexpected escape sequence, print the rest verbatim. */
                  print_str (rdm, ident.ascii, ident.ascii_len);
                  return;
                }
            }
          else if (ident.ascii[0] == '.')
            {
              if (ident.ascii_len >= 2 && ident.ascii[1] == '.')
                {
                  /* ".." becomes "::" */
                  PRINT ("::");
                  len = 2;
                }
              else
                {
                  PRINT (".");
                  len = 1;
                }
            }
          else
            {
              /* Print everything before the next escape sequence, at once. */
              for (len = 0; len < ident.ascii_len; len++)
                if (ident.ascii[len] == '$' || ident.ascii[len] == '.')
                  break;

              print_str (rdm, ident.ascii, len);
            }

          ident.ascii += len;
          ident.ascii_len -= len;
        }

      return;
    }

  if (!ident.punycode)
    {
      print_str (rdm, ident.ascii, ident.ascii_len);
      return;
    }

  len = 0;
  cap = 4;
  while (cap < ident.ascii_len)
    {
      cap *= 2;
      /* Check for overflows. */
      if ((cap * 4) / 4 != cap)
        {
          rdm->errored = 1;
          return;
        }
    }

  /* Store the output codepoints as groups of 4 UTF-8 bytes. */
  out = (uint8_t *)malloc (cap * 4);
  if (!out)
    {
      rdm->errored = 1;
      return;
    }

  /* Populate initial output from ASCII fragment. */
  for (len = 0; len < ident.ascii_len; len++)
    {
      p = out + 4 * len;
      p[0] = 0;
      p[1] = 0;
      p[2] = 0;
      p[3] = ident.ascii[len];
    }

  /* Punycode parameters and initial state. */
  base = 36;
  t_min = 1;
  t_max = 26;
  skew = 38;
  damp = 700;
  bias = 72;
  i = 0;
  c = 0x80;

  punycode_pos = 0;
  while (punycode_pos < ident.punycode_len)
    {
      /* Read one delta value. */
      delta = 0;
      w = 1;
      k = 0;
      do
        {
          k += base;
          t = k < bias ? 0 : (k - bias);
          if (t < t_min)
            t = t_min;
          if (t > t_max)
            t = t_max;

          if (punycode_pos >= ident.punycode_len)
            goto cleanup;
          d = ident.punycode[punycode_pos++];

          if (ISLOWER (d))
            d = d - 'a';
          else if (ISDIGIT (d))
            d = 26 + (d - '0');
          else
            {
              rdm->errored = 1;
              goto cleanup;
            }

          delta += d * w;
          w *= base - t;
        }
      while (d >= t);

      /* Compute the new insert position and character. */
      len++;
      i += delta;
      c += i / len;
      i %= len;

      /* Ensure enough space is available. */
      if (cap < len)
        {
          cap *= 2;
          /* Check for overflows. */
          if ((cap * 4) / 4 != cap || cap < len)
            {
              rdm->errored = 1;
              goto cleanup;
            }
        }
      p = (uint8_t *)realloc (out, cap * 4);
      if (!p)
        {
          rdm->errored = 1;
          goto cleanup;
        }
      out = p;

      /* Move the characters after the insert position. */
      p = out + i * 4;
      memmove (p + 4, p, (len - i - 1) * 4);

      /* Insert the new character, as UTF-8 bytes. */
      p[0] = c >= 0x10000 ? 0xf0 | (c >> 18) : 0;
      p[1] = c >= 0x800 ? (c < 0x10000 ? 0xe0 : 0x80) | ((c >> 12) & 0x3f) : 0;
      p[2] = (c < 0x800 ? 0xc0 : 0x80) | ((c >> 6) & 0x3f);
      p[3] = 0x80 | (c & 0x3f);

      /* If there are no more deltas, decoding is complete. */
      if (punycode_pos == ident.punycode_len)
        break;

      i++;

      /* Perform bias adaptation. */
      delta /= damp;
      damp = 2;

      delta += delta / len;
      k = 0;
      while (delta > ((base - t_min) * t_max) / 2)
        {
          delta /= base - t_min;
          k += base;
        }
      bias = k + ((base - t_min + 1) * delta) / (delta + skew);
    }

  /* Remove all the 0 bytes to leave behind an UTF-8 string. */
  for (i = 0, j = 0; i < len * 4; i++)
    if (out[i] != 0)
      out[j++] = out[i];

  print_str (rdm, (const char *)out, j);

cleanup:
  free (out);
}

/* Print the lifetime according to the previously decoded index.
   An index of `0` always refers to `'_`, but starting with `1`,
   indices refer to late-bound lifetimes introduced by a binder. */
static void
print_lifetime_from_index (struct rust_demangler *rdm, uint64_t lt)
{
  char c;
  uint64_t depth;

  PRINT ("'");
  if (lt == 0)
    {
      PRINT ("_");
      return;
    }

  depth = rdm->bound_lifetime_depth - lt;
  /* Try to print lifetimes alphabetically first. */
  if (depth < 26)
    {
      c = 'a' + depth;
      print_str (rdm, &c, 1);
    }
  else
    {
      /* Use `'_123` after running out of letters. */
      PRINT ("_");
      print_uint64 (rdm, depth);
    }
}

/* Demangling functions. */

static void demangle_binder (struct rust_demangler *rdm);
static void demangle_path (struct rust_demangler *rdm, int in_value);
static void demangle_generic_arg (struct rust_demangler *rdm);
static void demangle_type (struct rust_demangler *rdm);
static int demangle_path_maybe_open_generics (struct rust_demangler *rdm);
static void demangle_dyn_trait (struct rust_demangler *rdm);
static void demangle_const (struct rust_demangler *rdm);
static void demangle_const_uint (struct rust_demangler *rdm);
static void demangle_const_int (struct rust_demangler *rdm);
static void demangle_const_bool (struct rust_demangler *rdm);
static void demangle_const_char (struct rust_demangler *rdm);

/* Optionally enter a binder ('G') for late-bound lifetimes,
   printing e.g. `for<'a, 'b> `, and make those lifetimes visible
   to the caller (via depth level, which the caller should reset). */
static void
demangle_binder (struct rust_demangler *rdm)
{
  uint64_t i, bound_lifetimes;

  if (rdm->errored)
    return;

  bound_lifetimes = parse_opt_integer_62 (rdm, 'G');
  if (bound_lifetimes > 0)
    {
      PRINT ("for<");
      for (i = 0; i < bound_lifetimes; i++)
        {
          if (i > 0)
            PRINT (", ");
          rdm->bound_lifetime_depth++;
          print_lifetime_from_index (rdm, 1);
        }
      PRINT ("> ");
    }
}

static void
demangle_path (struct rust_demangler *rdm, int in_value)
{
  char tag, ns;
  int was_skipping_printing;
  size_t i, backref, old_next;
  uint64_t dis;
  struct rust_mangled_ident name;

  if (rdm->errored)
    return;

  switch (tag = next (rdm))
    {
    case 'C':
      dis = parse_disambiguator (rdm);
      name = parse_ident (rdm);

      print_ident (rdm, name);
      if (rdm->verbose)
        {
          PRINT ("[");
          print_uint64_hex (rdm, dis);
          PRINT ("]");
        }
      break;
    case 'N':
      ns = next (rdm);
      if (!ISLOWER (ns) && !ISUPPER (ns))
        {
          rdm->errored = 1;
          return;
        }

      demangle_path (rdm, in_value);

      dis = parse_disambiguator (rdm);
      name = parse_ident (rdm);

      if (ISUPPER (ns))
        {
          /* Special namespaces, like closures and shims. */
          PRINT ("::{");
          switch (ns)
            {
            case 'C':
              PRINT ("closure");
              break;
            case 'S':
              PRINT ("shim");
              break;
            default:
              print_str (rdm, &ns, 1);
            }
          if (name.ascii || name.punycode)
            {
              PRINT (":");
              print_ident (rdm, name);
            }
          PRINT ("#");
          print_uint64 (rdm, dis);
          PRINT ("}");
        }
      else
        {
          /* Implementation-specific/unspecified namespaces. */

          if (name.ascii || name.punycode)
            {
              PRINT ("::");
              print_ident (rdm, name);
            }
        }
      break;
    case 'M':
    case 'X':
      /* Ignore the `impl`'s own path.*/
      parse_disambiguator (rdm);
      was_skipping_printing = rdm->skipping_printing;
      rdm->skipping_printing = 1;
      demangle_path (rdm, in_value);
      rdm->skipping_printing = was_skipping_printing;
      /* fallthrough */
    case 'Y':
      PRINT ("<");
      demangle_type (rdm);
      if (tag != 'M')
        {
          PRINT (" as ");
          demangle_path (rdm, 0);
        }
      PRINT (">");
      break;
    case 'I':
      demangle_path (rdm, in_value);
      if (in_value)
        PRINT ("::");
      PRINT ("<");
      for (i = 0; !rdm->errored && !eat (rdm, 'E'); i++)
        {
          if (i > 0)
            PRINT (", ");
          demangle_generic_arg (rdm);
        }
      PRINT (">");
      break;
    case 'B':
      backref = parse_integer_62 (rdm);
      if (!rdm->skipping_printing)
        {
          old_next = rdm->next;
          rdm->next = backref;
          demangle_path (rdm, in_value);
          rdm->next = old_next;
        }
      break;
    default:
      rdm->errored = 1;
      return;
    }
}

static void
demangle_generic_arg (struct rust_demangler *rdm)
{
  uint64_t lt;
  if (eat (rdm, 'L'))
    {
      lt = parse_integer_62 (rdm);
      print_lifetime_from_index (rdm, lt);
    }
  else if (eat (rdm, 'K'))
    demangle_const (rdm);
  else
    demangle_type (rdm);
}

static const char *
basic_type (char tag)
{
  switch (tag)
    {
    case 'b':
      return "bool";
    case 'c':
      return "char";
    case 'e':
      return "str";
    case 'u':
      return "()";
    case 'a':
      return "i8";
    case 's':
      return "i16";
    case 'l':
      return "i32";
    case 'x':
      return "i64";
    case 'n':
      return "i128";
    case 'i':
      return "isize";
    case 'h':
      return "u8";
    case 't':
      return "u16";
    case 'm':
      return "u32";
    case 'y':
      return "u64";
    case 'o':
      return "u128";
    case 'j':
      return "usize";
    case 'f':
      return "f32";
    case 'd':
      return "f64";
    case 'z':
      return "!";
    case 'p':
      return "_";
    case 'v':
      return "...";

    default:
      return NULL;
    }
}

static void
demangle_type (struct rust_demangler *rdm)
{
  char tag;
  size_t i, old_next, backref;
  uint64_t lt, old_bound_lifetime_depth;
  const char *basic;
  struct rust_mangled_ident abi;

  if (rdm->errored)
    return;

  tag = next (rdm);

  basic = basic_type (tag);
  if (basic)
    {
      PRINT (basic);
      return;
    }

  switch (tag)
    {
    case 'R':
    case 'Q':
      PRINT ("&");
      if (eat (rdm, 'L'))
        {
          lt = parse_integer_62 (rdm);
          if (lt)
            {
              print_lifetime_from_index (rdm, lt);
              PRINT (" ");
            }
        }
      if (tag != 'R')
        PRINT ("mut ");
      demangle_type (rdm);
      break;
    case 'P':
    case 'O':
      PRINT ("*");
      if (tag != 'P')
        PRINT ("mut ");
      else
        PRINT ("const ");
      demangle_type (rdm);
      break;
    case 'A':
    case 'S':
      PRINT ("[");
      demangle_type (rdm);
      if (tag == 'A')
        {
          PRINT ("; ");
          demangle_const (rdm);
        }
      PRINT ("]");
      break;
    case 'T':
      PRINT ("(");
      for (i = 0; !rdm->errored && !eat (rdm, 'E'); i++)
        {
          if (i > 0)
            PRINT (", ");
          demangle_type (rdm);
        }
      if (i == 1)
        PRINT (",");
      PRINT (")");
      break;
    case 'F':
      old_bound_lifetime_depth = rdm->bound_lifetime_depth;
      demangle_binder (rdm);

      if (eat (rdm, 'U'))
        PRINT ("unsafe ");

      if (eat (rdm, 'K'))
        {
          if (eat (rdm, 'C'))
            {
              abi.ascii = "C";
              abi.ascii_len = 1;
            }
          else
            {
              abi = parse_ident (rdm);
              if (!abi.ascii || abi.punycode)
                {
                  rdm->errored = 1;
                  goto restore;
                }
            }

          PRINT ("extern \"");

          /* If the ABI had any `-`, they were replaced with `_`,
             so the parts between `_` have to be re-joined with `-`. */
          for (i = 0; i < abi.ascii_len; i++)
            {
              if (abi.ascii[i] == '_')
                {
                  print_str (rdm, abi.ascii, i);
                  PRINT ("-");
                  abi.ascii += i + 1;
                  abi.ascii_len -= i + 1;
                  i = 0;
                }
            }
          print_str (rdm, abi.ascii, abi.ascii_len);

          PRINT ("\" ");
        }

      PRINT ("fn(");
      for (i = 0; !rdm->errored && !eat (rdm, 'E'); i++)
        {
          if (i > 0)
            PRINT (", ");
          demangle_type (rdm);
        }
      PRINT (")");

      if (eat (rdm, 'u'))
        {
          /* Skip printing the return type if it's 'u', i.e. `()`. */
        }
      else
        {
          PRINT (" -> ");
          demangle_type (rdm);
        }

    /* Restore `bound_lifetime_depth` to outside the binder. */
    restore:
      rdm->bound_lifetime_depth = old_bound_lifetime_depth;
      break;
    case 'D':
      PRINT ("dyn ");

      old_bound_lifetime_depth = rdm->bound_lifetime_depth;
      demangle_binder (rdm);

      for (i = 0; !rdm->errored && !eat (rdm, 'E'); i++)
        {
          if (i > 0)
            PRINT (" + ");
          demangle_dyn_trait (rdm);
        }

      /* Restore `bound_lifetime_depth` to outside the binder. */
      rdm->bound_lifetime_depth = old_bound_lifetime_depth;

      if (!eat (rdm, 'L'))
        {
          rdm->errored = 1;
          return;
        }
      lt = parse_integer_62 (rdm);
      if (lt)
        {
          PRINT (" + ");
          print_lifetime_from_index (rdm, lt);
        }
      break;
    case 'B':
      backref = parse_integer_62 (rdm);
      if (!rdm->skipping_printing)
        {
          old_next = rdm->next;
          rdm->next = backref;
          demangle_type (rdm);
          rdm->next = old_next;
        }
      break;
    default:
      /* Go back to the tag, so `demangle_path` also sees it. */
      rdm->next--;
      demangle_path (rdm, 0);
    }
}

/* A trait in a trait object may have some "existential projections"
   (i.e. associated type bindings) after it, which should be printed
   in the `<...>` of the trait, e.g. `dyn Trait<T, U, Assoc=X>`.
   To this end, this method will keep the `<...>` of an 'I' path
   open, by omitting the `>`, and return `Ok(true)` in that case. */
static int
demangle_path_maybe_open_generics (struct rust_demangler *rdm)
{
  int open;
  size_t i, old_next, backref;

  open = 0;

  if (rdm->errored)
    return open;

  if (eat (rdm, 'B'))
    {
      backref = parse_integer_62 (rdm);
      if (!rdm->skipping_printing)
        {
          old_next = rdm->next;
          rdm->next = backref;
          open = demangle_path_maybe_open_generics (rdm);
          rdm->next = old_next;
        }
    }
  else if (eat (rdm, 'I'))
    {
      demangle_path (rdm, 0);
      PRINT ("<");
      open = 1;
      for (i = 0; !rdm->errored && !eat (rdm, 'E'); i++)
        {
          if (i > 0)
            PRINT (", ");
          demangle_generic_arg (rdm);
        }
    }
  else
    demangle_path (rdm, 0);
  return open;
}

static void
demangle_dyn_trait (struct rust_demangler *rdm)
{
  int open;
  struct rust_mangled_ident name;

  if (rdm->errored)
    return;

  open = demangle_path_maybe_open_generics (rdm);

  while (eat (rdm, 'p'))
    {
      if (!open)
        PRINT ("<");
      else
        PRINT (", ");
      open = 1;

      name = parse_ident (rdm);
      print_ident (rdm, name);
      PRINT (" = ");
      demangle_type (rdm);
    }

  if (open)
    PRINT (">");
}

static void
demangle_const (struct rust_demangler *rdm)
{
  char ty_tag;
  size_t old_next, backref;

  if (rdm->errored)
    return;

  if (eat (rdm, 'B'))
    {
      backref = parse_integer_62 (rdm);
      if (!rdm->skipping_printing)
        {
          old_next = rdm->next;
          rdm->next = backref;
          demangle_const (rdm);
          rdm->next = old_next;
        }
      return;
    }

  ty_tag = next (rdm);
  switch (ty_tag)
    {
    /* Placeholder. */
    case 'p':
      PRINT ("_");
      return;

    /* Unsigned integer types. */
    case 'h':
    case 't':
    case 'm':
    case 'y':
    case 'o':
    case 'j':
      demangle_const_uint (rdm);
      break;

    /* Signed integer types. */
    case 'a':
    case 's':
    case 'l':
    case 'x':
    case 'n':
    case 'i':
      demangle_const_int (rdm);
      break;

    /* Boolean. */
    case 'b':
      demangle_const_bool (rdm);
      break;

    /* Character. */
    case 'c':
      demangle_const_char (rdm);
      break;

    default:
      rdm->errored = 1;
      return;
    }

  if (rdm->errored)
    return;

  if (rdm->verbose)
    {
      PRINT (": ");
      PRINT (basic_type (ty_tag));
    }
}

static void
demangle_const_uint (struct rust_demangler *rdm)
{
  size_t hex_len;
  uint64_t value;

  if (rdm->errored)
    return;

  hex_len = parse_hex_nibbles (rdm, &value);

  if (hex_len > 16)
    {
      /* Print anything that doesn't fit in `uint64_t` verbatim. */
      PRINT ("0x");
      print_str (rdm, rdm->sym + (rdm->next - hex_len), hex_len);
    }
  else if (hex_len > 0)
    print_uint64 (rdm, value);
  else
    rdm->errored = 1;
}

static void
demangle_const_int (struct rust_demangler *rdm)
{
  if (eat (rdm, 'n'))
    PRINT ("-");
  demangle_const_uint (rdm);
}

static void
demangle_const_bool (struct rust_demangler *rdm)
{
  uint64_t value;

  if (parse_hex_nibbles (rdm, &value) != 1)
    {
      rdm->errored = 1;
      return;
    }

  if (value == 0)
    PRINT ("false");
  else if (value == 1)
    PRINT ("true");
  else
    rdm->errored = 1;
}

static void
demangle_const_char (struct rust_demangler *rdm)
{
  size_t hex_len;
  uint64_t value;

  hex_len = parse_hex_nibbles (rdm, &value);

  if (hex_len == 0 || hex_len > 8)
    {
      rdm->errored = 1;
      return;
    }

  /* Match Rust's character "debug" output as best as we can. */
  PRINT ("'");
  if (value == '\t')
    PRINT ("\\t");
  else if (value == '\r')
    PRINT ("\\r");
  else if (value == '\n')
    PRINT ("\\n");
  else if (value > ' ' && value < '~')
    {
      /* Rust also considers many non-ASCII codepoints to be printable, but
	 that logic is not easily ported to C. */
      char c = value;
      print_str (rdm, &c, 1);
    }
  else
    {
      PRINT ("\\u{");
      print_uint64_hex (rdm, value);
      PRINT ("}");
    }
  PRINT ("'");
}

/* A legacy hash is the prefix "h" followed by 16 lowercase hex digits.
   The hex digits must contain at least 5 distinct digits. */
static int
is_legacy_prefixed_hash (struct rust_mangled_ident ident)
{
  uint16_t seen;
  int nibble;
  size_t i, count;

  if (ident.ascii_len != 17 || ident.ascii[0] != 'h')
    return 0;

  seen = 0;
  for (i = 0; i < 16; i++)
    {
      nibble = decode_lower_hex_nibble (ident.ascii[1 + i]);
      if (nibble < 0)
        return 0;
      seen |= (uint16_t)1 << nibble;
    }

  /* Count how many distinct digits were seen. */
  count = 0;
  while (seen)
    {
      if (seen & 1)
        count++;
      seen >>= 1;
    }

  return count >= 5;
}

int
rust_demangle_callback (const char *mangled, int options,
                        demangle_callbackref callback, void *opaque)
{
  const char *p;
  struct rust_demangler rdm;
  struct rust_mangled_ident ident;

  rdm.sym = mangled;
  rdm.sym_len = 0;

  rdm.callback_opaque = opaque;
  rdm.callback = callback;

  rdm.next = 0;
  rdm.errored = 0;
  rdm.skipping_printing = 0;
  rdm.verbose = (options & DMGL_VERBOSE) != 0;
  rdm.version = 0;
  rdm.bound_lifetime_depth = 0;

  /* Rust symbols always start with _R (v0) or _ZN (legacy). */
  if (rdm.sym[0] == '_' && rdm.sym[1] == 'R')
    rdm.sym += 2;
  else if (rdm.sym[0] == '_' && rdm.sym[1] == 'Z' && rdm.sym[2] == 'N')
    {
      rdm.sym += 3;
      rdm.version = -1;
    }
  else
    return 0;

  /* Paths (v0) always start with uppercase characters. */
  if (rdm.version != -1 && !ISUPPER (rdm.sym[0]))
    return 0;

  /* Rust symbols (v0) use only [_0-9a-zA-Z] characters. */
  for (p = rdm.sym; *p; p++)
    {
      rdm.sym_len++;

      if (*p == '_' || ISALNUM (*p))
        continue;

      /* Legacy Rust symbols can also contain [.:$] characters. */
      if (rdm.version == -1 && (*p == '$' || *p == '.' || *p == ':'))
        continue;

      return 0;
    }

  /* Legacy Rust symbols need to be handled separately. */
  if (rdm.version == -1)
    {
      /* Legacy Rust symbols always end with E. */
      if (!(rdm.sym_len > 0 && rdm.sym[rdm.sym_len - 1] == 'E'))
        return 0;
      rdm.sym_len--;

      /* Legacy Rust symbols also always end with a path segment
         that encodes a 16 hex digit hash, i.e. '17h[a-f0-9]{16}'.
         This early check, before any parse_ident calls, should
         quickly filter out most C++ symbols unrelated to Rust. */
      if (!(rdm.sym_len > 19
            && !memcmp (&rdm.sym[rdm.sym_len - 19], "17h", 3)))
        return 0;

      do
        {
          ident = parse_ident (&rdm);
          if (rdm.errored || !ident.ascii)
            return 0;
        }
      while (rdm.next < rdm.sym_len);

      /* The last path segment should be the hash. */
      if (!is_legacy_prefixed_hash (ident))
        return 0;

      /* Reset the state for a second pass, to print the symbol. */
      rdm.next = 0;
      if (!rdm.verbose && rdm.sym_len > 19)
        {
          /* Hide the last segment, containing the hash, if not verbose. */
          rdm.sym_len -= 19;
        }

      do
        {
          if (rdm.next > 0)
            print_str (&rdm, "::", 2);

          ident = parse_ident (&rdm);
          print_ident (&rdm, ident);
        }
      while (rdm.next < rdm.sym_len);
    }
  else
    {
      demangle_path (&rdm, 1);

      /* Skip instantiating crate. */
      if (!rdm.errored && rdm.next < rdm.sym_len)
        {
          rdm.skipping_printing = 1;
          demangle_path (&rdm, 0);
        }

      /* It's an error to not reach the end. */
      rdm.errored |= rdm.next != rdm.sym_len;
    }

  return !rdm.errored;
}

/* Growable string buffers. */
struct str_buf
{
  char *ptr;
  size_t len;
  size_t cap;
  int errored;
};

static void
str_buf_reserve (struct str_buf *buf, size_t extra)
{
  size_t available, min_new_cap, new_cap;
  char *new_ptr;

  /* Allocation failed before. */
  if (buf->errored)
    return;

  available = buf->cap - buf->len;

  if (extra <= available)
    return;

  min_new_cap = buf->cap + (extra - available);

  /* Check for overflows. */
  if (min_new_cap < buf->cap)
    {
      buf->errored = 1;
      return;
    }

  new_cap = buf->cap;

  if (new_cap == 0)
    new_cap = 4;

  /* Double capacity until sufficiently large. */
  while (new_cap < min_new_cap)
    {
      new_cap *= 2;

      /* Check for overflows. */
      if (new_cap < buf->cap)
        {
          buf->errored = 1;
          return;
        }
    }

  new_ptr = (char *)realloc (buf->ptr, new_cap);
  if (new_ptr == NULL)
    {
      free (buf->ptr);
      buf->ptr = NULL;
      buf->len = 0;
      buf->cap = 0;
      buf->errored = 1;
    }
  else
    {
      buf->ptr = new_ptr;
      buf->cap = new_cap;
    }
}

static void
str_buf_append (struct str_buf *buf, const char *data, size_t len)
{
  str_buf_reserve (buf, len);
  if (buf->errored)
    return;

  memcpy (buf->ptr + buf->len, data, len);
  buf->len += len;
}

static void
str_buf_demangle_callback (const char *data, size_t len, void *opaque)
{
  str_buf_append ((struct str_buf *)opaque, data, len);
}

char *
rust_demangle (const char *mangled, int options)
{
  struct str_buf out;
  int success;

  out.ptr = NULL;
  out.len = 0;
  out.cap = 0;
  out.errored = 0;

  success = rust_demangle_callback (mangled, options,
                                    str_buf_demangle_callback, &out);

  if (!success)
    {
      free (out.ptr);
      return NULL;
    }

  str_buf_append (&out, "\0", 1);
  return out.ptr;
}
