about summary refs log tree commit diff
path: root/src/librustc_codegen_utils
diff options
context:
space:
mode:
Diffstat (limited to 'src/librustc_codegen_utils')
-rw-r--r--src/librustc_codegen_utils/Cargo.toml23
-rw-r--r--src/librustc_codegen_utils/codegen_backend.rs64
-rw-r--r--src/librustc_codegen_utils/lib.rs66
-rw-r--r--src/librustc_codegen_utils/link.rs189
-rw-r--r--src/librustc_codegen_utils/symbol_names.rs262
-rw-r--r--src/librustc_codegen_utils/symbol_names/legacy.rs434
-rw-r--r--src/librustc_codegen_utils/symbol_names/v0.rs641
-rw-r--r--src/librustc_codegen_utils/symbol_names_test.rs70
8 files changed, 0 insertions, 1749 deletions
diff --git a/src/librustc_codegen_utils/Cargo.toml b/src/librustc_codegen_utils/Cargo.toml
deleted file mode 100644
index b5533a8307c..00000000000
--- a/src/librustc_codegen_utils/Cargo.toml
+++ /dev/null
@@ -1,23 +0,0 @@
-[package]
-authors = ["The Rust Project Developers"]
-name = "rustc_codegen_utils"
-version = "0.0.0"
-edition = "2018"
-
-[lib]
-name = "rustc_codegen_utils"
-path = "lib.rs"
-test = false
-
-[dependencies]
-log = "0.4"
-punycode = "0.4.0"
-rustc-demangle = "0.1.16"
-
-rustc_ast = { path = "../librustc_ast" }
-rustc_span = { path = "../librustc_span" }
-rustc = { path = "../librustc" }
-rustc_hir = { path = "../librustc_hir" }
-rustc_target = { path = "../librustc_target" }
-rustc_data_structures = { path = "../librustc_data_structures" }
-rustc_metadata = { path = "../librustc_metadata" }
diff --git a/src/librustc_codegen_utils/codegen_backend.rs b/src/librustc_codegen_utils/codegen_backend.rs
deleted file mode 100644
index 96166e04c2e..00000000000
--- a/src/librustc_codegen_utils/codegen_backend.rs
+++ /dev/null
@@ -1,64 +0,0 @@
-//! The Rust compiler.
-//!
-//! # Note
-//!
-//! This API is completely unstable and subject to change.
-
-#![doc(html_root_url = "https://doc.rust-lang.org/nightly/")]
-
-use std::any::Any;
-
-use rustc::dep_graph::DepGraph;
-use rustc::middle::cstore::{EncodedMetadata, MetadataLoaderDyn};
-use rustc::session::config::{OutputFilenames, PrintRequest};
-use rustc::session::Session;
-use rustc::ty::query::Providers;
-use rustc::ty::TyCtxt;
-use rustc::util::common::ErrorReported;
-use rustc_span::symbol::Symbol;
-
-pub use rustc_data_structures::sync::MetadataRef;
-
-pub trait CodegenBackend {
-    fn init(&self, _sess: &Session) {}
-    fn print(&self, _req: PrintRequest, _sess: &Session) {}
-    fn target_features(&self, _sess: &Session) -> Vec<Symbol> {
-        vec![]
-    }
-    fn print_passes(&self) {}
-    fn print_version(&self) {}
-
-    fn metadata_loader(&self) -> Box<MetadataLoaderDyn>;
-    fn provide(&self, _providers: &mut Providers<'_>);
-    fn provide_extern(&self, _providers: &mut Providers<'_>);
-    fn codegen_crate<'tcx>(
-        &self,
-        tcx: TyCtxt<'tcx>,
-        metadata: EncodedMetadata,
-        need_metadata_module: bool,
-    ) -> Box<dyn Any>;
-
-    /// This is called on the returned `Box<dyn Any>` from `codegen_backend`
-    ///
-    /// # Panics
-    ///
-    /// Panics when the passed `Box<dyn Any>` was not returned by `codegen_backend`.
-    fn join_codegen(
-        &self,
-        ongoing_codegen: Box<dyn Any>,
-        sess: &Session,
-        dep_graph: &DepGraph,
-    ) -> Result<Box<dyn Any>, ErrorReported>;
-
-    /// This is called on the returned `Box<dyn Any>` from `join_codegen`
-    ///
-    /// # Panics
-    ///
-    /// Panics when the passed `Box<dyn Any>` was not returned by `join_codegen`.
-    fn link(
-        &self,
-        sess: &Session,
-        codegen_results: Box<dyn Any>,
-        outputs: &OutputFilenames,
-    ) -> Result<(), ErrorReported>;
-}
diff --git a/src/librustc_codegen_utils/lib.rs b/src/librustc_codegen_utils/lib.rs
deleted file mode 100644
index 38906bbaef8..00000000000
--- a/src/librustc_codegen_utils/lib.rs
+++ /dev/null
@@ -1,66 +0,0 @@
-//! # Note
-//!
-//! This API is completely unstable and subject to change.
-
-#![doc(html_root_url = "https://doc.rust-lang.org/nightly/")]
-#![feature(never_type)]
-#![feature(nll)]
-#![feature(in_band_lifetimes)]
-#![recursion_limit = "256"]
-
-#[macro_use]
-extern crate rustc;
-
-use rustc::ty::query::Providers;
-use rustc::ty::TyCtxt;
-use rustc_hir::def_id::{DefId, LOCAL_CRATE};
-use rustc_span::symbol::sym;
-
-pub mod codegen_backend;
-pub mod link;
-pub mod symbol_names;
-pub mod symbol_names_test;
-
-pub fn trigger_delay_span_bug(tcx: TyCtxt<'_>, key: DefId) {
-    tcx.sess.delay_span_bug(
-        tcx.def_span(key),
-        "delayed span bug triggered by #[rustc_error(delay_span_bug_from_inside_query)]",
-    );
-}
-
-/// check for the #[rustc_error] annotation, which forces an
-/// error in codegen. This is used to write compile-fail tests
-/// that actually test that compilation succeeds without
-/// reporting an error.
-pub fn check_for_rustc_errors_attr(tcx: TyCtxt<'_>) {
-    if let Some((def_id, _)) = tcx.entry_fn(LOCAL_CRATE) {
-        let attrs = &*tcx.get_attrs(def_id);
-        for attr in attrs {
-            if attr.check_name(sym::rustc_error) {
-                match attr.meta_item_list() {
-                    // check if there is a #[rustc_error(delayed)]
-                    Some(list) => {
-                        if list.iter().any(|list_item| {
-                            list_item.ident().map(|i| i.name)
-                                == Some(sym::delay_span_bug_from_inside_query)
-                        }) {
-                            tcx.ensure().trigger_delay_span_bug(def_id);
-                        }
-                    }
-                    // bare #[rustc_error]
-                    None => {
-                        tcx.sess.span_fatal(
-                            tcx.def_span(def_id),
-                            "fatal error triggered by #[rustc_error]",
-                        );
-                    }
-                }
-            }
-        }
-    }
-}
-
-pub fn provide(providers: &mut Providers<'_>) {
-    crate::symbol_names::provide(providers);
-    *providers = Providers { trigger_delay_span_bug, ..*providers };
-}
diff --git a/src/librustc_codegen_utils/link.rs b/src/librustc_codegen_utils/link.rs
deleted file mode 100644
index 524fb0a59c2..00000000000
--- a/src/librustc_codegen_utils/link.rs
+++ /dev/null
@@ -1,189 +0,0 @@
-use rustc::session::config::{self, Input, OutputFilenames, OutputType};
-use rustc::session::Session;
-use rustc_ast::{ast, attr};
-use rustc_span::symbol::sym;
-use rustc_span::Span;
-use std::path::{Path, PathBuf};
-
-pub fn out_filename(
-    sess: &Session,
-    crate_type: config::CrateType,
-    outputs: &OutputFilenames,
-    crate_name: &str,
-) -> PathBuf {
-    let default_filename = filename_for_input(sess, crate_type, crate_name, outputs);
-    let out_filename = outputs
-        .outputs
-        .get(&OutputType::Exe)
-        .and_then(|s| s.to_owned())
-        .or_else(|| outputs.single_output_file.clone())
-        .unwrap_or(default_filename);
-
-    check_file_is_writeable(&out_filename, sess);
-
-    out_filename
-}
-
-// Make sure files are writeable.  Mac, FreeBSD, and Windows system linkers
-// check this already -- however, the Linux linker will happily overwrite a
-// read-only file.  We should be consistent.
-pub fn check_file_is_writeable(file: &Path, sess: &Session) {
-    if !is_writeable(file) {
-        sess.fatal(&format!(
-            "output file {} is not writeable -- check its \
-                            permissions",
-            file.display()
-        ));
-    }
-}
-
-fn is_writeable(p: &Path) -> bool {
-    match p.metadata() {
-        Err(..) => true,
-        Ok(m) => !m.permissions().readonly(),
-    }
-}
-
-pub fn find_crate_name(sess: Option<&Session>, attrs: &[ast::Attribute], input: &Input) -> String {
-    let validate = |s: String, span: Option<Span>| {
-        rustc_metadata::validate_crate_name(sess, &s, span);
-        s
-    };
-
-    // Look in attributes 100% of the time to make sure the attribute is marked
-    // as used. After doing this, however, we still prioritize a crate name from
-    // the command line over one found in the #[crate_name] attribute. If we
-    // find both we ensure that they're the same later on as well.
-    let attr_crate_name =
-        attr::find_by_name(attrs, sym::crate_name).and_then(|at| at.value_str().map(|s| (at, s)));
-
-    if let Some(sess) = sess {
-        if let Some(ref s) = sess.opts.crate_name {
-            if let Some((attr, name)) = attr_crate_name {
-                if name.as_str() != *s {
-                    let msg = format!(
-                        "`--crate-name` and `#[crate_name]` are \
-                                       required to match, but `{}` != `{}`",
-                        s, name
-                    );
-                    sess.span_err(attr.span, &msg);
-                }
-            }
-            return validate(s.clone(), None);
-        }
-    }
-
-    if let Some((attr, s)) = attr_crate_name {
-        return validate(s.to_string(), Some(attr.span));
-    }
-    if let Input::File(ref path) = *input {
-        if let Some(s) = path.file_stem().and_then(|s| s.to_str()) {
-            if s.starts_with('-') {
-                let msg = format!(
-                    "crate names cannot start with a `-`, but \
-                                   `{}` has a leading hyphen",
-                    s
-                );
-                if let Some(sess) = sess {
-                    sess.err(&msg);
-                }
-            } else {
-                return validate(s.replace("-", "_"), None);
-            }
-        }
-    }
-
-    "rust_out".to_string()
-}
-
-pub fn filename_for_metadata(
-    sess: &Session,
-    crate_name: &str,
-    outputs: &OutputFilenames,
-) -> PathBuf {
-    let libname = format!("{}{}", crate_name, sess.opts.cg.extra_filename);
-
-    let out_filename = outputs
-        .single_output_file
-        .clone()
-        .unwrap_or_else(|| outputs.out_directory.join(&format!("lib{}.rmeta", libname)));
-
-    check_file_is_writeable(&out_filename, sess);
-
-    out_filename
-}
-
-pub fn filename_for_input(
-    sess: &Session,
-    crate_type: config::CrateType,
-    crate_name: &str,
-    outputs: &OutputFilenames,
-) -> PathBuf {
-    let libname = format!("{}{}", crate_name, sess.opts.cg.extra_filename);
-
-    match crate_type {
-        config::CrateType::Rlib => outputs.out_directory.join(&format!("lib{}.rlib", libname)),
-        config::CrateType::Cdylib | config::CrateType::ProcMacro | config::CrateType::Dylib => {
-            let (prefix, suffix) =
-                (&sess.target.target.options.dll_prefix, &sess.target.target.options.dll_suffix);
-            outputs.out_directory.join(&format!("{}{}{}", prefix, libname, suffix))
-        }
-        config::CrateType::Staticlib => {
-            let (prefix, suffix) = (
-                &sess.target.target.options.staticlib_prefix,
-                &sess.target.target.options.staticlib_suffix,
-            );
-            outputs.out_directory.join(&format!("{}{}{}", prefix, libname, suffix))
-        }
-        config::CrateType::Executable => {
-            let suffix = &sess.target.target.options.exe_suffix;
-            let out_filename = outputs.path(OutputType::Exe);
-            if suffix.is_empty() { out_filename } else { out_filename.with_extension(&suffix[1..]) }
-        }
-    }
-}
-
-/// Returns default crate type for target
-///
-/// Default crate type is used when crate type isn't provided neither
-/// through cmd line arguments nor through crate attributes
-///
-/// It is CrateType::Executable for all platforms but iOS as there is no
-/// way to run iOS binaries anyway without jailbreaking and
-/// interaction with Rust code through static library is the only
-/// option for now
-pub fn default_output_for_target(sess: &Session) -> config::CrateType {
-    if !sess.target.target.options.executables {
-        config::CrateType::Staticlib
-    } else {
-        config::CrateType::Executable
-    }
-}
-
-/// Checks if target supports crate_type as output
-pub fn invalid_output_for_target(sess: &Session, crate_type: config::CrateType) -> bool {
-    match crate_type {
-        config::CrateType::Cdylib | config::CrateType::Dylib | config::CrateType::ProcMacro => {
-            if !sess.target.target.options.dynamic_linking {
-                return true;
-            }
-            if sess.crt_static() && !sess.target.target.options.crt_static_allows_dylibs {
-                return true;
-            }
-        }
-        _ => {}
-    }
-    if sess.target.target.options.only_cdylib {
-        match crate_type {
-            config::CrateType::ProcMacro | config::CrateType::Dylib => return true,
-            _ => {}
-        }
-    }
-    if !sess.target.target.options.executables {
-        if crate_type == config::CrateType::Executable {
-            return true;
-        }
-    }
-
-    false
-}
diff --git a/src/librustc_codegen_utils/symbol_names.rs b/src/librustc_codegen_utils/symbol_names.rs
deleted file mode 100644
index 6713459f627..00000000000
--- a/src/librustc_codegen_utils/symbol_names.rs
+++ /dev/null
@@ -1,262 +0,0 @@
-//! The Rust Linkage Model and Symbol Names
-//! =======================================
-//!
-//! The semantic model of Rust linkage is, broadly, that "there's no global
-//! namespace" between crates. Our aim is to preserve the illusion of this
-//! model despite the fact that it's not *quite* possible to implement on
-//! modern linkers. We initially didn't use system linkers at all, but have
-//! been convinced of their utility.
-//!
-//! There are a few issues to handle:
-//!
-//!  - Linkers operate on a flat namespace, so we have to flatten names.
-//!    We do this using the C++ namespace-mangling technique. Foo::bar
-//!    symbols and such.
-//!
-//!  - Symbols for distinct items with the same *name* need to get different
-//!    linkage-names. Examples of this are monomorphizations of functions or
-//!    items within anonymous scopes that end up having the same path.
-//!
-//!  - Symbols in different crates but with same names "within" the crate need
-//!    to get different linkage-names.
-//!
-//!  - Symbol names should be deterministic: Two consecutive runs of the
-//!    compiler over the same code base should produce the same symbol names for
-//!    the same items.
-//!
-//!  - Symbol names should not depend on any global properties of the code base,
-//!    so that small modifications to the code base do not result in all symbols
-//!    changing. In previous versions of the compiler, symbol names incorporated
-//!    the SVH (Stable Version Hash) of the crate. This scheme turned out to be
-//!    infeasible when used in conjunction with incremental compilation because
-//!    small code changes would invalidate all symbols generated previously.
-//!
-//!  - Even symbols from different versions of the same crate should be able to
-//!    live next to each other without conflict.
-//!
-//! In order to fulfill the above requirements the following scheme is used by
-//! the compiler:
-//!
-//! The main tool for avoiding naming conflicts is the incorporation of a 64-bit
-//! hash value into every exported symbol name. Anything that makes a difference
-//! to the symbol being named, but does not show up in the regular path needs to
-//! be fed into this hash:
-//!
-//! - Different monomorphizations of the same item have the same path but differ
-//!   in their concrete type parameters, so these parameters are part of the
-//!   data being digested for the symbol hash.
-//!
-//! - Rust allows items to be defined in anonymous scopes, such as in
-//!   `fn foo() { { fn bar() {} } { fn bar() {} } }`. Both `bar` functions have
-//!   the path `foo::bar`, since the anonymous scopes do not contribute to the
-//!   path of an item. The compiler already handles this case via so-called
-//!   disambiguating `DefPaths` which use indices to distinguish items with the
-//!   same name. The DefPaths of the functions above are thus `foo[0]::bar[0]`
-//!   and `foo[0]::bar[1]`. In order to incorporate this disambiguation
-//!   information into the symbol name too, these indices are fed into the
-//!   symbol hash, so that the above two symbols would end up with different
-//!   hash values.
-//!
-//! The two measures described above suffice to avoid intra-crate conflicts. In
-//! order to also avoid inter-crate conflicts two more measures are taken:
-//!
-//! - The name of the crate containing the symbol is prepended to the symbol
-//!   name, i.e., symbols are "crate qualified". For example, a function `foo` in
-//!   module `bar` in crate `baz` would get a symbol name like
-//!   `baz::bar::foo::{hash}` instead of just `bar::foo::{hash}`. This avoids
-//!   simple conflicts between functions from different crates.
-//!
-//! - In order to be able to also use symbols from two versions of the same
-//!   crate (which naturally also have the same name), a stronger measure is
-//!   required: The compiler accepts an arbitrary "disambiguator" value via the
-//!   `-C metadata` command-line argument. This disambiguator is then fed into
-//!   the symbol hash of every exported item. Consequently, the symbols in two
-//!   identical crates but with different disambiguators are not in conflict
-//!   with each other. This facility is mainly intended to be used by build
-//!   tools like Cargo.
-//!
-//! A note on symbol name stability
-//! -------------------------------
-//! Previous versions of the compiler resorted to feeding NodeIds into the
-//! symbol hash in order to disambiguate between items with the same path. The
-//! current version of the name generation algorithm takes great care not to do
-//! that, since NodeIds are notoriously unstable: A small change to the
-//! code base will offset all NodeIds after the change and thus, much as using
-//! the SVH in the hash, invalidate an unbounded number of symbol names. This
-//! makes re-using previously compiled code for incremental compilation
-//! virtually impossible. Thus, symbol hash generation exclusively relies on
-//! DefPaths which are much more robust in the face of changes to the code base.
-
-use rustc::middle::codegen_fn_attrs::CodegenFnAttrFlags;
-use rustc::mir::mono::{InstantiationMode, MonoItem};
-use rustc::session::config::SymbolManglingVersion;
-use rustc::ty::query::Providers;
-use rustc::ty::subst::SubstsRef;
-use rustc::ty::{self, Instance, TyCtxt};
-use rustc_hir::def_id::{CrateNum, LOCAL_CRATE};
-use rustc_hir::Node;
-
-use rustc_span::symbol::Symbol;
-
-use log::debug;
-
-mod legacy;
-mod v0;
-
-/// This function computes the symbol name for the given `instance` and the
-/// given instantiating crate. That is, if you know that instance X is
-/// instantiated in crate Y, this is the symbol name this instance would have.
-pub fn symbol_name_for_instance_in_crate(
-    tcx: TyCtxt<'tcx>,
-    instance: Instance<'tcx>,
-    instantiating_crate: CrateNum,
-) -> String {
-    compute_symbol_name(tcx, instance, || instantiating_crate)
-}
-
-pub fn provide(providers: &mut Providers<'_>) {
-    *providers = Providers { symbol_name: symbol_name_provider, ..*providers };
-}
-
-// The `symbol_name` query provides the symbol name for calling a given
-// instance from the local crate. In particular, it will also look up the
-// correct symbol name of instances from upstream crates.
-fn symbol_name_provider(tcx: TyCtxt<'tcx>, instance: Instance<'tcx>) -> ty::SymbolName {
-    let symbol_name = compute_symbol_name(tcx, instance, || {
-        // This closure determines the instantiating crate for instances that
-        // need an instantiating-crate-suffix for their symbol name, in order
-        // to differentiate between local copies.
-        if is_generic(instance.substs) {
-            // For generics we might find re-usable upstream instances. If there
-            // is one, we rely on the symbol being instantiated locally.
-            instance.upstream_monomorphization(tcx).unwrap_or(LOCAL_CRATE)
-        } else {
-            // For non-generic things that need to avoid naming conflicts, we
-            // always instantiate a copy in the local crate.
-            LOCAL_CRATE
-        }
-    });
-
-    ty::SymbolName { name: Symbol::intern(&symbol_name) }
-}
-
-/// Computes the symbol name for the given instance. This function will call
-/// `compute_instantiating_crate` if it needs to factor the instantiating crate
-/// into the symbol name.
-fn compute_symbol_name(
-    tcx: TyCtxt<'tcx>,
-    instance: Instance<'tcx>,
-    compute_instantiating_crate: impl FnOnce() -> CrateNum,
-) -> String {
-    let def_id = instance.def_id();
-    let substs = instance.substs;
-
-    debug!("symbol_name(def_id={:?}, substs={:?})", def_id, substs);
-
-    let hir_id = tcx.hir().as_local_hir_id(def_id);
-
-    if def_id.is_local() {
-        if tcx.plugin_registrar_fn(LOCAL_CRATE) == Some(def_id) {
-            let disambiguator = tcx.sess.local_crate_disambiguator();
-            return tcx.sess.generate_plugin_registrar_symbol(disambiguator);
-        }
-        if tcx.proc_macro_decls_static(LOCAL_CRATE) == Some(def_id) {
-            let disambiguator = tcx.sess.local_crate_disambiguator();
-            return tcx.sess.generate_proc_macro_decls_symbol(disambiguator);
-        }
-    }
-
-    // FIXME(eddyb) Precompute a custom symbol name based on attributes.
-    let is_foreign = if let Some(id) = hir_id {
-        match tcx.hir().get(id) {
-            Node::ForeignItem(_) => true,
-            _ => false,
-        }
-    } else {
-        tcx.is_foreign_item(def_id)
-    };
-
-    let attrs = tcx.codegen_fn_attrs(def_id);
-
-    // Foreign items by default use no mangling for their symbol name. There's a
-    // few exceptions to this rule though:
-    //
-    // * This can be overridden with the `#[link_name]` attribute
-    //
-    // * On the wasm32 targets there is a bug (or feature) in LLD [1] where the
-    //   same-named symbol when imported from different wasm modules will get
-    //   hooked up incorectly. As a result foreign symbols, on the wasm target,
-    //   with a wasm import module, get mangled. Additionally our codegen will
-    //   deduplicate symbols based purely on the symbol name, but for wasm this
-    //   isn't quite right because the same-named symbol on wasm can come from
-    //   different modules. For these reasons if `#[link(wasm_import_module)]`
-    //   is present we mangle everything on wasm because the demangled form will
-    //   show up in the `wasm-import-name` custom attribute in LLVM IR.
-    //
-    // [1]: https://bugs.llvm.org/show_bug.cgi?id=44316
-    if is_foreign {
-        if tcx.sess.target.target.arch != "wasm32"
-            || !tcx.wasm_import_module_map(def_id.krate).contains_key(&def_id)
-        {
-            if let Some(name) = attrs.link_name {
-                return name.to_string();
-            }
-            return tcx.item_name(def_id).to_string();
-        }
-    }
-
-    if let Some(name) = attrs.export_name {
-        // Use provided name
-        return name.to_string();
-    }
-
-    if attrs.flags.contains(CodegenFnAttrFlags::NO_MANGLE) {
-        // Don't mangle
-        return tcx.item_name(def_id).to_string();
-    }
-
-    let avoid_cross_crate_conflicts =
-        // If this is an instance of a generic function, we also hash in
-        // the ID of the instantiating crate. This avoids symbol conflicts
-        // in case the same instances is emitted in two crates of the same
-        // project.
-        is_generic(substs) ||
-
-        // If we're dealing with an instance of a function that's inlined from
-        // another crate but we're marking it as globally shared to our
-        // compliation (aka we're not making an internal copy in each of our
-        // codegen units) then this symbol may become an exported (but hidden
-        // visibility) symbol. This means that multiple crates may do the same
-        // and we want to be sure to avoid any symbol conflicts here.
-        match MonoItem::Fn(instance).instantiation_mode(tcx) {
-            InstantiationMode::GloballyShared { may_conflict: true } => true,
-            _ => false,
-        };
-
-    let instantiating_crate =
-        if avoid_cross_crate_conflicts { Some(compute_instantiating_crate()) } else { None };
-
-    // Pick the crate responsible for the symbol mangling version, which has to:
-    // 1. be stable for each instance, whether it's being defined or imported
-    // 2. obey each crate's own `-Z symbol-mangling-version`, as much as possible
-    // We solve these as follows:
-    // 1. because symbol names depend on both `def_id` and `instantiating_crate`,
-    // both their `CrateNum`s are stable for any given instance, so we can pick
-    // either and have a stable choice of symbol mangling version
-    // 2. we favor `instantiating_crate` where possible (i.e. when `Some`)
-    let mangling_version_crate = instantiating_crate.unwrap_or(def_id.krate);
-    let mangling_version = if mangling_version_crate == LOCAL_CRATE {
-        tcx.sess.opts.debugging_opts.symbol_mangling_version
-    } else {
-        tcx.symbol_mangling_version(mangling_version_crate)
-    };
-
-    match mangling_version {
-        SymbolManglingVersion::Legacy => legacy::mangle(tcx, instance, instantiating_crate),
-        SymbolManglingVersion::V0 => v0::mangle(tcx, instance, instantiating_crate),
-    }
-}
-
-fn is_generic(substs: SubstsRef<'_>) -> bool {
-    substs.non_erasable_generics().next().is_some()
-}
diff --git a/src/librustc_codegen_utils/symbol_names/legacy.rs b/src/librustc_codegen_utils/symbol_names/legacy.rs
deleted file mode 100644
index 0dedda9bb6b..00000000000
--- a/src/librustc_codegen_utils/symbol_names/legacy.rs
+++ /dev/null
@@ -1,434 +0,0 @@
-use rustc::hir::map::{DefPathData, DisambiguatedDefPathData};
-use rustc::ich::NodeIdHashingMode;
-use rustc::mir::interpret::{ConstValue, Scalar};
-use rustc::ty::print::{PrettyPrinter, Print, Printer};
-use rustc::ty::subst::{GenericArg, GenericArgKind};
-use rustc::ty::{self, Instance, Ty, TyCtxt, TypeFoldable};
-use rustc::util::common::record_time;
-use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
-use rustc_hir::def_id::CrateNum;
-
-use log::debug;
-
-use std::fmt::{self, Write};
-use std::mem::{self, discriminant};
-
-pub(super) fn mangle(
-    tcx: TyCtxt<'tcx>,
-    instance: Instance<'tcx>,
-    instantiating_crate: Option<CrateNum>,
-) -> String {
-    let def_id = instance.def_id();
-
-    // We want to compute the "type" of this item. Unfortunately, some
-    // kinds of items (e.g., closures) don't have an entry in the
-    // item-type array. So walk back up the find the closest parent
-    // that DOES have an entry.
-    let mut ty_def_id = def_id;
-    let instance_ty;
-    loop {
-        let key = tcx.def_key(ty_def_id);
-        match key.disambiguated_data.data {
-            DefPathData::TypeNs(_) | DefPathData::ValueNs(_) => {
-                instance_ty = tcx.type_of(ty_def_id);
-                break;
-            }
-            _ => {
-                // if we're making a symbol for something, there ought
-                // to be a value or type-def or something in there
-                // *somewhere*
-                ty_def_id.index = key.parent.unwrap_or_else(|| {
-                    bug!(
-                        "finding type for {:?}, encountered def-id {:?} with no \
-                         parent",
-                        def_id,
-                        ty_def_id
-                    );
-                });
-            }
-        }
-    }
-
-    // Erase regions because they may not be deterministic when hashed
-    // and should not matter anyhow.
-    let instance_ty = tcx.erase_regions(&instance_ty);
-
-    let hash = get_symbol_hash(tcx, instance, instance_ty, instantiating_crate);
-
-    let mut printer = SymbolPrinter { tcx, path: SymbolPath::new(), keep_within_component: false }
-        .print_def_path(def_id, &[])
-        .unwrap();
-
-    if instance.is_vtable_shim() {
-        let _ = printer.write_str("{{vtable-shim}}");
-    }
-
-    printer.path.finish(hash)
-}
-
-fn get_symbol_hash<'tcx>(
-    tcx: TyCtxt<'tcx>,
-
-    // instance this name will be for
-    instance: Instance<'tcx>,
-
-    // type of the item, without any generic
-    // parameters substituted; this is
-    // included in the hash as a kind of
-    // safeguard.
-    item_type: Ty<'tcx>,
-
-    instantiating_crate: Option<CrateNum>,
-) -> u64 {
-    let def_id = instance.def_id();
-    let substs = instance.substs;
-    debug!("get_symbol_hash(def_id={:?}, parameters={:?})", def_id, substs);
-
-    let mut hasher = StableHasher::new();
-    let mut hcx = tcx.create_stable_hashing_context();
-
-    record_time(&tcx.sess.perf_stats.symbol_hash_time, || {
-        // the main symbol name is not necessarily unique; hash in the
-        // compiler's internal def-path, guaranteeing each symbol has a
-        // truly unique path
-        tcx.def_path_hash(def_id).hash_stable(&mut hcx, &mut hasher);
-
-        // Include the main item-type. Note that, in this case, the
-        // assertions about `needs_subst` may not hold, but this item-type
-        // ought to be the same for every reference anyway.
-        assert!(!item_type.has_erasable_regions());
-        hcx.while_hashing_spans(false, |hcx| {
-            hcx.with_node_id_hashing_mode(NodeIdHashingMode::HashDefPath, |hcx| {
-                item_type.hash_stable(hcx, &mut hasher);
-            });
-        });
-
-        // If this is a function, we hash the signature as well.
-        // This is not *strictly* needed, but it may help in some
-        // situations, see the `run-make/a-b-a-linker-guard` test.
-        if let ty::FnDef(..) = item_type.kind {
-            item_type.fn_sig(tcx).hash_stable(&mut hcx, &mut hasher);
-        }
-
-        // also include any type parameters (for generic items)
-        assert!(!substs.has_erasable_regions());
-        assert!(!substs.needs_subst());
-        substs.hash_stable(&mut hcx, &mut hasher);
-
-        if let Some(instantiating_crate) = instantiating_crate {
-            tcx.original_crate_name(instantiating_crate)
-                .as_str()
-                .hash_stable(&mut hcx, &mut hasher);
-            tcx.crate_disambiguator(instantiating_crate).hash_stable(&mut hcx, &mut hasher);
-        }
-
-        // We want to avoid accidental collision between different types of instances.
-        // Especially, VtableShim may overlap with its original instance without this.
-        discriminant(&instance.def).hash_stable(&mut hcx, &mut hasher);
-    });
-
-    // 64 bits should be enough to avoid collisions.
-    hasher.finish::<u64>()
-}
-
-// Follow C++ namespace-mangling style, see
-// http://en.wikipedia.org/wiki/Name_mangling for more info.
-//
-// It turns out that on macOS you can actually have arbitrary symbols in
-// function names (at least when given to LLVM), but this is not possible
-// when using unix's linker. Perhaps one day when we just use a linker from LLVM
-// we won't need to do this name mangling. The problem with name mangling is
-// that it seriously limits the available characters. For example we can't
-// have things like &T in symbol names when one would theoretically
-// want them for things like impls of traits on that type.
-//
-// To be able to work on all platforms and get *some* reasonable output, we
-// use C++ name-mangling.
-#[derive(Debug)]
-struct SymbolPath {
-    result: String,
-    temp_buf: String,
-}
-
-impl SymbolPath {
-    fn new() -> Self {
-        let mut result =
-            SymbolPath { result: String::with_capacity(64), temp_buf: String::with_capacity(16) };
-        result.result.push_str("_ZN"); // _Z == Begin name-sequence, N == nested
-        result
-    }
-
-    fn finalize_pending_component(&mut self) {
-        if !self.temp_buf.is_empty() {
-            let _ = write!(self.result, "{}{}", self.temp_buf.len(), self.temp_buf);
-            self.temp_buf.clear();
-        }
-    }
-
-    fn finish(mut self, hash: u64) -> String {
-        self.finalize_pending_component();
-        // E = end name-sequence
-        let _ = write!(self.result, "17h{:016x}E", hash);
-        self.result
-    }
-}
-
-struct SymbolPrinter<'tcx> {
-    tcx: TyCtxt<'tcx>,
-    path: SymbolPath,
-
-    // When `true`, `finalize_pending_component` isn't used.
-    // This is needed when recursing into `path_qualified`,
-    // or `path_generic_args`, as any nested paths are
-    // logically within one component.
-    keep_within_component: bool,
-}
-
-// HACK(eddyb) this relies on using the `fmt` interface to get
-// `PrettyPrinter` aka pretty printing of e.g. types in paths,
-// symbol names should have their own printing machinery.
-
-impl Printer<'tcx> for SymbolPrinter<'tcx> {
-    type Error = fmt::Error;
-
-    type Path = Self;
-    type Region = Self;
-    type Type = Self;
-    type DynExistential = Self;
-    type Const = Self;
-
-    fn tcx(&self) -> TyCtxt<'tcx> {
-        self.tcx
-    }
-
-    fn print_region(self, _region: ty::Region<'_>) -> Result<Self::Region, Self::Error> {
-        Ok(self)
-    }
-
-    fn print_type(self, ty: Ty<'tcx>) -> Result<Self::Type, Self::Error> {
-        match ty.kind {
-            // Print all nominal types as paths (unlike `pretty_print_type`).
-            ty::FnDef(def_id, substs)
-            | ty::Opaque(def_id, substs)
-            | ty::Projection(ty::ProjectionTy { item_def_id: def_id, substs })
-            | ty::UnnormalizedProjection(ty::ProjectionTy { item_def_id: def_id, substs })
-            | ty::Closure(def_id, substs)
-            | ty::Generator(def_id, substs, _) => self.print_def_path(def_id, substs),
-            _ => self.pretty_print_type(ty),
-        }
-    }
-
-    fn print_dyn_existential(
-        mut self,
-        predicates: &'tcx ty::List<ty::ExistentialPredicate<'tcx>>,
-    ) -> Result<Self::DynExistential, Self::Error> {
-        let mut first = true;
-        for p in predicates {
-            if !first {
-                write!(self, "+")?;
-            }
-            first = false;
-            self = p.print(self)?;
-        }
-        Ok(self)
-    }
-
-    fn print_const(mut self, ct: &'tcx ty::Const<'tcx>) -> Result<Self::Const, Self::Error> {
-        // only print integers
-        if let ty::ConstKind::Value(ConstValue::Scalar(Scalar::Raw { .. })) = ct.val {
-            if ct.ty.is_integral() {
-                return self.pretty_print_const(ct, true);
-            }
-        }
-        self.write_str("_")?;
-        Ok(self)
-    }
-
-    fn path_crate(mut self, cnum: CrateNum) -> Result<Self::Path, Self::Error> {
-        self.write_str(&self.tcx.original_crate_name(cnum).as_str())?;
-        Ok(self)
-    }
-    fn path_qualified(
-        self,
-        self_ty: Ty<'tcx>,
-        trait_ref: Option<ty::TraitRef<'tcx>>,
-    ) -> Result<Self::Path, Self::Error> {
-        // Similar to `pretty_path_qualified`, but for the other
-        // types that are printed as paths (see `print_type` above).
-        match self_ty.kind {
-            ty::FnDef(..)
-            | ty::Opaque(..)
-            | ty::Projection(_)
-            | ty::UnnormalizedProjection(_)
-            | ty::Closure(..)
-            | ty::Generator(..)
-                if trait_ref.is_none() =>
-            {
-                self.print_type(self_ty)
-            }
-
-            _ => self.pretty_path_qualified(self_ty, trait_ref),
-        }
-    }
-
-    fn path_append_impl(
-        self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        _disambiguated_data: &DisambiguatedDefPathData,
-        self_ty: Ty<'tcx>,
-        trait_ref: Option<ty::TraitRef<'tcx>>,
-    ) -> Result<Self::Path, Self::Error> {
-        self.pretty_path_append_impl(
-            |mut cx| {
-                cx = print_prefix(cx)?;
-
-                if cx.keep_within_component {
-                    // HACK(eddyb) print the path similarly to how `FmtPrinter` prints it.
-                    cx.write_str("::")?;
-                } else {
-                    cx.path.finalize_pending_component();
-                }
-
-                Ok(cx)
-            },
-            self_ty,
-            trait_ref,
-        )
-    }
-    fn path_append(
-        mut self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        disambiguated_data: &DisambiguatedDefPathData,
-    ) -> Result<Self::Path, Self::Error> {
-        self = print_prefix(self)?;
-
-        // Skip `::{{constructor}}` on tuple/unit structs.
-        match disambiguated_data.data {
-            DefPathData::Ctor => return Ok(self),
-            _ => {}
-        }
-
-        if self.keep_within_component {
-            // HACK(eddyb) print the path similarly to how `FmtPrinter` prints it.
-            self.write_str("::")?;
-        } else {
-            self.path.finalize_pending_component();
-        }
-
-        self.write_str(&disambiguated_data.data.as_symbol().as_str())?;
-        Ok(self)
-    }
-    fn path_generic_args(
-        mut self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        args: &[GenericArg<'tcx>],
-    ) -> Result<Self::Path, Self::Error> {
-        self = print_prefix(self)?;
-
-        let args = args.iter().cloned().filter(|arg| match arg.unpack() {
-            GenericArgKind::Lifetime(_) => false,
-            _ => true,
-        });
-
-        if args.clone().next().is_some() {
-            self.generic_delimiters(|cx| cx.comma_sep(args))
-        } else {
-            Ok(self)
-        }
-    }
-}
-
-impl PrettyPrinter<'tcx> for SymbolPrinter<'tcx> {
-    fn region_should_not_be_omitted(&self, _region: ty::Region<'_>) -> bool {
-        false
-    }
-    fn comma_sep<T>(mut self, mut elems: impl Iterator<Item = T>) -> Result<Self, Self::Error>
-    where
-        T: Print<'tcx, Self, Output = Self, Error = Self::Error>,
-    {
-        if let Some(first) = elems.next() {
-            self = first.print(self)?;
-            for elem in elems {
-                self.write_str(",")?;
-                self = elem.print(self)?;
-            }
-        }
-        Ok(self)
-    }
-
-    fn generic_delimiters(
-        mut self,
-        f: impl FnOnce(Self) -> Result<Self, Self::Error>,
-    ) -> Result<Self, Self::Error> {
-        write!(self, "<")?;
-
-        let kept_within_component = mem::replace(&mut self.keep_within_component, true);
-        self = f(self)?;
-        self.keep_within_component = kept_within_component;
-
-        write!(self, ">")?;
-
-        Ok(self)
-    }
-}
-
-impl fmt::Write for SymbolPrinter<'_> {
-    fn write_str(&mut self, s: &str) -> fmt::Result {
-        // Name sanitation. LLVM will happily accept identifiers with weird names, but
-        // gas doesn't!
-        // gas accepts the following characters in symbols: a-z, A-Z, 0-9, ., _, $
-        // NVPTX assembly has more strict naming rules than gas, so additionally, dots
-        // are replaced with '$' there.
-
-        for c in s.chars() {
-            if self.path.temp_buf.is_empty() {
-                match c {
-                    'a'..='z' | 'A'..='Z' | '_' => {}
-                    _ => {
-                        // Underscore-qualify anything that didn't start as an ident.
-                        self.path.temp_buf.push('_');
-                    }
-                }
-            }
-            match c {
-                // Escape these with $ sequences
-                '@' => self.path.temp_buf.push_str("$SP$"),
-                '*' => self.path.temp_buf.push_str("$BP$"),
-                '&' => self.path.temp_buf.push_str("$RF$"),
-                '<' => self.path.temp_buf.push_str("$LT$"),
-                '>' => self.path.temp_buf.push_str("$GT$"),
-                '(' => self.path.temp_buf.push_str("$LP$"),
-                ')' => self.path.temp_buf.push_str("$RP$"),
-                ',' => self.path.temp_buf.push_str("$C$"),
-
-                '-' | ':' | '.' if self.tcx.has_strict_asm_symbol_naming() => {
-                    // NVPTX doesn't support these characters in symbol names.
-                    self.path.temp_buf.push('$')
-                }
-
-                // '.' doesn't occur in types and functions, so reuse it
-                // for ':' and '-'
-                '-' | ':' => self.path.temp_buf.push('.'),
-
-                // Avoid crashing LLVM in certain (LTO-related) situations, see #60925.
-                'm' if self.path.temp_buf.ends_with(".llv") => self.path.temp_buf.push_str("$u6d$"),
-
-                // These are legal symbols
-                'a'..='z' | 'A'..='Z' | '0'..='9' | '_' | '.' | '$' => self.path.temp_buf.push(c),
-
-                _ => {
-                    self.path.temp_buf.push('$');
-                    for c in c.escape_unicode().skip(1) {
-                        match c {
-                            '{' => {}
-                            '}' => self.path.temp_buf.push('$'),
-                            c => self.path.temp_buf.push(c),
-                        }
-                    }
-                }
-            }
-        }
-
-        Ok(())
-    }
-}
diff --git a/src/librustc_codegen_utils/symbol_names/v0.rs b/src/librustc_codegen_utils/symbol_names/v0.rs
deleted file mode 100644
index ce6d0d9dc5b..00000000000
--- a/src/librustc_codegen_utils/symbol_names/v0.rs
+++ /dev/null
@@ -1,641 +0,0 @@
-use rustc::hir::map::{DefPathData, DisambiguatedDefPathData};
-use rustc::ty::print::{Print, Printer};
-use rustc::ty::subst::{GenericArg, GenericArgKind, Subst};
-use rustc::ty::{self, Instance, Ty, TyCtxt, TypeFoldable};
-use rustc_ast::ast::{FloatTy, IntTy, UintTy};
-use rustc_data_structures::base_n;
-use rustc_data_structures::fx::{FxHashMap, FxHashSet};
-use rustc_hir as hir;
-use rustc_hir::def_id::{CrateNum, DefId};
-use rustc_target::spec::abi::Abi;
-
-use std::fmt::Write;
-use std::ops::Range;
-
-pub(super) fn mangle(
-    tcx: TyCtxt<'tcx>,
-    instance: Instance<'tcx>,
-    instantiating_crate: Option<CrateNum>,
-) -> String {
-    let def_id = instance.def_id();
-    // FIXME(eddyb) this should ideally not be needed.
-    let substs = tcx.normalize_erasing_regions(ty::ParamEnv::reveal_all(), instance.substs);
-
-    let prefix = "_R";
-    let mut cx = SymbolMangler {
-        tcx,
-        compress: Some(Box::new(CompressionCaches {
-            start_offset: prefix.len(),
-
-            paths: FxHashMap::default(),
-            types: FxHashMap::default(),
-            consts: FxHashMap::default(),
-        })),
-        binders: vec![],
-        out: String::from(prefix),
-    };
-    cx = if instance.is_vtable_shim() {
-        cx.path_append_ns(|cx| cx.print_def_path(def_id, substs), 'S', 0, "").unwrap()
-    } else {
-        cx.print_def_path(def_id, substs).unwrap()
-    };
-    if let Some(instantiating_crate) = instantiating_crate {
-        cx = cx.print_def_path(instantiating_crate.as_def_id(), &[]).unwrap();
-    }
-    cx.out
-}
-
-struct CompressionCaches<'tcx> {
-    // The length of the prefix in `out` (e.g. 2 for `_R`).
-    start_offset: usize,
-
-    // The values are start positions in `out`, in bytes.
-    paths: FxHashMap<(DefId, &'tcx [GenericArg<'tcx>]), usize>,
-    types: FxHashMap<Ty<'tcx>, usize>,
-    consts: FxHashMap<&'tcx ty::Const<'tcx>, usize>,
-}
-
-struct BinderLevel {
-    /// The range of distances from the root of what's
-    /// being printed, to the lifetimes in a binder.
-    /// Specifically, a `BrAnon(i)` lifetime has depth
-    /// `lifetime_depths.start + i`, going away from the
-    /// the root and towards its use site, as `i` increases.
-    /// This is used to flatten rustc's pairing of `BrAnon`
-    /// (intra-binder disambiguation) with a `DebruijnIndex`
-    /// (binder addressing), to "true" de Bruijn indices,
-    /// by subtracting the depth of a certain lifetime, from
-    /// the innermost depth at its use site.
-    lifetime_depths: Range<u32>,
-}
-
-struct SymbolMangler<'tcx> {
-    tcx: TyCtxt<'tcx>,
-    compress: Option<Box<CompressionCaches<'tcx>>>,
-    binders: Vec<BinderLevel>,
-    out: String,
-}
-
-impl SymbolMangler<'tcx> {
-    fn push(&mut self, s: &str) {
-        self.out.push_str(s);
-    }
-
-    /// Push a `_`-terminated base 62 integer, using the format
-    /// specified in the RFC as `<base-62-number>`, that is:
-    /// * `x = 0` is encoded as just the `"_"` terminator
-    /// * `x > 0` is encoded as `x - 1` in base 62, followed by `"_"`,
-    ///   e.g. `1` becomes `"0_"`, `62` becomes `"Z_"`, etc.
-    fn push_integer_62(&mut self, x: u64) {
-        if let Some(x) = x.checked_sub(1) {
-            base_n::push_str(x as u128, 62, &mut self.out);
-        }
-        self.push("_");
-    }
-
-    /// Push a `tag`-prefixed base 62 integer, when larger than `0`, that is:
-    /// * `x = 0` is encoded as `""` (nothing)
-    /// * `x > 0` is encoded as the `tag` followed by `push_integer_62(x - 1)`
-    ///   e.g. `1` becomes `tag + "_"`, `2` becomes `tag + "0_"`, etc.
-    fn push_opt_integer_62(&mut self, tag: &str, x: u64) {
-        if let Some(x) = x.checked_sub(1) {
-            self.push(tag);
-            self.push_integer_62(x);
-        }
-    }
-
-    fn push_disambiguator(&mut self, dis: u64) {
-        self.push_opt_integer_62("s", dis);
-    }
-
-    fn push_ident(&mut self, ident: &str) {
-        let mut use_punycode = false;
-        for b in ident.bytes() {
-            match b {
-                b'_' | b'a'..=b'z' | b'A'..=b'Z' | b'0'..=b'9' => {}
-                0x80..=0xff => use_punycode = true,
-                _ => bug!("symbol_names: bad byte {} in ident {:?}", b, ident),
-            }
-        }
-
-        let punycode_string;
-        let ident = if use_punycode {
-            self.push("u");
-
-            // FIXME(eddyb) we should probably roll our own punycode implementation.
-            let mut punycode_bytes = match ::punycode::encode(ident) {
-                Ok(s) => s.into_bytes(),
-                Err(()) => bug!("symbol_names: punycode encoding failed for ident {:?}", ident),
-            };
-
-            // Replace `-` with `_`.
-            if let Some(c) = punycode_bytes.iter_mut().rfind(|&&mut c| c == b'-') {
-                *c = b'_';
-            }
-
-            // FIXME(eddyb) avoid rechecking UTF-8 validity.
-            punycode_string = String::from_utf8(punycode_bytes).unwrap();
-            &punycode_string
-        } else {
-            ident
-        };
-
-        let _ = write!(self.out, "{}", ident.len());
-
-        // Write a separating `_` if necessary (leading digit or `_`).
-        match ident.chars().next() {
-            Some('_') | Some('0'..='9') => {
-                self.push("_");
-            }
-            _ => {}
-        }
-
-        self.push(ident);
-    }
-
-    fn path_append_ns(
-        mut self,
-        print_prefix: impl FnOnce(Self) -> Result<Self, !>,
-        ns: char,
-        disambiguator: u64,
-        name: &str,
-    ) -> Result<Self, !> {
-        self.push("N");
-        self.out.push(ns);
-        self = print_prefix(self)?;
-        self.push_disambiguator(disambiguator as u64);
-        self.push_ident(name);
-        Ok(self)
-    }
-
-    fn print_backref(mut self, i: usize) -> Result<Self, !> {
-        self.push("B");
-        self.push_integer_62((i - self.compress.as_ref().unwrap().start_offset) as u64);
-        Ok(self)
-    }
-
-    fn in_binder<T>(
-        mut self,
-        value: &ty::Binder<T>,
-        print_value: impl FnOnce(Self, &T) -> Result<Self, !>,
-    ) -> Result<Self, !>
-    where
-        T: TypeFoldable<'tcx>,
-    {
-        let regions = if value.has_late_bound_regions() {
-            self.tcx.collect_referenced_late_bound_regions(value)
-        } else {
-            FxHashSet::default()
-        };
-
-        let mut lifetime_depths =
-            self.binders.last().map(|b| b.lifetime_depths.end).map_or(0..0, |i| i..i);
-
-        let lifetimes = regions
-            .into_iter()
-            .map(|br| {
-                match br {
-                    ty::BrAnon(i) => {
-                        // FIXME(eddyb) for some reason, `anonymize_late_bound_regions` starts at `1`.
-                        assert_ne!(i, 0);
-                        i - 1
-                    }
-                    _ => bug!("symbol_names: non-anonymized region `{:?}` in `{:?}`", br, value),
-                }
-            })
-            .max()
-            .map_or(0, |max| max + 1);
-
-        self.push_opt_integer_62("G", lifetimes as u64);
-        lifetime_depths.end += lifetimes;
-
-        self.binders.push(BinderLevel { lifetime_depths });
-        self = print_value(self, value.skip_binder())?;
-        self.binders.pop();
-
-        Ok(self)
-    }
-}
-
-impl Printer<'tcx> for SymbolMangler<'tcx> {
-    type Error = !;
-
-    type Path = Self;
-    type Region = Self;
-    type Type = Self;
-    type DynExistential = Self;
-    type Const = Self;
-
-    fn tcx(&self) -> TyCtxt<'tcx> {
-        self.tcx
-    }
-
-    fn print_def_path(
-        mut self,
-        def_id: DefId,
-        substs: &'tcx [GenericArg<'tcx>],
-    ) -> Result<Self::Path, Self::Error> {
-        if let Some(&i) = self.compress.as_ref().and_then(|c| c.paths.get(&(def_id, substs))) {
-            return self.print_backref(i);
-        }
-        let start = self.out.len();
-
-        self = self.default_print_def_path(def_id, substs)?;
-
-        // Only cache paths that do not refer to an enclosing
-        // binder (which would change depending on context).
-        if !substs.iter().any(|k| k.has_escaping_bound_vars()) {
-            if let Some(c) = &mut self.compress {
-                c.paths.insert((def_id, substs), start);
-            }
-        }
-        Ok(self)
-    }
-
-    fn print_impl_path(
-        self,
-        impl_def_id: DefId,
-        substs: &'tcx [GenericArg<'tcx>],
-        mut self_ty: Ty<'tcx>,
-        mut impl_trait_ref: Option<ty::TraitRef<'tcx>>,
-    ) -> Result<Self::Path, Self::Error> {
-        let key = self.tcx.def_key(impl_def_id);
-        let parent_def_id = DefId { index: key.parent.unwrap(), ..impl_def_id };
-
-        let mut param_env = self.tcx.param_env(impl_def_id).with_reveal_all();
-        if !substs.is_empty() {
-            param_env = param_env.subst(self.tcx, substs);
-        }
-
-        match &mut impl_trait_ref {
-            Some(impl_trait_ref) => {
-                assert_eq!(impl_trait_ref.self_ty(), self_ty);
-                *impl_trait_ref = self.tcx.normalize_erasing_regions(param_env, *impl_trait_ref);
-                self_ty = impl_trait_ref.self_ty();
-            }
-            None => {
-                self_ty = self.tcx.normalize_erasing_regions(param_env, self_ty);
-            }
-        }
-
-        self.path_append_impl(
-            |cx| cx.print_def_path(parent_def_id, &[]),
-            &key.disambiguated_data,
-            self_ty,
-            impl_trait_ref,
-        )
-    }
-
-    fn print_region(mut self, region: ty::Region<'_>) -> Result<Self::Region, Self::Error> {
-        let i = match *region {
-            // Erased lifetimes use the index 0, for a
-            // shorter mangling of `L_`.
-            ty::ReErased => 0,
-
-            // Late-bound lifetimes use indices starting at 1,
-            // see `BinderLevel` for more details.
-            ty::ReLateBound(debruijn, ty::BrAnon(i)) => {
-                // FIXME(eddyb) for some reason, `anonymize_late_bound_regions` starts at `1`.
-                assert_ne!(i, 0);
-                let i = i - 1;
-
-                let binder = &self.binders[self.binders.len() - 1 - debruijn.index()];
-                let depth = binder.lifetime_depths.start + i;
-
-                1 + (self.binders.last().unwrap().lifetime_depths.end - 1 - depth)
-            }
-
-            _ => bug!("symbol_names: non-erased region `{:?}`", region),
-        };
-        self.push("L");
-        self.push_integer_62(i as u64);
-        Ok(self)
-    }
-
-    fn print_type(mut self, ty: Ty<'tcx>) -> Result<Self::Type, Self::Error> {
-        // Basic types, never cached (single-character).
-        let basic_type = match ty.kind {
-            ty::Bool => "b",
-            ty::Char => "c",
-            ty::Str => "e",
-            ty::Tuple(_) if ty.is_unit() => "u",
-            ty::Int(IntTy::I8) => "a",
-            ty::Int(IntTy::I16) => "s",
-            ty::Int(IntTy::I32) => "l",
-            ty::Int(IntTy::I64) => "x",
-            ty::Int(IntTy::I128) => "n",
-            ty::Int(IntTy::Isize) => "i",
-            ty::Uint(UintTy::U8) => "h",
-            ty::Uint(UintTy::U16) => "t",
-            ty::Uint(UintTy::U32) => "m",
-            ty::Uint(UintTy::U64) => "y",
-            ty::Uint(UintTy::U128) => "o",
-            ty::Uint(UintTy::Usize) => "j",
-            ty::Float(FloatTy::F32) => "f",
-            ty::Float(FloatTy::F64) => "d",
-            ty::Never => "z",
-
-            // Placeholders (should be demangled as `_`).
-            ty::Param(_) | ty::Bound(..) | ty::Placeholder(_) | ty::Infer(_) | ty::Error => "p",
-
-            _ => "",
-        };
-        if !basic_type.is_empty() {
-            self.push(basic_type);
-            return Ok(self);
-        }
-
-        if let Some(&i) = self.compress.as_ref().and_then(|c| c.types.get(&ty)) {
-            return self.print_backref(i);
-        }
-        let start = self.out.len();
-
-        match ty.kind {
-            // Basic types, handled above.
-            ty::Bool | ty::Char | ty::Str | ty::Int(_) | ty::Uint(_) | ty::Float(_) | ty::Never => {
-                unreachable!()
-            }
-            ty::Tuple(_) if ty.is_unit() => unreachable!(),
-
-            // Placeholders, also handled as part of basic types.
-            ty::Param(_) | ty::Bound(..) | ty::Placeholder(_) | ty::Infer(_) | ty::Error => {
-                unreachable!()
-            }
-
-            ty::Ref(r, ty, mutbl) => {
-                self.push(match mutbl {
-                    hir::Mutability::Not => "R",
-                    hir::Mutability::Mut => "Q",
-                });
-                if *r != ty::ReErased {
-                    self = r.print(self)?;
-                }
-                self = ty.print(self)?;
-            }
-
-            ty::RawPtr(mt) => {
-                self.push(match mt.mutbl {
-                    hir::Mutability::Not => "P",
-                    hir::Mutability::Mut => "O",
-                });
-                self = mt.ty.print(self)?;
-            }
-
-            ty::Array(ty, len) => {
-                self.push("A");
-                self = ty.print(self)?;
-                self = self.print_const(len)?;
-            }
-            ty::Slice(ty) => {
-                self.push("S");
-                self = ty.print(self)?;
-            }
-
-            ty::Tuple(tys) => {
-                self.push("T");
-                for ty in tys.iter().map(|k| k.expect_ty()) {
-                    self = ty.print(self)?;
-                }
-                self.push("E");
-            }
-
-            // Mangle all nominal types as paths.
-            ty::Adt(&ty::AdtDef { did: def_id, .. }, substs)
-            | ty::FnDef(def_id, substs)
-            | ty::Opaque(def_id, substs)
-            | ty::Projection(ty::ProjectionTy { item_def_id: def_id, substs })
-            | ty::UnnormalizedProjection(ty::ProjectionTy { item_def_id: def_id, substs })
-            | ty::Closure(def_id, substs)
-            | ty::Generator(def_id, substs, _) => {
-                self = self.print_def_path(def_id, substs)?;
-            }
-            ty::Foreign(def_id) => {
-                self = self.print_def_path(def_id, &[])?;
-            }
-
-            ty::FnPtr(sig) => {
-                self.push("F");
-                self = self.in_binder(&sig, |mut cx, sig| {
-                    if sig.unsafety == hir::Unsafety::Unsafe {
-                        cx.push("U");
-                    }
-                    match sig.abi {
-                        Abi::Rust => {}
-                        Abi::C => cx.push("KC"),
-                        abi => {
-                            cx.push("K");
-                            let name = abi.name();
-                            if name.contains('-') {
-                                cx.push_ident(&name.replace('-', "_"));
-                            } else {
-                                cx.push_ident(name);
-                            }
-                        }
-                    }
-                    for &ty in sig.inputs() {
-                        cx = ty.print(cx)?;
-                    }
-                    if sig.c_variadic {
-                        cx.push("v");
-                    }
-                    cx.push("E");
-                    sig.output().print(cx)
-                })?;
-            }
-
-            ty::Dynamic(predicates, r) => {
-                self.push("D");
-                self = self.in_binder(&predicates, |cx, predicates| {
-                    cx.print_dyn_existential(predicates)
-                })?;
-                self = r.print(self)?;
-            }
-
-            ty::GeneratorWitness(_) => bug!("symbol_names: unexpected `GeneratorWitness`"),
-        }
-
-        // Only cache types that do not refer to an enclosing
-        // binder (which would change depending on context).
-        if !ty.has_escaping_bound_vars() {
-            if let Some(c) = &mut self.compress {
-                c.types.insert(ty, start);
-            }
-        }
-        Ok(self)
-    }
-
-    fn print_dyn_existential(
-        mut self,
-        predicates: &'tcx ty::List<ty::ExistentialPredicate<'tcx>>,
-    ) -> Result<Self::DynExistential, Self::Error> {
-        for predicate in predicates {
-            match *predicate {
-                ty::ExistentialPredicate::Trait(trait_ref) => {
-                    // Use a type that can't appear in defaults of type parameters.
-                    let dummy_self = self.tcx.mk_ty_infer(ty::FreshTy(0));
-                    let trait_ref = trait_ref.with_self_ty(self.tcx, dummy_self);
-                    self = self.print_def_path(trait_ref.def_id, trait_ref.substs)?;
-                }
-                ty::ExistentialPredicate::Projection(projection) => {
-                    let name = self.tcx.associated_item(projection.item_def_id).ident;
-                    self.push("p");
-                    self.push_ident(&name.as_str());
-                    self = projection.ty.print(self)?;
-                }
-                ty::ExistentialPredicate::AutoTrait(def_id) => {
-                    self = self.print_def_path(def_id, &[])?;
-                }
-            }
-        }
-        self.push("E");
-        Ok(self)
-    }
-
-    fn print_const(mut self, ct: &'tcx ty::Const<'tcx>) -> Result<Self::Const, Self::Error> {
-        if let Some(&i) = self.compress.as_ref().and_then(|c| c.consts.get(&ct)) {
-            return self.print_backref(i);
-        }
-        let start = self.out.len();
-
-        match ct.ty.kind {
-            ty::Uint(_) => {}
-            _ => {
-                bug!("symbol_names: unsupported constant of type `{}` ({:?})", ct.ty, ct);
-            }
-        }
-        self = ct.ty.print(self)?;
-
-        if let Some(bits) = ct.try_eval_bits(self.tcx, ty::ParamEnv::reveal_all(), ct.ty) {
-            let _ = write!(self.out, "{:x}_", bits);
-        } else {
-            // NOTE(eddyb) despite having the path, we need to
-            // encode a placeholder, as the path could refer
-            // back to e.g. an `impl` using the constant.
-            self.push("p");
-        }
-
-        // Only cache consts that do not refer to an enclosing
-        // binder (which would change depending on context).
-        if !ct.has_escaping_bound_vars() {
-            if let Some(c) = &mut self.compress {
-                c.consts.insert(ct, start);
-            }
-        }
-        Ok(self)
-    }
-
-    fn path_crate(mut self, cnum: CrateNum) -> Result<Self::Path, Self::Error> {
-        self.push("C");
-        let fingerprint = self.tcx.crate_disambiguator(cnum).to_fingerprint();
-        self.push_disambiguator(fingerprint.to_smaller_hash());
-        let name = self.tcx.original_crate_name(cnum).as_str();
-        self.push_ident(&name);
-        Ok(self)
-    }
-    fn path_qualified(
-        mut self,
-        self_ty: Ty<'tcx>,
-        trait_ref: Option<ty::TraitRef<'tcx>>,
-    ) -> Result<Self::Path, Self::Error> {
-        assert!(trait_ref.is_some());
-        let trait_ref = trait_ref.unwrap();
-
-        self.push("Y");
-        self = self_ty.print(self)?;
-        self.print_def_path(trait_ref.def_id, trait_ref.substs)
-    }
-
-    fn path_append_impl(
-        mut self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        disambiguated_data: &DisambiguatedDefPathData,
-        self_ty: Ty<'tcx>,
-        trait_ref: Option<ty::TraitRef<'tcx>>,
-    ) -> Result<Self::Path, Self::Error> {
-        self.push(match trait_ref {
-            Some(_) => "X",
-            None => "M",
-        });
-        self.push_disambiguator(disambiguated_data.disambiguator as u64);
-        self = print_prefix(self)?;
-        self = self_ty.print(self)?;
-        if let Some(trait_ref) = trait_ref {
-            self = self.print_def_path(trait_ref.def_id, trait_ref.substs)?;
-        }
-        Ok(self)
-    }
-    fn path_append(
-        self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        disambiguated_data: &DisambiguatedDefPathData,
-    ) -> Result<Self::Path, Self::Error> {
-        let ns = match disambiguated_data.data {
-            // Uppercase categories are more stable than lowercase ones.
-            DefPathData::TypeNs(_) => 't',
-            DefPathData::ValueNs(_) => 'v',
-            DefPathData::ClosureExpr => 'C',
-            DefPathData::Ctor => 'c',
-            DefPathData::AnonConst => 'k',
-            DefPathData::ImplTrait => 'i',
-
-            // These should never show up as `path_append` arguments.
-            DefPathData::CrateRoot
-            | DefPathData::Misc
-            | DefPathData::Impl
-            | DefPathData::MacroNs(_)
-            | DefPathData::LifetimeNs(_) => {
-                bug!("symbol_names: unexpected DefPathData: {:?}", disambiguated_data.data)
-            }
-        };
-
-        let name = disambiguated_data.data.get_opt_name().map(|s| s.as_str());
-
-        self.path_append_ns(
-            print_prefix,
-            ns,
-            disambiguated_data.disambiguator as u64,
-            name.as_ref().map_or("", |s| &s[..]),
-        )
-    }
-    fn path_generic_args(
-        mut self,
-        print_prefix: impl FnOnce(Self) -> Result<Self::Path, Self::Error>,
-        args: &[GenericArg<'tcx>],
-    ) -> Result<Self::Path, Self::Error> {
-        // Don't print any regions if they're all erased.
-        let print_regions = args.iter().any(|arg| match arg.unpack() {
-            GenericArgKind::Lifetime(r) => *r != ty::ReErased,
-            _ => false,
-        });
-        let args = args.iter().cloned().filter(|arg| match arg.unpack() {
-            GenericArgKind::Lifetime(_) => print_regions,
-            _ => true,
-        });
-
-        if args.clone().next().is_none() {
-            return print_prefix(self);
-        }
-
-        self.push("I");
-        self = print_prefix(self)?;
-        for arg in args {
-            match arg.unpack() {
-                GenericArgKind::Lifetime(lt) => {
-                    self = lt.print(self)?;
-                }
-                GenericArgKind::Type(ty) => {
-                    self = ty.print(self)?;
-                }
-                GenericArgKind::Const(c) => {
-                    self.push("K");
-                    // FIXME(const_generics) implement `ty::print::Print` on `ty::Const`.
-                    // self = c.print(self)?;
-                    self = self.print_const(c)?;
-                }
-            }
-        }
-        self.push("E");
-
-        Ok(self)
-    }
-}
diff --git a/src/librustc_codegen_utils/symbol_names_test.rs b/src/librustc_codegen_utils/symbol_names_test.rs
deleted file mode 100644
index 8f2f2628e7b..00000000000
--- a/src/librustc_codegen_utils/symbol_names_test.rs
+++ /dev/null
@@ -1,70 +0,0 @@
-//! Walks the crate looking for items/impl-items/trait-items that have
-//! either a `rustc_symbol_name` or `rustc_def_path` attribute and
-//! generates an error giving, respectively, the symbol name or
-//! def-path. This is used for unit testing the code that generates
-//! paths etc in all kinds of annoying scenarios.
-
-use rustc::ty::{Instance, TyCtxt};
-use rustc_hir as hir;
-use rustc_span::symbol::{sym, Symbol};
-
-const SYMBOL_NAME: Symbol = sym::rustc_symbol_name;
-const DEF_PATH: Symbol = sym::rustc_def_path;
-
-pub fn report_symbol_names(tcx: TyCtxt<'_>) {
-    // if the `rustc_attrs` feature is not enabled, then the
-    // attributes we are interested in cannot be present anyway, so
-    // skip the walk.
-    if !tcx.features().rustc_attrs {
-        return;
-    }
-
-    tcx.dep_graph.with_ignore(|| {
-        let mut visitor = SymbolNamesTest { tcx };
-        tcx.hir().krate().visit_all_item_likes(&mut visitor);
-    })
-}
-
-struct SymbolNamesTest<'tcx> {
-    tcx: TyCtxt<'tcx>,
-}
-
-impl SymbolNamesTest<'tcx> {
-    fn process_attrs(&mut self, hir_id: hir::HirId) {
-        let tcx = self.tcx;
-        let def_id = tcx.hir().local_def_id(hir_id);
-        for attr in tcx.get_attrs(def_id).iter() {
-            if attr.check_name(SYMBOL_NAME) {
-                // for now, can only use on monomorphic names
-                let instance = Instance::mono(tcx, def_id);
-                let mangled = self.tcx.symbol_name(instance);
-                tcx.sess.span_err(attr.span, &format!("symbol-name({})", mangled));
-                if let Ok(demangling) = rustc_demangle::try_demangle(&mangled.name.as_str()) {
-                    tcx.sess.span_err(attr.span, &format!("demangling({})", demangling));
-                    tcx.sess.span_err(attr.span, &format!("demangling-alt({:#})", demangling));
-                }
-            } else if attr.check_name(DEF_PATH) {
-                let path = tcx.def_path_str(def_id);
-                tcx.sess.span_err(attr.span, &format!("def-path({})", path));
-            }
-
-            // (*) The formatting of `tag({})` is chosen so that tests can elect
-            // to test the entirety of the string, if they choose, or else just
-            // some subset.
-        }
-    }
-}
-
-impl hir::itemlikevisit::ItemLikeVisitor<'tcx> for SymbolNamesTest<'tcx> {
-    fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) {
-        self.process_attrs(item.hir_id);
-    }
-
-    fn visit_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>) {
-        self.process_attrs(trait_item.hir_id);
-    }
-
-    fn visit_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>) {
-        self.process_attrs(impl_item.hir_id);
-    }
-}