Skip to content

Commit 92596f5

Browse files
authored
Merge pull request #21255 from dcci/mirrorsperf50
[Reflection] Try to read only the reflection sections.
2 parents ee39236 + 04cbdfa commit 92596f5

File tree

1 file changed

+51
-15
lines changed

1 file changed

+51
-15
lines changed

include/swift/Reflection/ReflectionContext.h

Lines changed: 51 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -139,26 +139,60 @@ class ReflectionContext
139139
if (!Command)
140140
return false;
141141

142-
// Read everything including the __TEXT segment.
143-
Buf = this->getReader().readBytes(ImageStart, Command->vmsize);
144-
auto Start = reinterpret_cast<const char *>(Buf.get());
142+
// Find the load command offset.
143+
auto loadCmdOffset = ImageStart.getAddressData() + Offset + sizeof(typename T::Header);
144+
145+
// Read the load command.
146+
auto LoadCmdAddress = reinterpret_cast<const char *>(loadCmdOffset);
147+
auto LoadCmdBuf = this->getReader().readBytes(
148+
RemoteAddress(LoadCmdAddress), sizeof(typename T::SegmentCmd));
149+
auto LoadCmd = reinterpret_cast<typename T::SegmentCmd *>(LoadCmdBuf.get());
150+
151+
// The sections start immediately after the load command.
152+
unsigned NumSect = LoadCmd->nsects;
153+
auto SectAddress = reinterpret_cast<const char *>(loadCmdOffset) +
154+
sizeof(typename T::SegmentCmd);
155+
auto Sections = this->getReader().readBytes(
156+
RemoteAddress(SectAddress), NumSect * sizeof(typename T::Section));
157+
158+
auto Slide = ImageStart.getAddressData() - Command->vmaddr;
159+
std::string Prefix = "__swift5";
160+
uint64_t RangeStart = UINT64_MAX;
161+
uint64_t RangeEnd = UINT64_MAX;
162+
auto SectionsBuf = reinterpret_cast<const char *>(Sections.get());
163+
for (unsigned I = 0; I < NumSect; ++I) {
164+
auto S = reinterpret_cast<typename T::Section *>(
165+
SectionsBuf + (I * sizeof(typename T::Section)));
166+
if (strncmp(S->sectname, Prefix.c_str(), strlen(Prefix.c_str())) != 0)
167+
continue;
168+
if (RangeStart == UINT64_MAX && RangeEnd == UINT64_MAX) {
169+
RangeStart = S->addr + Slide;
170+
RangeEnd = S->addr + S->size + Slide;
171+
continue;
172+
}
173+
RangeStart = std::min(RangeStart, (uint64_t)S->addr + Slide);
174+
RangeEnd = std::max(RangeEnd, (uint64_t)(S->addr + S->size + Slide));
175+
}
176+
177+
if (RangeStart == UINT64_MAX && RangeEnd == UINT64_MAX)
178+
return false;
179+
180+
auto SectBuf = this->getReader().readBytes(RemoteAddress(RangeStart),
181+
RangeEnd - RangeStart);
145182

146183
auto findMachOSectionByName = [&](std::string Name)
147184
-> std::pair<std::pair<const char *, const char *>, uint32_t> {
148-
auto cmdOffset = Start + Offset + sizeof(typename T::Header);
149-
auto SegCmd = reinterpret_cast<typename T::SegmentCmd *>(cmdOffset);
150-
auto SectAddress = reinterpret_cast<const char *>(cmdOffset) +
151-
sizeof(typename T::SegmentCmd);
152-
for (unsigned I = 0; I < SegCmd->nsects; ++I) {
185+
for (unsigned I = 0; I < NumSect; ++I) {
153186
auto S = reinterpret_cast<typename T::Section *>(
154-
SectAddress + (I * sizeof(typename T::Section)));
187+
SectionsBuf + (I * sizeof(typename T::Section)));
155188
if (strncmp(S->sectname, Name.c_str(), strlen(Name.c_str())) != 0)
156189
continue;
157-
auto Slide = ImageStart.getAddressData() - Command->vmaddr;
158190
auto RemoteSecStart = S->addr + Slide;
159-
auto LocalSecStart = RemoteSecStart - ImageStart.getAddressData() + Start;
160-
auto SecSize = S->size;
161-
return {{LocalSecStart, LocalSecStart + SecSize}, 0};
191+
auto SectBufData = reinterpret_cast<const char *>(SectBuf.get());
192+
auto LocalSectStart =
193+
reinterpret_cast<const char *>(SectBufData + RemoteSecStart - RangeStart);
194+
auto LocalSectEnd = reinterpret_cast<const char *>(LocalSectStart + S->size);
195+
return {{LocalSectStart, LocalSectEnd}, 0};
162196
}
163197
return {{nullptr, nullptr}, 0};
164198
};
@@ -178,8 +212,8 @@ class ReflectionContext
178212
ReflStrMdSec.first.first == nullptr)
179213
return false;
180214

181-
auto LocalStartAddress = reinterpret_cast<uintptr_t>(Buf.get());
182-
auto RemoteStartAddress = static_cast<uintptr_t>(ImageStart.getAddressData());
215+
auto LocalStartAddress = reinterpret_cast<uintptr_t>(SectBuf.get());
216+
auto RemoteStartAddress = static_cast<uintptr_t>(RangeStart);
183217

184218
ReflectionInfo info = {
185219
{{FieldMdSec.first.first, FieldMdSec.first.second}, 0},
@@ -212,6 +246,8 @@ class ReflectionContext
212246
}
213247

214248
savedBuffers.push_back(std::move(Buf));
249+
savedBuffers.push_back(std::move(SectBuf));
250+
savedBuffers.push_back(std::move(Sections));
215251
return true;
216252
}
217253

0 commit comments

Comments
 (0)