diff --git a/src/librustc_codegen_llvm/callee.rs b/src/librustc_codegen_llvm/callee.rs index 6ad75cff3ddb6..7b341651adf3d 100644 --- a/src/librustc_codegen_llvm/callee.rs +++ b/src/librustc_codegen_llvm/callee.rs @@ -35,7 +35,7 @@ pub fn get_fn(cx: &CodegenCx<'ll, 'tcx>, instance: Instance<'tcx>) -> &'ll Value return llfn; } - let sym = tcx.symbol_name(instance).name.as_str(); + let sym = tcx.symbol_name(instance).name; debug!("get_fn({:?}: {:?}) => {}", instance, instance.monomorphic_ty(cx.tcx()), sym); let fn_abi = FnAbi::of_instance(cx, instance, &[]); diff --git a/src/librustc_codegen_llvm/consts.rs b/src/librustc_codegen_llvm/consts.rs index 9d9b53fc4a87c..90887b760fb7d 100644 --- a/src/librustc_codegen_llvm/consts.rs +++ b/src/librustc_codegen_llvm/consts.rs @@ -18,7 +18,7 @@ use rustc_middle::mir::interpret::{ use rustc_middle::mir::mono::MonoItem; use rustc_middle::ty::{self, Instance, Ty}; use rustc_middle::{bug, span_bug}; -use rustc_span::symbol::{sym, Symbol}; +use rustc_span::symbol::sym; use rustc_span::Span; use rustc_target::abi::{Align, HasDataLayout, LayoutOf, Primitive, Scalar, Size}; @@ -107,11 +107,10 @@ fn check_and_apply_linkage( cx: &CodegenCx<'ll, 'tcx>, attrs: &CodegenFnAttrs, ty: Ty<'tcx>, - sym: Symbol, + sym: &str, span: Span, ) -> &'ll Value { let llty = cx.layout_of(ty).llvm_type(cx); - let sym = sym.as_str(); if let Some(linkage) = attrs.linkage { debug!("get_static: sym={} linkage={:?}", sym, linkage); @@ -215,14 +214,13 @@ impl CodegenCx<'ll, 'tcx> { // FIXME: refactor this to work without accessing the HIR let (g, attrs) = match self.tcx.hir().get(id) { Node::Item(&hir::Item { attrs, span, kind: hir::ItemKind::Static(..), .. }) => { - let sym_str = sym.as_str(); - if let Some(g) = self.get_declared_value(&sym_str) { + if let Some(g) = self.get_declared_value(sym) { if self.val_ty(g) != self.type_ptr_to(llty) { span_bug!(span, "Conflicting types for static"); } } - let g = self.declare_global(&sym_str, llty); + let g = self.declare_global(sym, llty); if !self.tcx.is_reachable_non_generic(def_id) { unsafe { diff --git a/src/librustc_codegen_llvm/debuginfo/metadata.rs b/src/librustc_codegen_llvm/debuginfo/metadata.rs index f2e042cf86aa5..ef9d42968ae2e 100644 --- a/src/librustc_codegen_llvm/debuginfo/metadata.rs +++ b/src/librustc_codegen_llvm/debuginfo/metadata.rs @@ -2468,8 +2468,7 @@ pub fn create_global_var_metadata(cx: &CodegenCx<'ll, '_>, def_id: DefId, global let variable_type = Instance::mono(cx.tcx, def_id).monomorphic_ty(cx.tcx); let type_metadata = type_metadata(cx, variable_type, span); let var_name = tcx.item_name(def_id).as_str(); - let linkage_name: &str = - &mangled_name_of_instance(cx, Instance::mono(tcx, def_id)).name.as_str(); + let linkage_name = mangled_name_of_instance(cx, Instance::mono(tcx, def_id)).name; // When empty, linkage_name field is omitted, // which is what we want for no_mangle statics let linkage_name = if var_name == linkage_name { "" } else { linkage_name }; diff --git a/src/librustc_codegen_llvm/debuginfo/mod.rs b/src/librustc_codegen_llvm/debuginfo/mod.rs index b5434298805f3..44993d7602fe6 100644 --- a/src/librustc_codegen_llvm/debuginfo/mod.rs +++ b/src/librustc_codegen_llvm/debuginfo/mod.rs @@ -267,7 +267,7 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> { let substs = instance.substs.truncate_to(self.tcx(), generics); let template_parameters = get_template_parameters(self, &generics, substs, &mut name); - let linkage_name: &str = &mangled_name_of_instance(self, instance).name.as_str(); + let linkage_name = &mangled_name_of_instance(self, instance).name; // Omit the linkage_name if it is the same as subprogram name. let linkage_name = if &name == linkage_name { "" } else { linkage_name }; diff --git a/src/librustc_codegen_llvm/debuginfo/namespace.rs b/src/librustc_codegen_llvm/debuginfo/namespace.rs index 475dea239a765..d1a55335c44e7 100644 --- a/src/librustc_codegen_llvm/debuginfo/namespace.rs +++ b/src/librustc_codegen_llvm/debuginfo/namespace.rs @@ -12,7 +12,7 @@ use rustc_hir::definitions::DefPathData; pub fn mangled_name_of_instance<'a, 'tcx>( cx: &CodegenCx<'a, 'tcx>, instance: Instance<'tcx>, -) -> ty::SymbolName { +) -> ty::SymbolName<'tcx> { let tcx = cx.tcx; tcx.symbol_name(instance) } diff --git a/src/librustc_codegen_llvm/intrinsic.rs b/src/librustc_codegen_llvm/intrinsic.rs index 153f0232f3a6c..d095587a1e8cb 100644 --- a/src/librustc_codegen_llvm/intrinsic.rs +++ b/src/librustc_codegen_llvm/intrinsic.rs @@ -196,7 +196,7 @@ impl IntrinsicCallMethods<'tcx> for Builder<'a, 'll, 'tcx> { // and/or monomorphization invalidates these assumptions. let coverageinfo = tcx.coverageinfo(caller_instance.def_id()); let mangled_fn = tcx.symbol_name(caller_instance); - let (mangled_fn_name, _len_val) = self.const_str(mangled_fn.name); + let (mangled_fn_name, _len_val) = self.const_str(Symbol::intern(mangled_fn.name)); let hash = self.const_u64(coverageinfo.hash); let num_counters = self.const_u32(coverageinfo.num_counters); use coverage::count_code_region_args::*; diff --git a/src/librustc_codegen_ssa/back/symbol_export.rs b/src/librustc_codegen_ssa/back/symbol_export.rs index faf6809f35b1c..e0910c693b132 100644 --- a/src/librustc_codegen_ssa/back/symbol_export.rs +++ b/src/librustc_codegen_ssa/back/symbol_export.rs @@ -16,7 +16,6 @@ use rustc_middle::ty::subst::{GenericArgKind, SubstsRef}; use rustc_middle::ty::Instance; use rustc_middle::ty::{SymbolName, TyCtxt}; use rustc_session::config::{CrateType, SanitizerSet}; -use rustc_span::symbol::sym; pub fn threshold(tcx: TyCtxt<'_>) -> SymbolExportLevel { crates_export_threshold(&tcx.sess.crate_types()) @@ -117,9 +116,9 @@ fn reachable_non_generics_provider(tcx: TyCtxt<'_>, cnum: CrateNum) -> DefIdMap< // In general though we won't link right if these // symbols are stripped, and LTO currently strips them. match name { - sym::rust_eh_personality - | sym::rust_eh_register_frames - | sym::rust_eh_unregister_frames => + "rust_eh_personality" + | "rust_eh_register_frames" + | "rust_eh_unregister_frames" => SymbolExportLevel::C, _ => SymbolExportLevel::Rust, } @@ -177,7 +176,7 @@ fn exported_symbols_provider_local( .collect(); if tcx.entry_fn(LOCAL_CRATE).is_some() { - let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new("main")); + let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, "main")); symbols.push((exported_symbol, SymbolExportLevel::C)); } @@ -185,7 +184,7 @@ fn exported_symbols_provider_local( if tcx.allocator_kind().is_some() { for method in ALLOCATOR_METHODS { let symbol_name = format!("__rust_{}", method.name); - let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(&symbol_name)); + let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, &symbol_name)); symbols.push((exported_symbol, SymbolExportLevel::Rust)); } @@ -199,7 +198,7 @@ fn exported_symbols_provider_local( ["__llvm_profile_raw_version", "__llvm_profile_filename"]; symbols.extend(PROFILER_WEAK_SYMBOLS.iter().map(|sym| { - let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(sym)); + let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, sym)); (exported_symbol, SymbolExportLevel::C) })); } @@ -209,14 +208,14 @@ fn exported_symbols_provider_local( const MSAN_WEAK_SYMBOLS: [&str; 2] = ["__msan_track_origins", "__msan_keep_going"]; symbols.extend(MSAN_WEAK_SYMBOLS.iter().map(|sym| { - let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(sym)); + let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, sym)); (exported_symbol, SymbolExportLevel::C) })); } if tcx.sess.crate_types().contains(&CrateType::Dylib) { let symbol_name = metadata_symbol_name(tcx); - let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(&symbol_name)); + let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, &symbol_name)); symbols.push((exported_symbol, SymbolExportLevel::Rust)); } diff --git a/src/librustc_codegen_ssa/mono_item.rs b/src/librustc_codegen_ssa/mono_item.rs index 5994ef2be5467..fc65149937ffe 100644 --- a/src/librustc_codegen_ssa/mono_item.rs +++ b/src/librustc_codegen_ssa/mono_item.rs @@ -64,7 +64,7 @@ impl<'a, 'tcx: 'a> MonoItemExt<'a, 'tcx> for MonoItem<'tcx> { cx.codegen_unit().name() ); - let symbol_name = self.symbol_name(cx.tcx()).name.as_str(); + let symbol_name = self.symbol_name(cx.tcx()).name; debug!("symbol {}", &symbol_name); diff --git a/src/librustc_metadata/rmeta/encoder.rs b/src/librustc_metadata/rmeta/encoder.rs index fb4fee402abfb..5f44bcc1b5409 100644 --- a/src/librustc_metadata/rmeta/encoder.rs +++ b/src/librustc_metadata/rmeta/encoder.rs @@ -558,7 +558,7 @@ impl<'tcx> EncodeContext<'tcx> { // Encode exported symbols info. This is prefetched in `encode_metadata` so we encode // this late to give the prefetching as much time as possible to complete. i = self.position(); - let exported_symbols = self.tcx.exported_symbols(LOCAL_CRATE); + let exported_symbols = tcx.exported_symbols(LOCAL_CRATE); let exported_symbols = self.encode_exported_symbols(&exported_symbols); let exported_symbols_bytes = self.position() - i; @@ -622,7 +622,7 @@ impl<'tcx> EncodeContext<'tcx> { let total_bytes = self.position(); - if self.tcx.sess.meta_stats() { + if tcx.sess.meta_stats() { let mut zero_bytes = 0; for e in self.opaque.data.iter() { if *e == 0 { @@ -1541,7 +1541,7 @@ impl EncodeContext<'tcx> { ) -> Lazy<[(ExportedSymbol<'tcx>, SymbolExportLevel)]> { // The metadata symbol name is special. It should not show up in // downstream crates. - let metadata_symbol_name = SymbolName::new(&metadata_symbol_name(self.tcx)); + let metadata_symbol_name = SymbolName::new(self.tcx, &metadata_symbol_name(self.tcx)); self.lazy( exported_symbols diff --git a/src/librustc_middle/middle/exported_symbols.rs b/src/librustc_middle/middle/exported_symbols.rs index 1f4318fa53751..569af70c5b5fc 100644 --- a/src/librustc_middle/middle/exported_symbols.rs +++ b/src/librustc_middle/middle/exported_symbols.rs @@ -26,13 +26,13 @@ pub enum ExportedSymbol<'tcx> { NonGeneric(DefId), Generic(DefId, SubstsRef<'tcx>), DropGlue(Ty<'tcx>), - NoDefId(ty::SymbolName), + NoDefId(ty::SymbolName<'tcx>), } impl<'tcx> ExportedSymbol<'tcx> { /// This is the symbol name of an instance if it is instantiated in the /// local crate. - pub fn symbol_name_for_local_instance(&self, tcx: TyCtxt<'tcx>) -> ty::SymbolName { + pub fn symbol_name_for_local_instance(&self, tcx: TyCtxt<'tcx>) -> ty::SymbolName<'tcx> { match *self { ExportedSymbol::NonGeneric(def_id) => tcx.symbol_name(ty::Instance::mono(tcx, def_id)), ExportedSymbol::Generic(def_id, substs) => { diff --git a/src/librustc_middle/mir/mono.rs b/src/librustc_middle/mir/mono.rs index c9e5a196f9179..474552d68b923 100644 --- a/src/librustc_middle/mir/mono.rs +++ b/src/librustc_middle/mir/mono.rs @@ -68,13 +68,13 @@ impl<'tcx> MonoItem<'tcx> { } } - pub fn symbol_name(&self, tcx: TyCtxt<'tcx>) -> SymbolName { + pub fn symbol_name(&self, tcx: TyCtxt<'tcx>) -> SymbolName<'tcx> { match *self { MonoItem::Fn(instance) => tcx.symbol_name(instance), MonoItem::Static(def_id) => tcx.symbol_name(Instance::mono(tcx, def_id)), MonoItem::GlobalAsm(hir_id) => { let def_id = tcx.hir().local_def_id(hir_id); - SymbolName { name: Symbol::intern(&format!("global_asm_{:?}", def_id)) } + SymbolName::new(tcx, &format!("global_asm_{:?}", def_id)) } } } @@ -335,9 +335,9 @@ impl<'tcx> CodegenUnit<'tcx> { // The codegen tests rely on items being process in the same order as // they appear in the file, so for local items, we sort by node_id first #[derive(PartialEq, Eq, PartialOrd, Ord)] - pub struct ItemSortKey(Option, SymbolName); + pub struct ItemSortKey<'tcx>(Option, SymbolName<'tcx>); - fn item_sort_key<'tcx>(tcx: TyCtxt<'tcx>, item: MonoItem<'tcx>) -> ItemSortKey { + fn item_sort_key<'tcx>(tcx: TyCtxt<'tcx>, item: MonoItem<'tcx>) -> ItemSortKey<'tcx> { ItemSortKey( match item { MonoItem::Fn(ref instance) => { diff --git a/src/librustc_middle/query/mod.rs b/src/librustc_middle/query/mod.rs index 0faf389aa385c..942fba478f1f1 100644 --- a/src/librustc_middle/query/mod.rs +++ b/src/librustc_middle/query/mod.rs @@ -691,7 +691,7 @@ rustc_queries! { /// 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. - query symbol_name(key: ty::Instance<'tcx>) -> ty::SymbolName { + query symbol_name(key: ty::Instance<'tcx>) -> ty::SymbolName<'tcx> { desc { "computing the symbol for `{}`", key } cache_on_disk_if { true } } diff --git a/src/librustc_middle/ty/codec.rs b/src/librustc_middle/ty/codec.rs index 67ceaca103e9f..a7c7b16048039 100644 --- a/src/librustc_middle/ty/codec.rs +++ b/src/librustc_middle/ty/codec.rs @@ -262,6 +262,14 @@ where Ok(decoder.tcx().adt_def(def_id)) } +#[inline] +pub fn decode_symbol_name(decoder: &mut D) -> Result, D::Error> +where + D: TyDecoder<'tcx>, +{ + Ok(ty::SymbolName::new(decoder.tcx(), &decoder.read_str()?)) +} + #[inline] pub fn decode_existential_predicate_slice( decoder: &mut D, @@ -504,6 +512,13 @@ macro_rules! implement_ty_decoder { } } + impl<'_x, $($typaram),*> SpecializedDecoder> + for $DecoderName<$($typaram),*> { + fn specialized_decode(&mut self) -> Result, Self::Error> { + unsafe { transmute(decode_symbol_name(self)) } + } + } + impl<'_x, '_y, $($typaram),*> SpecializedDecoder<&'_x ty::List>> for $DecoderName<$($typaram),*> where &'_x ty::List>: UseSpecializedDecodable { diff --git a/src/librustc_middle/ty/mod.rs b/src/librustc_middle/ty/mod.rs index bec1200d7aa0f..f352f3a397d4f 100644 --- a/src/librustc_middle/ty/mod.rs +++ b/src/librustc_middle/ty/mod.rs @@ -50,6 +50,7 @@ use std::hash::{Hash, Hasher}; use std::marker::PhantomData; use std::ops::Range; use std::ptr; +use std::str; pub use self::sty::BoundRegion::*; pub use self::sty::InferTy::*; @@ -2988,40 +2989,37 @@ pub struct CrateInherentImpls { pub inherent_impls: DefIdMap>, } -#[derive(Clone, Copy, PartialEq, Eq, RustcEncodable, RustcDecodable, HashStable)] -pub struct SymbolName { - // FIXME: we don't rely on interning or equality here - better have - // this be a `&'tcx str`. - pub name: Symbol, -} - -impl SymbolName { - pub fn new(name: &str) -> SymbolName { - SymbolName { name: Symbol::intern(name) } - } +#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, HashStable)] +pub struct SymbolName<'tcx> { + /// `&str` gives a consistent ordering, which ensures reproducible builds. + pub name: &'tcx str, } -impl PartialOrd for SymbolName { - fn partial_cmp(&self, other: &SymbolName) -> Option { - self.name.as_str().partial_cmp(&other.name.as_str()) +impl<'tcx> SymbolName<'tcx> { + pub fn new(tcx: TyCtxt<'tcx>, name: &str) -> SymbolName<'tcx> { + SymbolName { + name: unsafe { str::from_utf8_unchecked(tcx.arena.alloc_slice(name.as_bytes())) }, + } } } -/// Ordering must use the chars to ensure reproducible builds. -impl Ord for SymbolName { - fn cmp(&self, other: &SymbolName) -> Ordering { - self.name.as_str().cmp(&other.name.as_str()) +impl<'tcx> fmt::Display for SymbolName<'tcx> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Display::fmt(&self.name, fmt) } } -impl fmt::Display for SymbolName { +impl<'tcx> fmt::Debug for SymbolName<'tcx> { fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { fmt::Display::fmt(&self.name, fmt) } } -impl fmt::Debug for SymbolName { - fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { - fmt::Display::fmt(&self.name, fmt) +impl<'tcx> rustc_serialize::UseSpecializedEncodable for SymbolName<'tcx> { + fn default_encode(&self, s: &mut S) -> Result<(), S::Error> { + s.emit_str(self.name) } } + +// The decoding takes place in `decode_symbol_name()`. +impl<'tcx> rustc_serialize::UseSpecializedDecodable for SymbolName<'tcx> {} diff --git a/src/librustc_middle/ty/query/values.rs b/src/librustc_middle/ty/query/values.rs index 0a0ff101b5203..f28b0f499f082 100644 --- a/src/librustc_middle/ty/query/values.rs +++ b/src/librustc_middle/ty/query/values.rs @@ -1,7 +1,5 @@ use crate::ty::{self, AdtSizedConstraint, Ty, TyCtxt, TyS}; -use rustc_span::symbol::Symbol; - pub(super) trait Value<'tcx>: Sized { fn from_cycle_error(tcx: TyCtxt<'tcx>) -> Self; } @@ -21,9 +19,15 @@ impl<'tcx> Value<'tcx> for &'_ TyS<'_> { } } -impl<'tcx> Value<'tcx> for ty::SymbolName { - fn from_cycle_error(_: TyCtxt<'tcx>) -> Self { - ty::SymbolName { name: Symbol::intern("") } +impl<'tcx> Value<'tcx> for ty::SymbolName<'_> { + fn from_cycle_error(tcx: TyCtxt<'tcx>) -> Self { + // SAFETY: This is never called when `Self` is not `SymbolName<'tcx>`. + // FIXME: Represent the above fact in the trait system somehow. + unsafe { + std::mem::transmute::, ty::SymbolName<'_>>(ty::SymbolName::new( + tcx, "", + )) + } } } diff --git a/src/librustc_mir/monomorphize/partitioning.rs b/src/librustc_mir/monomorphize/partitioning.rs index ebea65c8f96f2..65ed76c558c51 100644 --- a/src/librustc_mir/monomorphize/partitioning.rs +++ b/src/librustc_mir/monomorphize/partitioning.rs @@ -817,7 +817,7 @@ where debug!("CodegenUnit {} estimated size {} :", cgu.name(), cgu.size_estimate()); for (mono_item, linkage) in cgu.items() { - let symbol_name = mono_item.symbol_name(tcx).name.as_str(); + let symbol_name = mono_item.symbol_name(tcx).name; let symbol_hash_start = symbol_name.rfind('h'); let symbol_hash = symbol_hash_start.map(|i| &symbol_name[i..]).unwrap_or(""); diff --git a/src/librustc_span/symbol.rs b/src/librustc_span/symbol.rs index 0e9df5feb32ba..8b93b8a7aa74a 100644 --- a/src/librustc_span/symbol.rs +++ b/src/librustc_span/symbol.rs @@ -856,8 +856,6 @@ symbols! { rustc_unsafe_specialization_marker, rustc_variance, rust_eh_personality, - rust_eh_register_frames, - rust_eh_unregister_frames, rustfmt, rust_oom, rvalue_static_promotion, diff --git a/src/librustc_symbol_mangling/lib.rs b/src/librustc_symbol_mangling/lib.rs index 012321026938e..2579cf53d3d50 100644 --- a/src/librustc_symbol_mangling/lib.rs +++ b/src/librustc_symbol_mangling/lib.rs @@ -106,8 +106,6 @@ use rustc_middle::ty::subst::SubstsRef; use rustc_middle::ty::{self, Instance, TyCtxt}; use rustc_session::config::SymbolManglingVersion; -use rustc_span::symbol::Symbol; - use log::debug; mod legacy; @@ -133,7 +131,7 @@ pub fn provide(providers: &mut 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 { +fn symbol_name_provider(tcx: TyCtxt<'tcx>, instance: Instance<'tcx>) -> ty::SymbolName<'tcx> { 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 @@ -149,7 +147,7 @@ fn symbol_name_provider(tcx: TyCtxt<'tcx>, instance: Instance<'tcx>) -> ty::Symb } }); - ty::SymbolName { name: Symbol::intern(&symbol_name) } + ty::SymbolName::new(tcx, &symbol_name) } /// Computes the symbol name for the given instance. This function will call diff --git a/src/librustc_symbol_mangling/test.rs b/src/librustc_symbol_mangling/test.rs index 5175b692e17b6..2f1c896ce2f16 100644 --- a/src/librustc_symbol_mangling/test.rs +++ b/src/librustc_symbol_mangling/test.rs @@ -39,7 +39,7 @@ impl SymbolNamesTest<'tcx> { let instance = Instance::mono(tcx, def_id.to_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()) { + if let Ok(demangling) = rustc_demangle::try_demangle(mangled.name) { tcx.sess.span_err(attr.span, &format!("demangling({})", demangling)); tcx.sess.span_err(attr.span, &format!("demangling-alt({:#})", demangling)); }