Skip to content

Commit 5b3e97d

Browse files
author
Davide Italiano
committed
[Reflection] Try to read only the reflection sections.
(instead of the whole object).
1 parent e231ae1 commit 5b3e97d

File tree

1 file changed

+48
-4
lines changed

1 file changed

+48
-4
lines changed

include/swift/Reflection/ReflectionContext.h

Lines changed: 48 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -140,9 +140,49 @@ class ReflectionContext
140140
return false;
141141

142142
// Read everything including the __TEXT segment.
143-
Buf = this->getReader().readBytes(ImageStart, Command->vmsize);
143+
// Buf = this->getReader().readBytes(ImageStart, Command->vmsize);
144144
auto Start = reinterpret_cast<const char *>(Buf.get());
145145

146+
// Find the load command offset.
147+
auto loadCmdOffset = Start + Offset + sizeof(typename T::Header);
148+
149+
// Read the load command.
150+
auto LoadCmdAddress = reinterpret_cast<const char *>(loadCmdOffset);
151+
auto LoadCmdBuf = this->getReader().readBytes(
152+
RemoteAddress(LoadCmdAddress), sizeof(typename T::SegmentCmd));
153+
auto LoadCmd = reinterpret_cast<typename T::SegmentCmd *>(LoadCmdBuf.get());
154+
155+
// The sections start immediately after the load command.
156+
unsigned NumSect = LoadCmd->nsects;
157+
auto SectAddress = reinterpret_cast<const char *>(loadCmdOffset) +
158+
sizeof(typename T::SegmentCmd);
159+
auto Sections = this->getReader().readBytes(
160+
RemoteAddress(SectAddress), NumSect * sizeof(typename T::Section));
161+
162+
std::string Prefix = "__swift5";
163+
uint64_t RangeStart = UINT64_MAX;
164+
uint64_t RangeEnd = UINT64_MAX;
165+
for (unsigned I = 0; I < NumSect; ++I) {
166+
auto S = reinterpret_cast<typename T::Section *>(
167+
SectAddress + (I * sizeof(typename T::Section)));
168+
if (strncmp(S->sectname, Prefix.c_str(), strlen(Prefix.c_str())) != 0)
169+
continue;
170+
if (RangeStart == UINT64_MAX && RangeEnd == UINT64_MAX) {
171+
RangeStart = S->addr;
172+
RangeEnd = S->addr + S->size;
173+
continue;
174+
}
175+
RangeStart = std::min(RangeStart, (uint64_t)S->addr);
176+
RangeEnd = std::max(RangeEnd, (uint64_t)(S->addr + S->size));
177+
}
178+
179+
if (RangeStart == UINT64_MAX && RangeEnd == UINT64_MAX)
180+
return false;
181+
182+
auto Slide = ImageStart.getAddressData() - Command->vmaddr;
183+
auto SectBuf = this->getReader().readBytes(RemoteAddress(RangeStart),
184+
RangeEnd - RangeStart);
185+
146186
auto findMachOSectionByName = [&](std::string Name)
147187
-> std::pair<std::pair<const char *, const char *>, uint32_t> {
148188
auto cmdOffset = Start + Offset + sizeof(typename T::Header);
@@ -156,9 +196,13 @@ class ReflectionContext
156196
continue;
157197
auto Slide = ImageStart.getAddressData() - Command->vmaddr;
158198
auto RemoteSecStart = S->addr + Slide;
159-
auto LocalSecStart = RemoteSecStart - ImageStart.getAddressData() + Start;
160-
auto SecSize = S->size;
161-
return {{LocalSecStart, LocalSecStart + SecSize}, 0};
199+
auto LocalSectBuf =
200+
this->getReader().readBytes(RemoteAddress(RemoteSecStart), S->size);
201+
auto LocalSectStart =
202+
reinterpret_cast<const char *>(LocalSectBuf.get());
203+
auto LocalSectEnd =
204+
reinterpret_cast<const char *>(LocalSectBuf.get()) + S->size;
205+
return {{LocalSectStart, LocalSectEnd}, 0};
162206
}
163207
return {{nullptr, nullptr}, 0};
164208
};

0 commit comments

Comments
 (0)