mirror of
https://github.com/RPCS3/llvm.git
synced 2024-11-26 05:00:39 +00:00
ELFObjectWriter: deduplicate suffices in strtab
We already do this for shstrtab, so might as well do it for strtab. This extracts the string table building code into a separate class. The idea is to use it for other object formats too. I mostly wanted to do this for the general principle, but it does save a little bit on object file size. I tried this on a clang bootstrap and saved 0.54% on the sum of object file sizes (1.14 MB out of 212 MB for a release build). Differential Revision: http://reviews.llvm.org/D3533 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@207670 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
b1c1b8a78d
commit
a8febf2283
59
include/llvm/Object/StringTableBuilder.h
Normal file
59
include/llvm/Object/StringTableBuilder.h
Normal file
@ -0,0 +1,59 @@
|
||||
//===-- StringTableBuilder.h - String table building utility ------*- C++ -*-=//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_OBJECT_STRINGTABLE_BUILDER_H
|
||||
#define LLVM_OBJECT_STRINGTABLE_BUILDER_H
|
||||
|
||||
#include "llvm/ADT/SmallString.h"
|
||||
#include "llvm/ADT/StringMap.h"
|
||||
#include <cassert>
|
||||
|
||||
namespace llvm {
|
||||
|
||||
/// \brief Utility for building string tables with deduplicated suffixes.
|
||||
class StringTableBuilder {
|
||||
SmallString<256> StringTable;
|
||||
StringMap<size_t> StringIndexMap;
|
||||
|
||||
public:
|
||||
/// \brief Add a string to the builder. Returns a StringRef to the internal
|
||||
/// copy of s. Can only be used before the table is finalized.
|
||||
StringRef add(StringRef s) {
|
||||
assert(!isFinalized());
|
||||
return StringIndexMap.GetOrCreateValue(s, 0).getKey();
|
||||
}
|
||||
|
||||
/// \brief Analyze the strings and build the final table. No more strings can
|
||||
/// be added after this point.
|
||||
void finalize();
|
||||
|
||||
/// \brief Retrieve the string table data. Can only be used after the table
|
||||
/// is finalized.
|
||||
StringRef data() {
|
||||
assert(isFinalized());
|
||||
return StringTable;
|
||||
}
|
||||
|
||||
/// \brief Get the offest of a string in the string table. Can only be used
|
||||
/// after the table is finalized.
|
||||
size_t getOffset(StringRef s) {
|
||||
assert(isFinalized());
|
||||
assert(StringIndexMap.count(s) && "String is not in table!");
|
||||
return StringIndexMap[s];
|
||||
}
|
||||
|
||||
private:
|
||||
bool isFinalized() {
|
||||
return !StringTable.empty();
|
||||
}
|
||||
};
|
||||
|
||||
} // end llvm namespace
|
||||
|
||||
#endif
|
@ -28,6 +28,7 @@
|
||||
#include "llvm/MC/MCObjectWriter.h"
|
||||
#include "llvm/MC/MCSectionELF.h"
|
||||
#include "llvm/MC/MCValue.h"
|
||||
#include "llvm/Object/StringTableBuilder.h"
|
||||
#include "llvm/Support/Compression.h"
|
||||
#include "llvm/Support/Debug.h"
|
||||
#include "llvm/Support/Endian.h"
|
||||
@ -132,11 +133,11 @@ class ELFObjectWriter : public MCObjectWriter {
|
||||
MCSymbolData *SymbolData;
|
||||
uint64_t StringIndex;
|
||||
uint32_t SectionIndex;
|
||||
StringRef Name;
|
||||
|
||||
// Support lexicographic sorting.
|
||||
bool operator<(const ELFSymbolData &RHS) const {
|
||||
return SymbolData->getSymbol().getName() <
|
||||
RHS.SymbolData->getSymbol().getName();
|
||||
return Name < RHS.Name;
|
||||
}
|
||||
};
|
||||
|
||||
@ -149,13 +150,13 @@ class ELFObjectWriter : public MCObjectWriter {
|
||||
|
||||
llvm::DenseMap<const MCSectionData *, std::vector<ELFRelocationEntry>>
|
||||
Relocations;
|
||||
DenseMap<const MCSection*, uint64_t> SectionStringTableIndex;
|
||||
StringTableBuilder ShStrTabBuilder;
|
||||
|
||||
/// @}
|
||||
/// @name Symbol Table Data
|
||||
/// @{
|
||||
|
||||
SmallString<256> StringTable;
|
||||
StringTableBuilder StrTabBuilder;
|
||||
std::vector<uint64_t> FileSymbolData;
|
||||
std::vector<ELFSymbolData> LocalSymbolData;
|
||||
std::vector<ELFSymbolData> ExternalSymbolData;
|
||||
@ -676,7 +677,6 @@ void ELFObjectWriter::WriteSymbolTable(MCDataFragment *SymtabF,
|
||||
SectionIndexMapTy &SectionIndexMap) {
|
||||
// The string table must be emitted first because we need the index
|
||||
// into the string table for all the symbol names.
|
||||
assert(StringTable.size() && "Missing string table");
|
||||
|
||||
// FIXME: Make sure the start of the symbol table is aligned.
|
||||
|
||||
@ -1031,27 +1031,6 @@ ELFObjectWriter::computeSymbolTable(MCAssembler &Asm, const MCAsmLayout &Layout,
|
||||
MCELF::SetBinding(Data, ELF::STB_GLOBAL);
|
||||
}
|
||||
|
||||
// Index 0 is always the empty string.
|
||||
StringMap<uint64_t> StringIndexMap;
|
||||
StringTable += '\x00';
|
||||
|
||||
// FIXME: We could optimize suffixes in strtab in the same way we
|
||||
// optimize them in shstrtab.
|
||||
|
||||
for (MCAssembler::const_file_name_iterator it = Asm.file_names_begin(),
|
||||
ie = Asm.file_names_end();
|
||||
it != ie;
|
||||
++it) {
|
||||
StringRef Name = *it;
|
||||
uint64_t &Entry = StringIndexMap[Name];
|
||||
if (!Entry) {
|
||||
Entry = StringTable.size();
|
||||
StringTable += Name;
|
||||
StringTable += '\x00';
|
||||
}
|
||||
FileSymbolData.push_back(Entry);
|
||||
}
|
||||
|
||||
// Add the data for the symbols.
|
||||
for (MCSymbolData &SD : Asm.symbols()) {
|
||||
const MCSymbol &Symbol = SD.getSymbol();
|
||||
@ -1102,7 +1081,6 @@ ELFObjectWriter::computeSymbolTable(MCAssembler &Asm, const MCAsmLayout &Layout,
|
||||
// @@ in defined ones.
|
||||
StringRef Name = Symbol.getName();
|
||||
SmallString<32> Buf;
|
||||
|
||||
size_t Pos = Name.find("@@@");
|
||||
if (Pos != StringRef::npos) {
|
||||
Buf += Name.substr(0, Pos);
|
||||
@ -1110,14 +1088,8 @@ ELFObjectWriter::computeSymbolTable(MCAssembler &Asm, const MCAsmLayout &Layout,
|
||||
Buf += Name.substr(Pos + Skip);
|
||||
Name = Buf;
|
||||
}
|
||||
MSD.Name = StrTabBuilder.add(Name);
|
||||
|
||||
uint64_t &Entry = StringIndexMap[Name];
|
||||
if (!Entry) {
|
||||
Entry = StringTable.size();
|
||||
StringTable += Name;
|
||||
StringTable += '\x00';
|
||||
}
|
||||
MSD.StringIndex = Entry;
|
||||
if (MSD.SectionIndex == ELF::SHN_UNDEF)
|
||||
UndefinedSymbolData.push_back(MSD);
|
||||
else if (Local)
|
||||
@ -1126,6 +1098,21 @@ ELFObjectWriter::computeSymbolTable(MCAssembler &Asm, const MCAsmLayout &Layout,
|
||||
ExternalSymbolData.push_back(MSD);
|
||||
}
|
||||
|
||||
for (auto i = Asm.file_names_begin(), e = Asm.file_names_end(); i != e; ++i)
|
||||
StrTabBuilder.add(*i);
|
||||
|
||||
StrTabBuilder.finalize();
|
||||
|
||||
for (auto i = Asm.file_names_begin(), e = Asm.file_names_end(); i != e; ++i)
|
||||
FileSymbolData.push_back(StrTabBuilder.getOffset(*i));
|
||||
|
||||
for (ELFSymbolData& MSD : LocalSymbolData)
|
||||
MSD.StringIndex = StrTabBuilder.getOffset(MSD.Name);
|
||||
for (ELFSymbolData& MSD : ExternalSymbolData)
|
||||
MSD.StringIndex = StrTabBuilder.getOffset(MSD.Name);
|
||||
for (ELFSymbolData& MSD : UndefinedSymbolData)
|
||||
MSD.StringIndex = StrTabBuilder.getOffset(MSD.Name);
|
||||
|
||||
// Symbols are required to be in lexicographic order.
|
||||
array_pod_sort(LocalSymbolData.begin(), LocalSymbolData.end());
|
||||
array_pod_sort(ExternalSymbolData.begin(), ExternalSymbolData.end());
|
||||
@ -1436,23 +1423,6 @@ void ELFObjectWriter::WriteRelocationsFragment(const MCAssembler &Asm,
|
||||
}
|
||||
}
|
||||
|
||||
static int compareBySuffix(const MCSectionELF *const *a,
|
||||
const MCSectionELF *const *b) {
|
||||
const StringRef &NameA = (*a)->getSectionName();
|
||||
const StringRef &NameB = (*b)->getSectionName();
|
||||
const unsigned sizeA = NameA.size();
|
||||
const unsigned sizeB = NameB.size();
|
||||
const unsigned len = std::min(sizeA, sizeB);
|
||||
for (unsigned int i = 0; i < len; ++i) {
|
||||
char ca = NameA[sizeA - i - 1];
|
||||
char cb = NameB[sizeB - i - 1];
|
||||
if (ca != cb)
|
||||
return cb - ca;
|
||||
}
|
||||
|
||||
return sizeB - sizeA;
|
||||
}
|
||||
|
||||
void ELFObjectWriter::CreateMetadataSections(MCAssembler &Asm,
|
||||
MCAsmLayout &Layout,
|
||||
SectionIndexMapTy &SectionIndexMap,
|
||||
@ -1493,45 +1463,20 @@ void ELFObjectWriter::CreateMetadataSections(MCAssembler &Asm,
|
||||
WriteSymbolTable(F, Asm, Layout, SectionIndexMap);
|
||||
|
||||
F = new MCDataFragment(&StrtabSD);
|
||||
F->getContents().append(StringTable.begin(), StringTable.end());
|
||||
F->getContents().append(StrTabBuilder.data().begin(),
|
||||
StrTabBuilder.data().end());
|
||||
|
||||
F = new MCDataFragment(&ShstrtabSD);
|
||||
|
||||
std::vector<const MCSectionELF*> Sections;
|
||||
for (MCAssembler::const_iterator it = Asm.begin(),
|
||||
ie = Asm.end(); it != ie; ++it) {
|
||||
// Section header string table.
|
||||
for (auto it = Asm.begin(), ie = Asm.end(); it != ie; ++it) {
|
||||
const MCSectionELF &Section =
|
||||
static_cast<const MCSectionELF&>(it->getSection());
|
||||
Sections.push_back(&Section);
|
||||
}
|
||||
array_pod_sort(Sections.begin(), Sections.end(), compareBySuffix);
|
||||
|
||||
// Section header string table.
|
||||
//
|
||||
// The first entry of a string table holds a null character so skip
|
||||
// section 0.
|
||||
uint64_t Index = 1;
|
||||
F->getContents().push_back('\x00');
|
||||
|
||||
for (unsigned int I = 0, E = Sections.size(); I != E; ++I) {
|
||||
const MCSectionELF &Section = *Sections[I];
|
||||
|
||||
StringRef Name = Section.getSectionName();
|
||||
if (I != 0) {
|
||||
StringRef PreviousName = Sections[I - 1]->getSectionName();
|
||||
if (PreviousName.endswith(Name)) {
|
||||
SectionStringTableIndex[&Section] = Index - Name.size() - 1;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
// Remember the index into the string table so we can write it
|
||||
// into the sh_name field of the section header table.
|
||||
SectionStringTableIndex[&Section] = Index;
|
||||
|
||||
Index += Name.size() + 1;
|
||||
F->getContents().append(Name.begin(), Name.end());
|
||||
F->getContents().push_back('\x00');
|
||||
ShStrTabBuilder.add(Section.getSectionName());
|
||||
}
|
||||
ShStrTabBuilder.finalize();
|
||||
F->getContents().append(ShStrTabBuilder.data().begin(),
|
||||
ShStrTabBuilder.data().end());
|
||||
}
|
||||
|
||||
void ELFObjectWriter::CreateIndexedSections(MCAssembler &Asm,
|
||||
@ -1599,7 +1544,7 @@ void ELFObjectWriter::WriteSection(MCAssembler &Asm,
|
||||
|
||||
switch(Section.getType()) {
|
||||
case ELF::SHT_DYNAMIC:
|
||||
sh_link = SectionStringTableIndex[&Section];
|
||||
sh_link = ShStrTabBuilder.getOffset(Section.getSectionName());
|
||||
sh_info = 0;
|
||||
break;
|
||||
|
||||
@ -1680,7 +1625,8 @@ void ELFObjectWriter::WriteSection(MCAssembler &Asm,
|
||||
}
|
||||
}
|
||||
|
||||
WriteSecHdrEntry(SectionStringTableIndex[&Section], Section.getType(),
|
||||
WriteSecHdrEntry(ShStrTabBuilder.getOffset(Section.getSectionName()),
|
||||
Section.getType(),
|
||||
Section.getFlags(), 0, Offset, Size, sh_link, sh_info,
|
||||
Alignment, Section.getEntrySize());
|
||||
}
|
||||
|
@ -12,6 +12,7 @@ add_llvm_library(LLVMObject
|
||||
MachOUniversal.cpp
|
||||
Object.cpp
|
||||
ObjectFile.cpp
|
||||
StringTableBuilder.cpp
|
||||
SymbolicFile.cpp
|
||||
YAML.cpp
|
||||
)
|
||||
|
51
lib/Object/StringTableBuilder.cpp
Normal file
51
lib/Object/StringTableBuilder.cpp
Normal file
@ -0,0 +1,51 @@
|
||||
//===-- StringTableBuilder.cpp - String table building utility ------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/SmallVector.h"
|
||||
#include "llvm/Object/StringTableBuilder.h"
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
static bool compareBySuffix(StringRef a, StringRef b) {
|
||||
size_t sizeA = a.size();
|
||||
size_t sizeB = b.size();
|
||||
size_t len = std::min(sizeA, sizeB);
|
||||
for (size_t i = 0; i < len; ++i) {
|
||||
char ca = a[sizeA - i - 1];
|
||||
char cb = b[sizeB - i - 1];
|
||||
if (ca != cb)
|
||||
return ca > cb;
|
||||
}
|
||||
return sizeA > sizeB;
|
||||
}
|
||||
|
||||
void StringTableBuilder::finalize() {
|
||||
SmallVector<StringRef, 8> Strings;
|
||||
for (auto i = StringIndexMap.begin(), e = StringIndexMap.end(); i != e; ++i)
|
||||
Strings.push_back(i->getKey());
|
||||
|
||||
std::sort(Strings.begin(), Strings.end(), compareBySuffix);
|
||||
|
||||
// FIXME: Starting with a null byte is ELF specific. Generalize this so we
|
||||
// can use the class with other object formats.
|
||||
StringTable += '\x00';
|
||||
|
||||
StringRef Previous;
|
||||
for (StringRef s : Strings) {
|
||||
if (Previous.endswith(s)) {
|
||||
StringIndexMap[s] = StringTable.size() - 1 - s.size();
|
||||
continue;
|
||||
}
|
||||
|
||||
StringIndexMap[s] = StringTable.size();
|
||||
StringTable += s;
|
||||
StringTable += '\x00';
|
||||
Previous = s;
|
||||
}
|
||||
}
|
@ -543,7 +543,7 @@
|
||||
|
||||
// CHECK-ELF: Symbols [
|
||||
// CHECK-ELF: Symbol {
|
||||
// CHECK-ELF: Name: var (6)
|
||||
// CHECK-ELF: Name: var
|
||||
// CHECK-ELF-NEXT: Value:
|
||||
// CHECK-ELF-NEXT: Size:
|
||||
// CHECK-ELF-NEXT: Binding: Global
|
||||
|
@ -313,7 +313,7 @@
|
||||
|
||||
// CHECK-ELF: Symbols [
|
||||
// CHECK-ELF: Symbol {
|
||||
// CHECK-ELF: Name: var (6)
|
||||
// CHECK-ELF: Name: var
|
||||
// CHECK-ELF-NEXT: Value:
|
||||
// CHECK-ELF-NEXT: Size:
|
||||
// CHECK-ELF-NEXT: Binding: Global
|
||||
|
@ -49,7 +49,7 @@
|
||||
// Test that g1 and g2 are local, but g3 is an undefined global.
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: g1 (1)
|
||||
// CHECK: Name: g1
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -58,7 +58,7 @@
|
||||
// CHECK-NEXT: Section: .foo (0x7)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: g2 (4)
|
||||
// CHECK-NEXT: Name: g2
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -68,7 +68,7 @@
|
||||
// CHECK-NEXT: }
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: g3 (7)
|
||||
// CHECK: Name: g3
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -9,7 +9,7 @@
|
||||
.comm common1,1,1
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common1 (1)
|
||||
// CHECK: Name: common1
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 1
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -25,7 +25,7 @@
|
||||
.comm common2,1,1
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common2 (9)
|
||||
// CHECK: Name: common2
|
||||
// CHECK-NEXT: Value: 0x1
|
||||
// CHECK-NEXT: Size: 1
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -39,7 +39,7 @@
|
||||
.comm common6,8,16
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common6 (17)
|
||||
// CHECK: Name: common6
|
||||
// CHECK-NEXT: Value: 0x10
|
||||
// CHECK-NEXT: Size: 8
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -54,7 +54,7 @@
|
||||
.comm common3,4,4
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common3 (25)
|
||||
// CHECK: Name: common3
|
||||
// CHECK-NEXT: Value: 0x4
|
||||
// CHECK-NEXT: Size: 4
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -76,7 +76,7 @@ foo:
|
||||
.comm common4,40,16
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common4 (37)
|
||||
// CHECK: Name: common4
|
||||
// CHECK-NEXT: Value: 0x10
|
||||
// CHECK-NEXT: Size: 40
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -89,7 +89,7 @@ foo:
|
||||
.comm common5,4,4
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: common5 (45)
|
||||
// CHECK: Name: common5
|
||||
// CHECK-NEXT: Value: 0x4
|
||||
// CHECK-NEXT: Size: 4
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -11,7 +11,7 @@ foo.c:
|
||||
bar.c:
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: foo.c (1)
|
||||
// CHECK: Name: foo.c
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -19,7 +19,7 @@ bar.c:
|
||||
// CHECK-NEXT: Other: 0
|
||||
// CHECK-NEXT: Section: Absolute (0xFFF1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK: Name: bar.c (7)
|
||||
// CHECK: Name: bar.c
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -28,7 +28,7 @@ bar.c:
|
||||
// CHECK-NEXT: Section: Absolute (0xFFF1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: bar.c (7)
|
||||
// CHECK: Name: bar.c
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -37,7 +37,7 @@ bar.c:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: foo.c (1)
|
||||
// CHECK: Name: foo.c
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -4,7 +4,7 @@
|
||||
.lcomm B, 32 << 20
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: A (1)
|
||||
// CHECK: Name: A
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 5
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -13,7 +13,7 @@
|
||||
// CHECK-NEXT: Section: .bss (0x3)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: B (3)
|
||||
// CHECK: Name: B
|
||||
// CHECK-NEXT: Value: 0x5
|
||||
// CHECK-NEXT: Size: 33554432
|
||||
// CHECK-NEXT: Binding: Local
|
||||
|
@ -12,7 +12,7 @@
|
||||
|
||||
|
||||
// Test that both a and b show up in the correct section.
|
||||
// SYMBOLS: Name: a (1)
|
||||
// SYMBOLS: Name: a
|
||||
// SYMBOLS-NEXT: Value: 0x0
|
||||
// SYMBOLS-NEXT: Size: 0
|
||||
// SYMBOLS-NEXT: Binding: Local (0x0)
|
||||
@ -21,7 +21,7 @@
|
||||
// SYMBOLS-NEXT: Section: last (0xFF00)
|
||||
// SYMBOLS-NEXT: }
|
||||
// SYMBOLS-NEXT: Symbol {
|
||||
// SYMBOLS-NEXT: Name: b (3)
|
||||
// SYMBOLS-NEXT: Name: b
|
||||
// SYMBOLS-NEXT: Value: 0x1
|
||||
// SYMBOLS-NEXT: Size: 0
|
||||
// SYMBOLS-NEXT: Binding: Local (0x0)
|
||||
@ -32,7 +32,7 @@
|
||||
|
||||
|
||||
// Test that this file has one section too many.
|
||||
// SYMBOLS: Name: last (0)
|
||||
// SYMBOLS: Name: last
|
||||
// SYMBOLS-NEXT: Value: 0x0
|
||||
// SYMBOLS-NEXT: Size: 0
|
||||
// SYMBOLS-NEXT: Binding: Local (0x0)
|
||||
|
@ -7,7 +7,7 @@
|
||||
// CHECK-NEXT: ]
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: baz (5)
|
||||
// CHECK: Name: baz
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -8,7 +8,7 @@ mov %eax,bar
|
||||
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: bar (5)
|
||||
// CHECK: Name: bar
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -17,7 +17,7 @@ mov %eax,bar
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo (1)
|
||||
// CHECK-NEXT: Name: foo
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -5,7 +5,7 @@
|
||||
.set kernbase,0xffffffff80000000
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: kernbase (1)
|
||||
// CHECK: Name: kernbase
|
||||
// CHECK-NEXT: Value: 0xFFFFFFFF80000000
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -26,7 +26,7 @@
|
||||
|
||||
// Test that there is an undefined reference to bar
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: bar (10)
|
||||
// CHECK: Name: bar
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
21
test/MC/ELF/strtab-suffix-opt.s
Normal file
21
test/MC/ELF/strtab-suffix-opt.s
Normal file
@ -0,0 +1,21 @@
|
||||
// RUN: llvm-mc -filetype=obj -triple i686-pc-linux-gnu %s -o - | llvm-readobj -symbols | FileCheck %s
|
||||
|
||||
.text
|
||||
.globl foobar
|
||||
.align 16, 0x90
|
||||
.type foobar,@function
|
||||
foobar:
|
||||
pushl %ebp
|
||||
movl %esp, %ebp
|
||||
subl $8, %esp
|
||||
calll foo
|
||||
calll bar
|
||||
addl $8, %esp
|
||||
popl %ebp
|
||||
retl
|
||||
.Ltmp3:
|
||||
.size foobar, .Ltmp3-foobar
|
||||
|
||||
// CHECK: Name: foobar (1)
|
||||
// CHECK: Name: bar (4)
|
||||
// CHECK: Name: foo (8)
|
@ -18,7 +18,7 @@
|
||||
.long fooE@INDNTPOFF
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: foo1 (1)
|
||||
// CHECK: Name: foo1
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -27,7 +27,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo2 (6)
|
||||
// CHECK-NEXT: Name: foo2
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -36,7 +36,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo3 (11)
|
||||
// CHECK-NEXT: Name: foo3
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -45,7 +45,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo4 (16)
|
||||
// CHECK-NEXT: Name: foo4
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -54,7 +54,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo5 (21)
|
||||
// CHECK-NEXT: Name: foo5
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -63,7 +63,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo6 (26)
|
||||
// CHECK-NEXT: Name: foo6
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -72,7 +72,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo7 (31)
|
||||
// CHECK-NEXT: Name: foo7
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -81,7 +81,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo8 (36)
|
||||
// CHECK-NEXT: Name: foo8
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -90,7 +90,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo9 (41)
|
||||
// CHECK-NEXT: Name: foo9
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -99,7 +99,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: fooA (46)
|
||||
// CHECK-NEXT: Name: fooA
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -108,7 +108,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: fooB (51)
|
||||
// CHECK-NEXT: Name: fooB
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -117,7 +117,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: fooC (56)
|
||||
// CHECK-NEXT: Name: fooC
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -126,7 +126,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: fooD (61)
|
||||
// CHECK-NEXT: Name: fooD
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -135,7 +135,7 @@
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: fooE (66)
|
||||
// CHECK-NEXT: Name: fooE
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -13,7 +13,7 @@ foobar:
|
||||
.long 43
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: foobar (31)
|
||||
// CHECK: Name: foobar
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -23,7 +23,7 @@ foobar:
|
||||
// CHECK-NEXT: }
|
||||
|
||||
// CHECK: Symbol {
|
||||
// CHECK: Name: foo1 (1)
|
||||
// CHECK: Name: foo1
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -32,7 +32,7 @@ foobar:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo2 (6)
|
||||
// CHECK-NEXT: Name: foo2
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -41,7 +41,7 @@ foobar:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo3 (11)
|
||||
// CHECK-NEXT: Name: foo3
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -50,7 +50,7 @@ foobar:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo4 (16)
|
||||
// CHECK-NEXT: Name: foo4
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -59,7 +59,7 @@ foobar:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo5 (21)
|
||||
// CHECK-NEXT: Name: foo5
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -68,7 +68,7 @@ foobar:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: foo6 (26)
|
||||
// CHECK-NEXT: Name: foo6
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -176,7 +176,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym1 (54)
|
||||
// CHECK-NEXT: Name: sym1
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -185,7 +185,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym10 (162)
|
||||
// CHECK-NEXT: Name: sym10
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -194,7 +194,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym11 (176)
|
||||
// CHECK-NEXT: Name: sym11
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -203,7 +203,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym12 (190)
|
||||
// CHECK-NEXT: Name: sym12
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -212,7 +212,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym2 (66)
|
||||
// CHECK-NEXT: Name: sym2
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -221,7 +221,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym3 (78)
|
||||
// CHECK-NEXT: Name: sym3
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -230,7 +230,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym4 (90)
|
||||
// CHECK-NEXT: Name: sym4
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -239,7 +239,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym5 (102)
|
||||
// CHECK-NEXT: Name: sym5
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -248,7 +248,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym6 (114)
|
||||
// CHECK-NEXT: Name: sym6
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -257,7 +257,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym7 (126)
|
||||
// CHECK-NEXT: Name: sym7
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -266,7 +266,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym8 (138)
|
||||
// CHECK-NEXT: Name: sym8
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
@ -275,7 +275,7 @@ alias12:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: sym9 (150)
|
||||
// CHECK-NEXT: Name: sym9
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global (0x1)
|
||||
|
@ -80,7 +80,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar6 (21)
|
||||
// CHECK-NEXT: Name: bar6
|
||||
// CHECK-NEXT: Value: 0x18
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -89,7 +89,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar7 (26)
|
||||
// CHECK-NEXT: Name: bar7
|
||||
// CHECK-NEXT: Value: 0x18
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -98,7 +98,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar8 (31)
|
||||
// CHECK-NEXT: Name: bar8
|
||||
// CHECK-NEXT: Value: 0x1C
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -107,7 +107,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar9 (36)
|
||||
// CHECK-NEXT: Name: bar9
|
||||
// CHECK-NEXT: Value: 0x20
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -116,7 +116,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: .text (0)
|
||||
// CHECK-NEXT: Name: .text
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -125,7 +125,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: .data (0)
|
||||
// CHECK-NEXT: Name: .data
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -134,7 +134,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .data (0x3)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: .bss (0)
|
||||
// CHECK-NEXT: Name: .bss
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Local
|
||||
@ -143,7 +143,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .bss (0x4)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar10 (41)
|
||||
// CHECK-NEXT: Name: bar10
|
||||
// CHECK-NEXT: Value: 0x28
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -152,7 +152,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar11 (47)
|
||||
// CHECK-NEXT: Name: bar11
|
||||
// CHECK-NEXT: Value: 0x30
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -161,7 +161,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar12 (53)
|
||||
// CHECK-NEXT: Name: bar12
|
||||
// CHECK-NEXT: Value: 0x30
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -170,7 +170,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar13 (59)
|
||||
// CHECK-NEXT: Name: bar13
|
||||
// CHECK-NEXT: Value: 0x34
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -179,7 +179,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar14 (65)
|
||||
// CHECK-NEXT: Name: bar14
|
||||
// CHECK-NEXT: Value: 0x38
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -188,7 +188,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar15 (71)
|
||||
// CHECK-NEXT: Name: bar15
|
||||
// CHECK-NEXT: Value: 0x40
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -197,7 +197,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: .text (0x1)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar2 (1)
|
||||
// CHECK-NEXT: Name: bar2
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -206,7 +206,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar3 (6)
|
||||
// CHECK-NEXT: Name: bar3
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Weak
|
||||
@ -215,7 +215,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar4 (11)
|
||||
// CHECK-NEXT: Name: bar4
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
@ -224,7 +224,7 @@ bar15:
|
||||
// CHECK-NEXT: Section: Undefined (0x0)
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: Symbol {
|
||||
// CHECK-NEXT: Name: bar5 (16)
|
||||
// CHECK-NEXT: Name: bar5
|
||||
// CHECK-NEXT: Value: 0x0
|
||||
// CHECK-NEXT: Size: 0
|
||||
// CHECK-NEXT: Binding: Global
|
||||
|
@ -30,10 +30,8 @@ using namespace llvm;
|
||||
// This class has a deliberately small interface, since a lot of
|
||||
// implementation variation is possible.
|
||||
//
|
||||
// TODO: Use an ordered container with a suffix-based comparison in order
|
||||
// to deduplicate suffixes. std::map<> with a custom comparator is likely
|
||||
// to be the simplest implementation, but a suffix trie could be more
|
||||
// suitable for the job.
|
||||
// TODO: Use the StringTable builder from lib/Object instead, since it
|
||||
// will deduplicate suffixes.
|
||||
namespace {
|
||||
class StringTableBuilder {
|
||||
/// \brief Indices of strings currently present in `Buf`.
|
||||
|
@ -4,5 +4,6 @@ set(LLVM_LINK_COMPONENTS
|
||||
)
|
||||
|
||||
add_llvm_unittest(ObjectTests
|
||||
StringTableBuilderTest.cpp
|
||||
YAMLTest.cpp
|
||||
)
|
||||
|
40
unittests/Object/StringTableBuilderTest.cpp
Normal file
40
unittests/Object/StringTableBuilderTest.cpp
Normal file
@ -0,0 +1,40 @@
|
||||
//===----------- StringTableBuilderTest.cpp -------------------------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "llvm/Object/StringTableBuilder.h"
|
||||
#include <string>
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
|
||||
TEST(StringTableBuilderTest, Basic) {
|
||||
StringTableBuilder B;
|
||||
|
||||
B.add("foo");
|
||||
B.add("bar");
|
||||
B.add("foobar");
|
||||
|
||||
B.finalize();
|
||||
|
||||
std::string Expected;
|
||||
Expected += '\x00';
|
||||
Expected += "foobar";
|
||||
Expected += '\x00';
|
||||
Expected += "foo";
|
||||
Expected += '\x00';
|
||||
|
||||
EXPECT_EQ(Expected, B.data());
|
||||
EXPECT_EQ(1U, B.getOffset("foobar"));
|
||||
EXPECT_EQ(4U, B.getOffset("bar"));
|
||||
EXPECT_EQ(8U, B.getOffset("foo"));
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user