diff options
author | bors[bot] <26634292+bors[bot]@users.noreply.github.com> | 2021-05-11 17:46:10 +0000 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-05-11 17:46:10 +0000 |
commit | 5134aaa9f0b37ea372cb185fe7aa6c26fe0a4c2e (patch) | |
tree | 95c03868e9d05a84000e29187e2e5ccba431cd35 /gcc | |
parent | 299d98d8e6fcb8d014b299adc426d93cf0c8050f (diff) | |
parent | 58e108c7c6d0fa3c9ebc7eeb681851924e22ddd5 (diff) | |
download | gcc-5134aaa9f0b37ea372cb185fe7aa6c26fe0a4c2e.zip gcc-5134aaa9f0b37ea372cb185fe7aa6c26fe0a4c2e.tar.gz gcc-5134aaa9f0b37ea372cb185fe7aa6c26fe0a4c2e.tar.bz2 |
Merge #425
425: Basic implementation of legacy symbol mangling r=philberty a=philberty
Implement basic rustc legacy symbol mangling
Rust supports two different symbol mangling methods legacy and V0. V0 is
the goal but its not yet stable. This implements the legacy method but
with a dummy hash value since it requires a sip128 implementation to
generate the apropriate hash which can be done in a sperate change.
This change allows us to actually assemble generic functions and avoid
bad symbol duplications.
Addresses #305
Co-authored-by: Philip Herron <philip.herron@embecosm.com>
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/rust/backend/rust-compile-context.h | 5 | ||||
-rw-r--r-- | gcc/rust/backend/rust-compile-implitem.h | 16 | ||||
-rw-r--r-- | gcc/rust/backend/rust-compile-item.h | 21 | ||||
-rw-r--r-- | gcc/rust/backend/rust-compile.cc | 68 | ||||
-rw-r--r-- | gcc/rust/rust-session-manager.cc | 8 | ||||
-rw-r--r-- | gcc/rust/typecheck/rust-tyty.h | 5 | ||||
-rw-r--r-- | gcc/rust/util/rust-hir-map.cc | 27 | ||||
-rw-r--r-- | gcc/rust/util/rust-hir-map.h | 24 |
8 files changed, 140 insertions, 34 deletions
diff --git a/gcc/rust/backend/rust-compile-context.h b/gcc/rust/backend/rust-compile-context.h index bdc9eca..7db4ea2 100644 --- a/gcc/rust/backend/rust-compile-context.h +++ b/gcc/rust/backend/rust-compile-context.h @@ -258,6 +258,11 @@ public: return pop; } + std::string mangle_item (const std::string &name) const; + + std::string mangle_impl_item (const TyTy::BaseType *self, + const std::string &name) const; + private: ::Backend *backend; Resolver::Resolver *resolver; diff --git a/gcc/rust/backend/rust-compile-implitem.h b/gcc/rust/backend/rust-compile-implitem.h index cee3a3b..f2caa2e 100644 --- a/gcc/rust/backend/rust-compile-implitem.h +++ b/gcc/rust/backend/rust-compile-implitem.h @@ -112,15 +112,17 @@ public: ::Btype *compiled_fn_type = TyTyResolveCompile::compile (ctx, fntype); unsigned int flags = 0; - std::string fn_identifier - = self->get_name () + "_" + function.get_function_name (); // if its the main fn or pub visibility mark its as DECL_PUBLIC // please see https://github.com/Rust-GCC/gccrs/pull/137 if (function.has_visibility ()) flags |= Backend::function_is_visible; - std::string asm_name = fn_identifier; + std::string fn_identifier + = self->get_name () + "_" + function.get_function_name (); + std::string asm_name + = ctx->mangle_impl_item (self, function.get_function_name ()); + Bfunction *fndecl = ctx->get_backend ()->function (compiled_fn_type, fn_identifier, asm_name, flags, function.get_locus ()); @@ -291,15 +293,17 @@ public: ::Btype *compiled_fn_type = TyTyResolveCompile::compile (ctx, fntype); unsigned int flags = 0; - std::string fn_identifier - = self->get_name () + "_" + method.get_method_name (); // if its the main fn or pub visibility mark its as DECL_PUBLIC // please see https://github.com/Rust-GCC/gccrs/pull/137 if (method.has_visibility ()) flags |= Backend::function_is_visible; - std::string asm_name = fn_identifier; + std::string fn_identifier + = self->get_name () + "_" + method.get_method_name (); + std::string asm_name + = ctx->mangle_impl_item (self, method.get_method_name ()); + Bfunction *fndecl = ctx->get_backend ()->function (compiled_fn_type, fn_identifier, asm_name, flags, method.get_locus ()); diff --git a/gcc/rust/backend/rust-compile-item.h b/gcc/rust/backend/rust-compile-item.h index 2bbfe4c..5a7d846 100644 --- a/gcc/rust/backend/rust-compile-item.h +++ b/gcc/rust/backend/rust-compile-item.h @@ -53,8 +53,7 @@ public: Bexpression *value = CompileExpr::Compile (var.get_expr (), ctx); std::string name = var.get_identifier (); - // FIXME need name mangling - std::string asm_name = "__" + var.get_identifier (); + std::string asm_name = ctx->mangle_item (name); bool is_external = false; bool is_hidden = false; @@ -147,21 +146,11 @@ public: std::string ir_symbol_name = function.get_function_name (); std::string asm_name = function.get_function_name (); - if (!is_main_fn) - { - // FIXME need name mangling - if (concrete == nullptr) - asm_name = "__" + function.get_function_name (); - else - { - ir_symbol_name - = function.get_function_name () + fntype->subst_as_string (); - asm_name = "__" + function.get_function_name (); - for (auto &sub : fntype->get_substs ()) - asm_name += "G" + sub.as_string (); - } - } + // we don't mangle the main fn since we haven't implemented the main shim + // yet + if (!is_main_fn) + asm_name = ctx->mangle_item (ir_symbol_name); Bfunction *fndecl = ctx->get_backend ()->function (compiled_fn_type, ir_symbol_name, diff --git a/gcc/rust/backend/rust-compile.cc b/gcc/rust/backend/rust-compile.cc index 4893541..9dd3b57 100644 --- a/gcc/rust/backend/rust-compile.cc +++ b/gcc/rust/backend/rust-compile.cc @@ -413,5 +413,73 @@ HIRCompileBase::compile_function_body ( } } +// Mr Mangle time + +static const std::string kMangledSymbolPrefix = "_ZN"; +static const std::string kMangledSymbolDelim = "E"; +static const std::string kMangledGenericDelim = "$C$"; +static const std::string kMangledSubstBegin = "$LT$"; +static const std::string kMangledSubstEnd = "$GT$"; + +static std::string +mangle_name (const std::string &name) +{ + return std::to_string (name.size ()) + name; +} + +static std::string +dummy_hash () +{ + return "h0123456789abcdef"; +} + +static std::string +mangle_self (const TyTy::BaseType *self) +{ + if (self->get_kind () != TyTy::TypeKind::ADT) + return mangle_name (self->get_name ()); + + const TyTy::ADTType *s = static_cast<const TyTy::ADTType *> (self); + std::string buf = s->get_identifier (); + + if (s->has_subsititions_defined ()) + { + buf += kMangledSubstBegin; + + const std::vector<TyTy::SubstitutionParamMapping> ¶ms + = s->get_substs (); + for (size_t i = 0; i < params.size (); i++) + { + const TyTy::SubstitutionParamMapping &sub = params.at (i); + buf += sub.as_string (); + + if ((i + 1) < params.size ()) + buf += kMangledGenericDelim; + } + + buf += kMangledSubstEnd; + } + + return mangle_name (buf); +} + +std::string +Context::mangle_item (const std::string &name) const +{ + const std::string &crate_name = mappings->get_current_crate_name (); + return kMangledSymbolPrefix + mangle_name (crate_name) + mangle_name (name) + + mangle_name (dummy_hash ()) + kMangledSymbolDelim; +} + +std::string +Context::mangle_impl_item (const TyTy::BaseType *self, + const std::string &name) const +{ + const std::string &crate_name = mappings->get_current_crate_name (); + return kMangledSymbolPrefix + mangle_name (crate_name) + mangle_self (self) + + mangle_name (name) + mangle_name (dummy_hash ()) + + kMangledSymbolDelim; +} + } // namespace Compile } // namespace Rust diff --git a/gcc/rust/rust-session-manager.cc b/gcc/rust/rust-session-manager.cc index da788b5..5e9746f 100644 --- a/gcc/rust/rust-session-manager.cc +++ b/gcc/rust/rust-session-manager.cc @@ -70,6 +70,10 @@ const char *kHIRDumpFile = "gccrs.hir.dump"; const char *kHIRTypeResolutionDumpFile = "gccrs.type-resolution.dump"; const char *kTargetOptionsDumpFile = "gccrs.target-options.dump"; +// FIME in the imports/visibility milestone - this needs to be command line +// option +const std::string kDefaultCrateName = "TestCrate"; + // Implicitly enable a target_feature (and recursively enable dependencies). void Session::implicitly_enable_feature (std::string feature_name) @@ -445,6 +449,10 @@ Session::enable_dump (std::string arg) void Session::parse_files (int num_files, const char **files) { + auto mappings = Analysis::Mappings::get (); + CrateNum crate_num = mappings->setup_crate_mappings (kDefaultCrateName); + mappings->set_current_crate (crate_num); + for (int i = 0; i < num_files; i++) { printf ("Attempting to parse file: %s\n", files[i]); diff --git a/gcc/rust/typecheck/rust-tyty.h b/gcc/rust/typecheck/rust-tyty.h index 7425030..aa709ec 100644 --- a/gcc/rust/typecheck/rust-tyty.h +++ b/gcc/rust/typecheck/rust-tyty.h @@ -618,6 +618,11 @@ public: std::vector<SubstitutionParamMapping> &get_substs () { return substitutions; } + const std::vector<SubstitutionParamMapping> &get_substs () const + { + return substitutions; + } + std::vector<SubstitutionParamMapping> clone_substs () { std::vector<SubstitutionParamMapping> clone; diff --git a/gcc/rust/util/rust-hir-map.cc b/gcc/rust/util/rust-hir-map.cc index 0dcbd4f..3a0cbb1 100644 --- a/gcc/rust/util/rust-hir-map.cc +++ b/gcc/rust/util/rust-hir-map.cc @@ -107,7 +107,7 @@ Mappings::get () { static std::unique_ptr<Mappings> instance; if (!instance) - instance = std::move (std::unique_ptr<Mappings> (new Mappings ())); + instance = std::unique_ptr<Mappings> (new Mappings ()); return instance.get (); } @@ -125,18 +125,23 @@ Mappings::set_current_crate (CrateNum crateNum) } CrateNum -Mappings::get_current_crate () +Mappings::setup_crate_mappings (std::string crate_name) { - // HACK - if (hirIdIter.find (currentCrateNum) == hirIdIter.end ()) - { - hirIdIter[currentCrateNum] = UNKNOWN_HIRID; - nodeIdIter[currentCrateNum] = UNKNOWN_NODEID; - localIdIter[currentCrateNum] = UNKNOWN_LOCAL_DEFID; - nodeIdToHirMappings[currentCrateNum] = {}; - locations[currentCrateNum] = {}; - } + CrateNum crate_num = get_next_crate_num (); + hirIdIter[crate_num] = UNKNOWN_HIRID; + nodeIdIter[crate_num] = UNKNOWN_NODEID; + localIdIter[crate_num] = UNKNOWN_LOCAL_DEFID; + nodeIdToHirMappings[crate_num] = {}; + locations[crate_num] = {}; + crate_names[crate_num] = crate_name; + + return crate_num; +} + +CrateNum +Mappings::get_current_crate () const +{ return currentCrateNum; } diff --git a/gcc/rust/util/rust-hir-map.h b/gcc/rust/util/rust-hir-map.h index 9777ee3..a198be6 100644 --- a/gcc/rust/util/rust-hir-map.h +++ b/gcc/rust/util/rust-hir-map.h @@ -83,7 +83,26 @@ public: CrateNum get_next_crate_num (); void set_current_crate (CrateNum crateNum); - CrateNum get_current_crate (); + CrateNum get_current_crate () const; + CrateNum setup_crate_mappings (std::string crate_name); + + bool get_crate_name (CrateNum crate_num, std::string &name) const + { + auto it = crate_names.find (crate_num); + if (it == crate_names.end ()) + return false; + + name.assign (it->second); + return true; + } + + std::string get_current_crate_name () const + { + std::string name; + bool ok = get_crate_name (get_current_crate (), name); + rust_assert (ok); + return name; + } NodeId get_next_node_id () { return get_next_node_id (get_current_crate ()); } NodeId get_next_node_id (CrateNum crateNum); @@ -212,6 +231,9 @@ private: // all hirid nodes std::map<CrateNum, std::set<HirId> > hirNodesWithinCrate; + + // crate names + std::map<CrateNum, std::string> crate_names; }; } // namespace Analysis |