1 //===- Object.cpp ---------------------------------------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
10 #include "llvm/ADT/DenseSet.h"
17 using namespace object
;
19 void Object::addSymbols(ArrayRef
<Symbol
> NewSymbols
) {
20 for (Symbol S
: NewSymbols
) {
21 S
.UniqueId
= NextSymbolUniqueId
++;
22 Symbols
.emplace_back(S
);
27 void Object::updateSymbols() {
28 SymbolMap
= DenseMap
<size_t, Symbol
*>(Symbols
.size());
29 size_t RawSymIndex
= 0;
30 for (Symbol
&Sym
: Symbols
) {
31 SymbolMap
[Sym
.UniqueId
] = &Sym
;
32 Sym
.RawIndex
= RawSymIndex
;
33 RawSymIndex
+= 1 + Sym
.Sym
.NumberOfAuxSymbols
;
37 const Symbol
*Object::findSymbol(size_t UniqueId
) const {
38 auto It
= SymbolMap
.find(UniqueId
);
39 if (It
== SymbolMap
.end())
44 void Object::removeSymbols(function_ref
<bool(const Symbol
&)> ToRemove
) {
46 std::remove_if(std::begin(Symbols
), std::end(Symbols
),
47 [ToRemove
](const Symbol
&Sym
) { return ToRemove(Sym
); }),
52 Error
Object::markSymbols() {
53 for (Symbol
&Sym
: Symbols
)
54 Sym
.Referenced
= false;
55 for (const Section
&Sec
: Sections
) {
56 for (const Relocation
&R
: Sec
.Relocs
) {
57 auto It
= SymbolMap
.find(R
.Target
);
58 if (It
== SymbolMap
.end())
59 return make_error
<StringError
>("Relocation target " + Twine(R
.Target
) +
61 object_error::invalid_symbol_index
);
62 It
->second
->Referenced
= true;
65 return Error::success();
68 void Object::addSections(ArrayRef
<Section
> NewSections
) {
69 for (Section S
: NewSections
) {
70 S
.UniqueId
= NextSectionUniqueId
++;
71 Sections
.emplace_back(S
);
76 void Object::updateSections() {
77 SectionMap
= DenseMap
<ssize_t
, Section
*>(Sections
.size());
79 for (Section
&S
: Sections
) {
80 SectionMap
[S
.UniqueId
] = &S
;
85 const Section
*Object::findSection(ssize_t UniqueId
) const {
86 auto It
= SectionMap
.find(UniqueId
);
87 if (It
== SectionMap
.end())
92 void Object::removeSections(function_ref
<bool(const Section
&)> ToRemove
) {
93 DenseSet
<ssize_t
> AssociatedSections
;
94 auto RemoveAssociated
= [&AssociatedSections
](const Section
&Sec
) {
95 return AssociatedSections
.count(Sec
.UniqueId
) == 1;
98 DenseSet
<ssize_t
> RemovedSections
;
100 std::remove_if(std::begin(Sections
), std::end(Sections
),
101 [ToRemove
, &RemovedSections
](const Section
&Sec
) {
102 bool Remove
= ToRemove(Sec
);
104 RemovedSections
.insert(Sec
.UniqueId
);
108 // Remove all symbols referring to the removed sections.
109 AssociatedSections
.clear();
112 std::begin(Symbols
), std::end(Symbols
),
113 [&RemovedSections
, &AssociatedSections
](const Symbol
&Sym
) {
114 // If there are sections that are associative to a removed
116 // remove those as well as nothing will include them (and we can't
117 // leave them dangling).
118 if (RemovedSections
.count(Sym
.AssociativeComdatTargetSectionId
) ==
120 AssociatedSections
.insert(Sym
.TargetSectionId
);
121 return RemovedSections
.count(Sym
.TargetSectionId
) == 1;
124 ToRemove
= RemoveAssociated
;
125 } while (!AssociatedSections
.empty());
130 void Object::truncateSections(function_ref
<bool(const Section
&)> ToTruncate
) {
131 for (Section
&Sec
: Sections
) {
132 if (ToTruncate(Sec
)) {
133 Sec
.Contents
= ArrayRef
<uint8_t>();
135 Sec
.Header
.SizeOfRawData
= 0;
140 } // end namespace coff
141 } // end namespace objcopy
142 } // end namespace llvm