[lld] r275711 - Handle versioned symbols efficiently.
Rui Ueyama via llvm-commits
llvm-commits at lists.llvm.org
Mon Jul 18 16:50:54 PDT 2016
As George pointed out, it was measured with a debug build, so the numbers
were bogus. I'll test it again and roll it back if needed tomorrow.
On Mon, Jul 18, 2016 at 5:04 PM, Rafael EspĂndola <
rafael.espindola at gmail.com> wrote:
> I cannot reproduce these numbers.
>
> I could not test scylla and firefox because of pr28605, but the times
> I got with the rest are attached. The ratios are from the previous
> value.
>
> Can you upload the --reproduce of the testcase you used somewhere?
>
> Thanks,
> Rafael
>
> On 17 July 2016 at 13:23, Rui Ueyama via llvm-commits
> <llvm-commits at lists.llvm.org> wrote:
> > Author: ruiu
> > Date: Sun Jul 17 12:23:17 2016
> > New Revision: 275711
> >
> > URL: http://llvm.org/viewvc/llvm-project?rev=275711&view=rev
> > Log:
> > Handle versioned symbols efficiently.
> >
> > Versions can be assigned to symbols in two different ways.
> > One is the usual version scripts, and the other is special
> > symbol suffix '@'. If a symbol contains '@', the string after
> > that is considered to specify a version name.
> >
> > Previously, we look for '@' for all symbols.
> >
> > Anything that works on every symbol can be expensive because
> > the linker has to handle a lot of symbols. The search for '@'
> > was not an exception.
> >
> > In this patch, I made two optimizations.
> >
> > The first optimization is to handle '@' only when at least one
> > version is defined. If no versions are defined, no versions can
> > be assigned to any symbols, so it's waste of time to search for '@'.
> >
> > The second optimization is to scan only suffixes of symbol names
> > instead of entire symbol names. Symbol names can be very long, but
> > symbol versions are usually short, so scanning entire symbol names
> > is waste of time, too.
> >
> > There are some error cases which we no longer be able to detect
> > with this patch. I don't think it's a major drawback because they
> > are minor errors. Speed is more important.
> >
> > This change improves LLD with debug info self-link time from
> > 6.6993 seconds to 6.3426 seconds (or -5.3%).
> >
> > Differential Revision: https://reviews.llvm.org/D22433
> >
> > Removed:
> > lld/trunk/test/ELF/verdef-executable.s
> > Modified:
> > lld/trunk/ELF/Config.h
> > lld/trunk/ELF/Driver.cpp
> > lld/trunk/ELF/SymbolTable.cpp
> > lld/trunk/ELF/SymbolTable.h
> > lld/trunk/ELF/Symbols.cpp
> > lld/trunk/ELF/Symbols.h
> > lld/trunk/test/ELF/verdef-defaultver.s
> >
> > Modified: lld/trunk/ELF/Config.h
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Config.h?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/Config.h (original)
> > +++ lld/trunk/ELF/Config.h Sun Jul 17 12:23:17 2016
> > @@ -90,7 +90,6 @@ struct Configuration {
> > bool FatalWarnings;
> > bool GcSections;
> > bool GnuHash = false;
> > - bool HasVersionScript = false;
> > bool ICF;
> > bool Mips64EL = false;
> > bool NoGnuUnique;
> >
> > Modified: lld/trunk/ELF/Driver.cpp
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Driver.cpp?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/Driver.cpp (original)
> > +++ lld/trunk/ELF/Driver.cpp Sun Jul 17 12:23:17 2016
> > @@ -443,11 +443,9 @@ void LinkerDriver::readConfigs(opt::Inpu
> > for (auto *Arg : Args.filtered(OPT_export_dynamic_symbol))
> > Config->DynamicList.push_back(Arg->getValue());
> >
> > - if (auto *Arg = Args.getLastArg(OPT_version_script)) {
> > - Config->HasVersionScript = true;
> > + if (auto *Arg = Args.getLastArg(OPT_version_script))
> > if (Optional<MemoryBufferRef> Buffer = readFile(Arg->getValue()))
> > parseVersionScript(*Buffer);
> > - }
> >
> > for (auto *Arg : Args.filtered(OPT_trace_symbol))
> > Config->TraceSymbol.insert(Arg->getValue());
> > @@ -557,6 +555,7 @@ template <class ELFT> void LinkerDriver:
> > Symtab.scanShlibUndefined();
> > Symtab.scanDynamicList();
> > Symtab.scanVersionScript();
> > + Symtab.scanSymbolVersions();
> > Symtab.traceDefined();
> >
> > Symtab.addCombinedLtoObject();
> >
> > Modified: lld/trunk/ELF/SymbolTable.cpp
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.cpp?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/SymbolTable.cpp (original)
> > +++ lld/trunk/ELF/SymbolTable.cpp Sun Jul 17 12:23:17 2016
> > @@ -165,39 +165,6 @@ static uint8_t getMinVisibility(uint8_t
> > return std::min(VA, VB);
> > }
> >
> > -// A symbol version may be included in a symbol name as a suffix after
> '@'.
> > -// This function parses that part and returns a version ID number.
> > -static uint16_t getVersionId(Symbol *Sym, StringRef Name) {
> > - size_t VersionBegin = Name.find('@');
> > - if (VersionBegin == StringRef::npos)
> > - return Config->DefaultSymbolVersion;
> > -
> > - // If symbol name contains '@' or '@@' we can assign its version id
> right
> > - // here. '@@' means the default version. It is usually the most
> recent one.
> > - // VERSYM_HIDDEN flag should be set for all non-default versions.
> > - StringRef Version = Name.drop_front(VersionBegin + 1);
> > - bool Default = Version.startswith("@");
> > - if (Default)
> > - Version = Version.drop_front();
> > -
> > - for (VersionDefinition &V : Config->VersionDefinitions)
> > - if (V.Name == Version)
> > - return Default ? V.Id : (V.Id | VERSYM_HIDDEN);
> > -
> > -
> > - // If we are not building shared and version script
> > - // is not specified, then it is not a error, it is
> > - // in common not to use script for linking executables.
> > - // In this case we just create new version.
> > - if (!Config->Shared && !Config->HasVersionScript) {
> > - size_t Id = defineSymbolVersion(Version);
> > - return Default ? Id : (Id | VERSYM_HIDDEN);
> > - }
> > -
> > - error("symbol " + Name + " has undefined version " + Version);
> > - return 0;
> > -}
> > -
> > // Find an existing symbol or create and insert a new one.
> > template <class ELFT>
> > std::pair<Symbol *, bool> SymbolTable<ELFT>::insert(StringRef Name) {
> > @@ -210,9 +177,7 @@ std::pair<Symbol *, bool> SymbolTable<EL
> > Sym->Visibility = STV_DEFAULT;
> > Sym->IsUsedInRegularObj = false;
> > Sym->ExportDynamic = false;
> > - Sym->VersionId = getVersionId(Sym, Name);
> > - Sym->VersionedName =
> > - Sym->VersionId != VER_NDX_LOCAL && Sym->VersionId !=
> VER_NDX_GLOBAL;
> > + Sym->VersionId = Config->DefaultSymbolVersion;
> > SymVector.push_back(Sym);
> > } else {
> > Sym = SymVector[P.first->second];
> > @@ -646,6 +611,84 @@ template <class ELFT> void SymbolTable<E
> > }
> > }
> >
> > +// Returns the size of the longest version name.
> > +static int getMaxVersionLen() {
> > + size_t Len = 0;
> > + for (VersionDefinition &V : Config->VersionDefinitions)
> > + Len = std::max(Len, V.Name.size());
> > + return Len;
> > +}
> > +
> > +// Parses a symbol name in the form of <name>@<version> or
> <name>@@<version>.
> > +static std::pair<StringRef, uint16_t>
> > +getSymbolVersion(SymbolBody *B, int MaxVersionLen) {
> > + StringRef S = B->getName();
> > +
> > + // MaxVersionLen was passed so that we don't need to scan
> > + // all characters in a symbol name. It is effective because
> > + // versions are usually short and symbol names can be very long.
> > + size_t Pos = S.find('@', std::max(0, int(S.size()) - MaxVersionLen -
> 2));
> > + if (Pos == 0 || Pos == StringRef::npos)
> > + return {"", 0};
> > +
> > + StringRef Name = S.substr(0, Pos);
> > + StringRef Verstr = S.substr(Pos + 1);
> > + if (Verstr.empty())
> > + return {"", 0};
> > +
> > + // '@@' in a symbol name means the default version.
> > + // It is usually the most recent one.
> > + bool IsDefault = (Verstr[0] == '@');
> > + if (IsDefault)
> > + Verstr = Verstr.substr(1);
> > +
> > + for (VersionDefinition &V : Config->VersionDefinitions) {
> > + if (V.Name == Verstr)
> > + return {Name, IsDefault ? V.Id : (V.Id | VERSYM_HIDDEN)};
> > + }
> > +
> > + // It is an error if the specified version was not defined.
> > + error("symbol " + S + " has undefined version " + Verstr);
> > + return {"", 0};
> > +}
> > +
> > +// Versions are usually assigned to symbols using version scripts,
> > +// but there's another way to assign versions to symbols.
> > +// If a symbol name contains '@', the string after it is not
> > +// actually a part of the symbol name but specifies a version.
> > +// This function takes care of it.
> > +template <class ELFT> void SymbolTable<ELFT>::scanSymbolVersions() {
> > + if (Config->VersionDefinitions.empty())
> > + return;
> > +
> > + int MaxVersionLen = getMaxVersionLen();
> > +
> > + // Unfortunately there's no way other than iterating over all
> > + // symbols to look for '@' characters in symbol names.
> > + // So this is inherently slow. A good news is that we do this
> > + // only when versions have been defined.
> > + for (Symbol *Sym : SymVector) {
> > + // Symbol versions for exported symbols are by nature
> > + // only for defined global symbols.
> > + SymbolBody *B = Sym->body();
> > + if (!B->isDefined())
> > + continue;
> > + uint8_t Visibility = B->getVisibility();
> > + if (Visibility != STV_DEFAULT && Visibility != STV_PROTECTED)
> > + continue;
> > +
> > + // Look for '@' in the symbol name.
> > + StringRef Name;
> > + uint16_t Version;
> > + std::tie(Name, Version) = getSymbolVersion(B, MaxVersionLen);
> > + if (Name.empty())
> > + continue;
> > +
> > + B->setName(Name);
> > + Sym->VersionId = Version;
> > + }
> > +}
> > +
> > // Print the module names which define the notified
> > // symbols provided through -y or --trace-symbol option.
> > template <class ELFT> void SymbolTable<ELFT>::traceDefined() {
> >
> > Modified: lld/trunk/ELF/SymbolTable.h
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.h?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/SymbolTable.h (original)
> > +++ lld/trunk/ELF/SymbolTable.h Sun Jul 17 12:23:17 2016
> > @@ -82,6 +82,7 @@ public:
> > void scanShlibUndefined();
> > void scanDynamicList();
> > void scanVersionScript();
> > + void scanSymbolVersions();
> > void traceDefined();
> >
> > SymbolBody *find(StringRef Name);
> >
> > Modified: lld/trunk/ELF/Symbols.cpp
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.cpp?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/Symbols.cpp (original)
> > +++ lld/trunk/ELF/Symbols.cpp Sun Jul 17 12:23:17 2016
> > @@ -98,10 +98,12 @@ SymbolBody::SymbolBody(Kind K, StringRef
> >
> > StringRef SymbolBody::getName() const {
> > assert(!isLocal());
> > - StringRef S = StringRef(Name.S, Name.Len);
> > - if (!symbol()->VersionedName)
> > - return S;
> > - return S.substr(0, S.find('@'));
> > + return StringRef(Name.S, Name.Len);
> > +}
> > +
> > +void SymbolBody::setName(StringRef S) {
> > + Name.S = S.data();
> > + Name.Len = S.size();
> > }
> >
> > // Returns true if a symbol can be replaced at load-time by a symbol
> >
> > Modified: lld/trunk/ELF/Symbols.h
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.h?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/ELF/Symbols.h (original)
> > +++ lld/trunk/ELF/Symbols.h Sun Jul 17 12:23:17 2016
> > @@ -70,8 +70,9 @@ public:
> > bool isLocal() const { return IsLocal; }
> > bool isPreemptible() const;
> >
> > - // Returns the symbol name.
> > StringRef getName() const;
> > + void setName(StringRef S);
> > +
> > uint32_t getNameOffset() const {
> > assert(isLocal());
> > return NameOffset;
> > @@ -419,11 +420,6 @@ struct Symbol {
> > // --export-dynamic, and by dynamic lists.
> > unsigned ExportDynamic : 1;
> >
> > - // If this flag is true then symbol name also contains version name.
> Such
> > - // name can have single or double symbol @. Double means that version
> is
> > - // used as default. Single signals about depricated symbol version.
> > - unsigned VersionedName : 1;
> > -
> > bool includeInDynsym() const;
> > bool isWeak() const { return Binding == llvm::ELF::STB_WEAK; }
> >
> >
> > Modified: lld/trunk/test/ELF/verdef-defaultver.s
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/test/ELF/verdef-defaultver.s?rev=275711&r1=275710&r2=275711&view=diff
> >
> ==============================================================================
> > --- lld/trunk/test/ELF/verdef-defaultver.s (original)
> > +++ lld/trunk/test/ELF/verdef-defaultver.s Sun Jul 17 12:23:17 2016
> > @@ -198,10 +198,6 @@
> > # EXE-NEXT: }
> > # EXE-NEXT: }
> >
> > -# RUN: not ld.lld -shared %t1 -o %terr.so 2>&1 | \
> > -# RUN: FileCheck -check-prefix=ERR1 %s
> > -# ERR1: symbol b@@LIBSAMPLE_2.0 has undefined version LIBSAMPLE_2.0
> > -
> > .globl _start
> > _start:
> > callq a
> >
> > Removed: lld/trunk/test/ELF/verdef-executable.s
> > URL:
> http://llvm.org/viewvc/llvm-project/lld/trunk/test/ELF/verdef-executable.s?rev=275710&view=auto
> >
> ==============================================================================
> > --- lld/trunk/test/ELF/verdef-executable.s (original)
> > +++ lld/trunk/test/ELF/verdef-executable.s (removed)
> > @@ -1,269 +0,0 @@
> > -# REQUIRES: x86
> > -
> > -# RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t1
> > -# RUN: ld.lld %t1 -o %t
> > -# RUN: llvm-readobj -t -V -dyn-symbols %t | FileCheck
> --check-prefix=EXE %s
> > -
> > -# EXE: Symbols [
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name:
> > -# EXE-NEXT: Value: 0x0
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Local
> > -# EXE-NEXT: Type: None (0x0)
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: Undefined (0x0)
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: _start
> > -# EXE-NEXT: Value: 0x11004
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: None
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: a
> > -# EXE-NEXT: Value: 0x11000
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: b
> > -# EXE-NEXT: Value: 0x11002
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: b
> > -# EXE-NEXT: Value: 0x11001
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: b_1
> > -# EXE-NEXT: Value: 0x11001
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: b_2
> > -# EXE-NEXT: Value: 0x11002
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: Symbol {
> > -# EXE-NEXT: Name: c
> > -# EXE-NEXT: Value: 0x11003
> > -# EXE-NEXT: Size: 0
> > -# EXE-NEXT: Binding: Global
> > -# EXE-NEXT: Type: Function
> > -# EXE-NEXT: Other: 0
> > -# EXE-NEXT: Section: .text
> > -# EXE-NEXT: }
> > -# EXE-NEXT: ]
> > -# EXE-NEXT: DynamicSymbols [
> > -# EXE-NEXT: ]
> > -# EXE-NEXT: Version symbols {
> > -# EXE-NEXT: }
> > -# EXE-NEXT: SHT_GNU_verdef {
> > -# EXE-NEXT: }
> > -# EXE-NEXT: SHT_GNU_verneed {
> > -# EXE-NEXT: }
> > -
> > -# RUN: ld.lld -pie --export-dynamic %t1 -o %t2
> > -# RUN: llvm-readobj -t -V -dyn-symbols %t2 | \
> > -# RUN: FileCheck --check-prefix=EXEDYN %s
> > -
> > -# EXEDYN: DynamicSymbols [
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: @
> > -# EXEDYN-NEXT: Value: 0x0
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Local
> > -# EXEDYN-NEXT: Type: None
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: Undefined
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: _start@
> > -# EXEDYN-NEXT: Value: 0x1004
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: None
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: a@
> > -# EXEDYN-NEXT: Value: 0x1000
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: b@@LIBSAMPLE_2.0
> > -# EXEDYN-NEXT: Value: 0x1002
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: b at LIBSAMPLE_1.0
> > -# EXEDYN-NEXT: Value: 0x1001
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: b_1@
> > -# EXEDYN-NEXT: Value: 0x1001
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: b_2@
> > -# EXEDYN-NEXT: Value: 0x1002
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Name: c@
> > -# EXEDYN-NEXT: Value: 0x1003
> > -# EXEDYN-NEXT: Size: 0
> > -# EXEDYN-NEXT: Binding: Global
> > -# EXEDYN-NEXT: Type: Function
> > -# EXEDYN-NEXT: Other: 0
> > -# EXEDYN-NEXT: Section: .text
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: ]
> > -# EXEDYN-NEXT: Version symbols {
> > -# EXEDYN-NEXT: Section Name: .gnu.version
> > -# EXEDYN-NEXT: Address: 0x288
> > -# EXEDYN-NEXT: Offset: 0x288
> > -# EXEDYN-NEXT: Link: 1
> > -# EXEDYN-NEXT: Symbols [
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 0
> > -# EXEDYN-NEXT: Name: @
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Name: _start@
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Name: a@
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 2
> > -# EXEDYN-NEXT: Name: b@@LIBSAMPLE_2.0
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 3
> > -# EXEDYN-NEXT: Name: b at LIBSAMPLE_1.0
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Name: b_1@
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Name: b_2@
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Symbol {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Name: c@
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: ]
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: SHT_GNU_verdef {
> > -# EXEDYN-NEXT: Definition {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Flags: Base
> > -# EXEDYN-NEXT: Index: 1
> > -# EXEDYN-NEXT: Hash:
> > -# EXEDYN-NEXT: Name:
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Definition {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Flags: 0x0
> > -# EXEDYN-NEXT: Index: 2
> > -# EXEDYN-NEXT: Hash: 98456416
> > -# EXEDYN-NEXT: Name: LIBSAMPLE_2.0
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: Definition {
> > -# EXEDYN-NEXT: Version: 1
> > -# EXEDYN-NEXT: Flags: 0x0
> > -# EXEDYN-NEXT: Index: 3
> > -# EXEDYN-NEXT: Hash: 98457184
> > -# EXEDYN-NEXT: Name: LIBSAMPLE_1.0
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: }
> > -# EXEDYN-NEXT: SHT_GNU_verneed {
> > -# EXEDYN-NEXT: }
> > -
> > -## Check when linking executable that error produced if version script
> > -## was specified and there are symbols with version in name that
> > -## is absent in script.
> > -# RUN: echo "VERSION { \
> > -# RUN: global: foo; \
> > -# RUN: local: *; }; " > %t.script
> > -# RUN: not ld.lld --version-script %t.script %t1 -o %t3 2>&1 | \
> > -# RUN: FileCheck -check-prefix=ERR %s
> > -# ERR: symbol b at LIBSAMPLE_1.0 has undefined version LIBSAMPLE_1.0
> > -
> > -b at LIBSAMPLE_1.0 = b_1
> > -b@@LIBSAMPLE_2.0 = b_2
> > -
> > -.globl a
> > -.type a, at function
> > -a:
> > -retq
> > -
> > -.globl b_1
> > -.type b_1, at function
> > -b_1:
> > -retq
> > -
> > -.globl b_2
> > -.type b_2, at function
> > -b_2:
> > -retq
> > -
> > -.globl c
> > -.type c, at function
> > -c:
> > -retq
> > -
> > -.globl _start
> > -_start:
> > - nop
> >
> >
> > _______________________________________________
> > llvm-commits mailing list
> > llvm-commits at lists.llvm.org
> > http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20160718/59c15fd3/attachment-0001.html>
More information about the llvm-commits
mailing list