1 //===- SectionSymbolSet.cpp -----------------------------------------------===//
2 //
3 // The MCLinker Project
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 #include "mcld/LD/SectionSymbolSet.h"
10
11 #include "mcld/Fragment/FragmentRef.h"
12 #include "mcld/LD/EhFrame.h"
13 #include "mcld/LD/LDFileFormat.h"
14 #include "mcld/LD/LDSection.h"
15 #include "mcld/LD/LDSymbol.h"
16 #include "mcld/LD/NamePool.h"
17 #include "mcld/LD/RelocData.h"
18 #include "mcld/LD/ResolveInfo.h"
19 #include "mcld/LD/SectionData.h"
20
21 namespace mcld {
22
23 //===----------------------------------------------------------------------===//
24 // SectionSymbolSet
25 //===----------------------------------------------------------------------===//
26
SectionSymbolSet()27 SectionSymbolSet::SectionSymbolSet() {
28 m_pSectionSymbolMap = new SectHashTableType(16);
29 }
30
~SectionSymbolSet()31 SectionSymbolSet::~SectionSymbolSet() {
32 delete m_pSectionSymbolMap;
33 }
34
add(LDSection & pOutSect,NamePool & pNamePool)35 bool SectionSymbolSet::add(LDSection& pOutSect, NamePool& pNamePool) {
36 // create the resolveInfo for this section symbol
37 llvm::StringRef sym_name = llvm::StringRef(pOutSect.name());
38 ResolveInfo* sym_info = pNamePool.createSymbol(sym_name,
39 false,
40 ResolveInfo::Section,
41 ResolveInfo::Define,
42 ResolveInfo::Local,
43 0x0, // size
44 ResolveInfo::Default);
45
46 // create the output section symbol and set its fragRef to the first fragment
47 // of the section
48 LDSymbol* sym = LDSymbol::Create(*sym_info);
49 sym_info->setSymPtr(sym);
50
51 // insert the symbol to the Section to Symbol hash map
52 bool exist = false;
53 SectHashTableType::entry_type* entry =
54 m_pSectionSymbolMap->insert(&pOutSect, exist);
55 assert(!exist);
56 entry->setValue(sym);
57
58 return true;
59 }
60
finalize(LDSection & pOutSect,SymbolTable & pSymTab,bool relocatable)61 bool SectionSymbolSet::finalize(LDSection& pOutSect,
62 SymbolTable& pSymTab,
63 bool relocatable) {
64 if (!relocatable && pOutSect.size() == 0)
65 return true;
66
67 LDSymbol* sym = get(pOutSect);
68 assert(sym != NULL);
69 SectionData* data = NULL;
70 switch (pOutSect.kind()) {
71 case LDFileFormat::Relocation:
72 // Relocation section should not have section symbol.
73 return true;
74
75 case LDFileFormat::EhFrame:
76 if (EhFrame* ehframe = pOutSect.getEhFrame())
77 data = ehframe->getSectionData();
78 break;
79
80 default:
81 data = pOutSect.getSectionData();
82 break;
83 }
84 FragmentRef* frag_ref;
85 if (data && !data->empty())
86 frag_ref = FragmentRef::Create(data->front(), 0x0);
87 else
88 frag_ref = FragmentRef::Null();
89 sym->setFragmentRef(frag_ref);
90 // push symbol into output symbol table
91 pSymTab.add(*sym);
92
93 return true;
94 }
95
get(const LDSection & pOutSect)96 LDSymbol* SectionSymbolSet::get(const LDSection& pOutSect) {
97 SectHashTableType::iterator entry = m_pSectionSymbolMap->find(&pOutSect);
98 return entry.getEntry()->value();
99 }
100
get(const LDSection & pOutSect) const101 const LDSymbol* SectionSymbolSet::get(const LDSection& pOutSect) const {
102 SectHashTableType::iterator entry = m_pSectionSymbolMap->find(&pOutSect);
103 return entry.getEntry()->value();
104 }
105
106 } // namespace mcld
107