diff options
Diffstat (limited to 'gcc/go/gofrontend/gogo.cc')
-rw-r--r-- | gcc/go/gofrontend/gogo.cc | 79 |
1 files changed, 67 insertions, 12 deletions
diff --git a/gcc/go/gofrontend/gogo.cc b/gcc/go/gofrontend/gogo.cc index f042f64d492..699456dd4ee 100644 --- a/gcc/go/gofrontend/gogo.cc +++ b/gcc/go/gofrontend/gogo.cc @@ -338,22 +338,28 @@ Gogo::set_package_name(const std::string& package_name, // Now that we know the name of the package we are compiling, set // the package path to use for reflect.Type.PkgPath and global // symbol names. - if (!this->pkgpath_set_) + if (this->pkgpath_set_) + this->pkgpath_symbol_ = Gogo::pkgpath_for_symbol(this->pkgpath_); + else { if (!this->prefix_from_option_ && package_name == "main") - this->pkgpath_ = package_name; + { + this->pkgpath_ = package_name; + this->pkgpath_symbol_ = Gogo::pkgpath_for_symbol(package_name); + } else { if (!this->prefix_from_option_) this->prefix_ = "go"; this->pkgpath_ = this->prefix_ + '.' + package_name; + this->pkgpath_symbol_ = (Gogo::pkgpath_for_symbol(this->prefix_) + '.' + + Gogo::pkgpath_for_symbol(package_name)); } this->pkgpath_set_ = true; } - this->pkgpath_symbol_ = Gogo::pkgpath_for_symbol(this->pkgpath_); - - this->package_ = this->register_package(this->pkgpath_, location); + this->package_ = this->register_package(this->pkgpath_, + this->pkgpath_symbol_, location); this->package_->set_package_name(package_name, location); if (this->is_main_package()) @@ -656,10 +662,11 @@ Gogo::add_imported_package(const std::string& real_name, const std::string& alias_arg, bool is_alias_exported, const std::string& pkgpath, + const std::string& pkgpath_symbol, Location location, bool* padd_to_globals) { - Package* ret = this->register_package(pkgpath, location); + Package* ret = this->register_package(pkgpath, pkgpath_symbol, location); ret->set_package_name(real_name, location); *padd_to_globals = false; @@ -688,10 +695,13 @@ Gogo::add_imported_package(const std::string& real_name, // Register a package. This package may or may not be imported. This // returns the Package structure for the package, creating if it // necessary. LOCATION is the location of the import statement that -// led us to see this package. +// led us to see this package. PKGPATH_SYMBOL is the symbol to use +// for names in the package; it may be the empty string, in which case +// we either get it later or make a guess when we need it. Package* -Gogo::register_package(const std::string& pkgpath, Location location) +Gogo::register_package(const std::string& pkgpath, + const std::string& pkgpath_symbol, Location location) { Package* package = NULL; std::pair<Packages::iterator, bool> ins = @@ -701,13 +711,15 @@ Gogo::register_package(const std::string& pkgpath, Location location) // We have seen this package name before. package = ins.first->second; go_assert(package != NULL && package->pkgpath() == pkgpath); + if (!pkgpath_symbol.empty()) + package->set_pkgpath_symbol(pkgpath_symbol); if (Linemap::is_unknown_location(package->location())) package->set_location(location); } else { // First time we have seen this package name. - package = new Package(pkgpath, location); + package = new Package(pkgpath, pkgpath_symbol, location); go_assert(ins.first->second == NULL); ins.first->second = package; } @@ -3424,10 +3436,24 @@ Gogo::do_exports() // support streaming to a separate file. Stream_to_section stream; + // Write out either the prefix or pkgpath depending on how we were + // invoked. + std::string prefix; + std::string pkgpath; + if (this->pkgpath_from_option_) + pkgpath = this->pkgpath_; + else if (this->prefix_from_option_) + prefix = this->prefix_; + else if (this->is_main_package()) + pkgpath = "main"; + else + prefix = "go"; + Export exp(&stream); exp.register_builtin_types(this); exp.export_globals(this->package_name(), - this->pkgpath(), + prefix, + pkgpath, this->package_priority(), this->imports_, (this->need_init_fn_ && !this->is_main_package() @@ -6030,8 +6056,9 @@ Unnamed_label::get_goto(Translate_context* context, Location location) // Class Package. -Package::Package(const std::string& pkgpath, Location location) - : pkgpath_(pkgpath), pkgpath_symbol_(Gogo::pkgpath_for_symbol(pkgpath)), +Package::Package(const std::string& pkgpath, + const std::string& pkgpath_symbol, Location location) + : pkgpath_(pkgpath), pkgpath_symbol_(pkgpath_symbol), package_name_(), bindings_(new Bindings(NULL)), priority_(0), location_(location), used_(false), is_imported_(false), uses_sink_alias_(false) @@ -6055,6 +6082,34 @@ Package::set_package_name(const std::string& package_name, Location location) package_name.c_str()); } +// Return the pkgpath symbol, which is a prefix for symbols defined in +// this package. + +std::string +Package::pkgpath_symbol() const +{ + if (this->pkgpath_symbol_.empty()) + { + // In the general case, this is wrong, because the package might + // have been compiled with -fprefix. However, it is what we + // used to do, so it is no more wrong than we were before. + return Gogo::pkgpath_for_symbol(this->pkgpath_); + } + return this->pkgpath_symbol_; +} + +// Set the package path symbol. + +void +Package::set_pkgpath_symbol(const std::string& pkgpath_symbol) +{ + go_assert(!pkgpath_symbol.empty()); + if (this->pkgpath_symbol_.empty()) + this->pkgpath_symbol_ = pkgpath_symbol; + else + go_assert(this->pkgpath_symbol_ == pkgpath_symbol); +} + // Set the priority. We may see multiple priorities for an imported // package; we want to use the largest one. |