@@ -119,25 +119,22 @@ LLDBMemoryReader::getSymbolAddress(const std::string &name) {
119
119
return swift::remote::RemoteAddress (load_addr);
120
120
}
121
121
122
- swift::remote::RemoteAbsolutePointer
123
- LLDBMemoryReader::resolvePointer (swift::remote::RemoteAddress address,
124
- uint64_t readValue) {
122
+ llvm::Optional<swift::remote::RemoteAbsolutePointer>
123
+ LLDBMemoryReader::resolvePointerAsSymbol (swift::remote::RemoteAddress address) {
125
124
// If an address has a symbol, that symbol provides additional useful data to
126
125
// MetadataReader. Without the symbol, MetadataReader can derive the symbol
127
126
// by loading other parts of reflection metadata, but that work has a cost.
128
127
// For lldb, that data loading can be a significant performance hit. Providing
129
128
// a symbol greatly reduces memory read traffic to the process.
130
- auto pointer = swift::remote::RemoteAbsolutePointer (" " , readValue);
131
-
132
129
auto &target = m_process.GetTarget ();
133
130
if (!target.GetSwiftUseReflectionSymbols ())
134
- return pointer ;
131
+ return {} ;
135
132
136
133
llvm::Optional<Address> maybeAddr =
137
134
resolveRemoteAddress (address.getAddressData ());
138
135
// This is not an assert, but should never happen.
139
136
if (!maybeAddr)
140
- return pointer ;
137
+ return {} ;
141
138
142
139
Address addr;
143
140
if (maybeAddr->IsSectionOffset ()) {
@@ -146,21 +143,85 @@ LLDBMemoryReader::resolvePointer(swift::remote::RemoteAddress address,
146
143
} else {
147
144
// `address` is a real load address.
148
145
if (!target.ResolveLoadAddress (address.getAddressData (), addr))
149
- return pointer ;
146
+ return {} ;
150
147
}
151
148
152
149
if (!addr.GetSection ()->CanContainSwiftReflectionData ())
153
- return pointer ;
150
+ return {} ;
154
151
155
152
if (auto *symbol = addr.CalculateSymbolContextSymbol ()) {
156
153
auto mangledName = symbol->GetMangled ().GetMangledName ().GetStringRef ();
157
154
// MemoryReader requires this to be a Swift symbol. LLDB can also be
158
155
// aware of local symbols, so avoid returning those.
159
156
if (swift::Demangle::isSwiftSymbol (mangledName))
160
- return {mangledName, 0 };
157
+ return {{mangledName, 0 }};
158
+ }
159
+
160
+ return {};
161
+ }
162
+
163
+ swift::remote::RemoteAbsolutePointer
164
+ LLDBMemoryReader::resolvePointer (swift::remote::RemoteAddress address,
165
+ uint64_t readValue) {
166
+ Log *log (GetLogIfAllCategoriesSet (LIBLLDB_LOG_TYPES));
167
+
168
+ // We may have gotten a pointer to a process address, try to map it back
169
+ // to a tagged address so further memory reads originating from it benefit
170
+ // from the file-cache optimization.
171
+ swift::remote::RemoteAbsolutePointer process_pointer (" " , readValue);
172
+
173
+ auto &target = m_process.GetTarget ();
174
+ Address addr;
175
+ if (!target.ResolveLoadAddress (readValue, addr)) {
176
+ LLDB_LOGV (log,
177
+ " [MemoryReader] Could not resolve load address of pointer {0:x} "
178
+ " read from {1:x}." ,
179
+ readValue, address.getAddressData ());
180
+ return process_pointer;
181
+ }
182
+
183
+ auto module_containing_pointer = addr.GetSection ()->GetModule ();
184
+
185
+ // Check if the module containing the pointer is registered with
186
+ // LLDBMemoryReader.
187
+ auto pair_iterator = std::find_if (
188
+ m_range_module_map.begin (), m_range_module_map.end (), [&](auto pair) {
189
+ return std::get<ModuleSP>(pair) == module_containing_pointer;
190
+ });
191
+
192
+ // We haven't registered the image that contains the pointer.
193
+ if (pair_iterator == m_range_module_map.end ()) {
194
+ LLDB_LOG (log,
195
+ " [MemoryReader] Could not resolve find module containing pointer "
196
+ " {0:x} read from {1:x}." ,
197
+ readValue, address.getAddressData ());
198
+ return process_pointer;
199
+ }
200
+
201
+ // If the containing image is the first registered one, the image's tagged
202
+ // start address for it is the first tagged address. Otherwise, the previous
203
+ // pair's address is the start tagged address.
204
+ uint64_t start_tagged_address = pair_iterator == m_range_module_map.begin ()
205
+ ? LLDB_FILE_ADDRESS_BIT
206
+ : std::prev (pair_iterator)->first ;
207
+
208
+ uint64_t tagged_address = start_tagged_address + addr.GetFileAddress ();
209
+
210
+ if (tagged_address >= std::get<uint64_t >(*pair_iterator)) {
211
+ // If the tagged address invades the next image's tagged address space,
212
+ // something went wrong. Log it and just return the process address.
213
+ LLDB_LOG (log,
214
+ " [MemoryReader] Pointer {0:x} read from {1:x} resolved to tagged "
215
+ " address {2:x}, which is outside its image address space." ,
216
+ readValue, address.getAddressData (), tagged_address);
217
+ return process_pointer;
161
218
}
162
219
163
- return pointer;
220
+ LLDB_LOGV (log,
221
+ " [MemoryReader] Successfully resolved pointer {0:x} read from "
222
+ " {1:x} to tagged address {2:x}." ,
223
+ readValue, address.getAddressData (), tagged_address);
224
+ return swift::remote::RemoteAbsolutePointer (" " , tagged_address);
164
225
}
165
226
166
227
bool LLDBMemoryReader::readBytes (swift::remote::RemoteAddress address,
0 commit comments