402 Commits

Author SHA1 Message Date
nerix
4c7a706589
[LLDB] Simplify libstdc++ string summaries (#146562)
From #143177. This combines the summaries for the pre- and post C++ 11
`std::string` as well as `std::wstring`. In all cases, the data pointer
is reachable through `_M_dataplus._M_p`. It has the correct type (i.e.
`char*`/`wchar_t*`) and it's null terminated, so LLDB knows how to
format it as expected when using `GetSummaryAsCString`.
2025-07-02 11:21:31 +01:00
Michael Buch
aeea062dd4
[lldb][DataFormatter] Unwrap reference type when formatting std::unordered_map (#145872)
Desugar any potential references/typedefs before checking
`isStdTemplate`. Previously, the typename might've been:
```
const std::unordered_map<...> &
```
for references. This patch gets the pointee type before grabbing the
canonical type. `GetNonReferenceType` will unwrap typedefs too, so we
should always end up with a non-reference before we get to
`GetCanonicalType`.

https://github.com/llvm/llvm-project/issues/145847
2025-06-26 17:10:12 +01:00
Charles Zablit
a0329eaa0c
[lldb] upgrade HandleFrameFormatVariable callees to llvm::Expected (#144731)
Upgrade the callees of `HandleFrameFormatVariable`
(`GetDemangledTemplateArguments`, etc), to return a `llvm::Expected`
instead of an `std::optional`.

This patch also bundles the logic of validating the demangled name and
information into a single reusable function to reduce code duplication.
2025-06-23 18:41:48 +02:00
nerix
b14e03d855
[LLDB] Consolidate C++ string buffer summaries (#144258)
As part of https://github.com/llvm/llvm-project/pull/143177, I moved the
non-libc++ specific formatting of `std::string`s out to `CxxStringTypes`
as MSVC's STL `std::string` can also be thought of a pointer+size pair.
I named this kind of string "string buffer".

This PR picks that change, so the MSVC PR can be smaller.
Unfortunately, libstdc++'s `std::string` does not fit this (it also uses
a different string printer function).

This resolves two FIXMEs in the libc++ tests, where empty u16 and u32
strings didn't have any prefix (u/U).
2025-06-17 17:44:37 +01:00
Michael Buch
382e3fdbb4
[lldb][Formatter] Get element type for unordered_maps from __hash_table::value_type (#144517)
https://github.com/llvm/llvm-project/pull/143501 changes usage of
`__hash_value_type` in libcxx to an empty tag type. This type will no
longer have a definition in DWARF. Currently the LLDB unordered_map
formatter deduces the map's `element_type` by looking at the `__cc_`
member of `__hash_value_type`. But that will no longer work because we
only have its forward declaration. Since what we're really after is the
type that `__hash_value_type` is wrapping, we can just look at the
`__hash_table::value_type` typedef. With
https://github.com/llvm/llvm-project/pull/143501 that will now point to
the `std::pair` element type (which used to be what we got from
`__cc_`).

TBD: need to double-check this works for older layouts. Quick glance at
the code makes me suspicious of cases like `unordered_map<std::pair<int,
int>, int>`
2025-06-17 17:37:27 +01:00
Adrian Vogelsgesang
4a46ead8fb
[lldb] Show coro_frame in std::coroutine_handle pretty printer (#141516)
This commit adjusts the pretty printer for `std::coroutine_handle` based
on recent personal experiences with debugging C++20 coroutines:

1. It adds the `coro_frame` member. This member exposes the complete
   coroutine frame contents, including the suspension point id and all
   internal variables which the compiler decided to persist into the
   coroutine frame. While this data is highly compiler-specific, inspecting
   it can help identify the internal state of suspended coroutines.
2. It includes the `promise` and `coro_frame` members, even if
   devirtualization failed and we could not infer the promise type / the
   coro_frame type. Having them available as `void*` pointers can still be
   useful to identify, e.g., which two coroutine handles have the same
   frame / promise pointers.
2025-06-11 14:09:54 +02:00
Pavel Labath
2c4f67794b
[lldb/cmake] Implicitly pass arguments to llvm_add_library (#142583)
If we're not touching them, we don't need to do anything special to pass
them along -- with one important caveat: due to how cmake arguments
work, the implicitly passed arguments need to be specified before
arguments that we handle.

This isn't particularly nice, but the alternative is enumerating all
arguments that can be used by llvm_add_library and the macros it calls
(it also relies on implicit passing of some arguments to
llvm_process_sources).
2025-06-04 11:33:37 +02:00
Jonas Devlieghere
6760857bf3
[lldb] Fix data race in statusline format handling (#142489)
This fixes a data race between the main thread and the default event
handler thread. The statusline format option value was protected by a
mutex, but it was returned as a pointer, allowing one thread to access
it while another was modifying it.

Avoid the data race by returning format values by value instead of by
pointer.
2025-06-03 19:12:30 -07:00
Michael Buch
cb56e15bb3
[lldb][TypeSystem][NFC] CreateFunctionType to take parameters by llvm::ArrayRef (#142620) 2025-06-03 23:37:39 +01:00
Pavel Labath
e9fad0e91c
[lldb] Refactor away UB in SBValue::GetLoadAddress (#141799)
The problem was in calling GetLoadAddress on a value in the error state,
where `ValueObject::GetLoadAddress` could end up accessing the
uninitialized "address type" by-ref return value from `GetAddressOf`.
This probably happened because each function expected the other to
initialize it.

We can guarantee initialization by turning this into a proper return
value.

I've added a test, but it only (reliably) crashes if lldb is built with
ubsan.
2025-06-02 09:39:56 +02:00
nerix
9e9626b3d5
[LLDB] Avoid crashes when inspecting MSVC STL types (#140761)
When inspecting/printing types from MSVC's STL, LLDB would crash because
it assumes these types were from libstdc++. Specifically,
`std::shared_ptr` and `std::optional` would crash because of a null
pointer dereference. I added a minimal test that tests the types with
C++ helpers for libstdc++ (only tests for crashes).

- Fixes #115216 
- Fixes #120310 

This still has one unresolved discussion: What about MS STL types? This
is https://github.com/llvm/llvm-project/issues/24834, but there was a
bit of discussion in #120310 as well. The main issue is that MSVC's STL
uses the same type names as libstdc++ (i.e. neither uses an inline
namespace like libc++ for some types).
2025-05-30 20:43:53 +01:00
Charles Zablit
b8997c07d9
[Demangling] Refactor Demangler range tracking (#140762)
This PR is a subset of the commits made in
https://github.com/swiftlang/llvm-project/pull/10710.

The most notable change is the addition of `PrefixRange` and
`SuffixRange` which are a catch-all to track anything after or before a
function's demangled name. In the case of Swift, this allows to add
support for name highlighting without having to track the range of the
scope and specifiers of a function (this will come in another PR).
2025-05-28 13:53:02 +01:00
Ebuka Ezike
04f9fac622
[lldb] optionally match the __debug namespace for libstdc++ containers. (#140727)
If libstdc++ is compiled with `_GLIBCXX_DEBUG` flag it puts the containers in the namespace `std::__debug`. this causes the summary and synthetic formatters not to match the types. The formatters is updated to optionally match the `__debug::`.

The formatters now clashed with the libc++ containers namespace regex which uses `std::__1` namespace

The libc++ formatter is loaded first, then the libstdc++ since the priority of the formatters in lldb is the last one added.

Fixes #60841
2025-05-27 20:52:51 +01:00
Dave Lee
e424787a95
[lldb] Add templated CompilerType::GetTypeSystem (NFC) (#140424)
Add an overloaded `GetTypeSystem` to specify the expected type system subclass. Changes code from  `GetTypeSystem().dyn_cast_or_null<TypeSystemClang>()` to `GetTypeSystem<TypeSystemClang>()`.
2025-05-21 12:03:58 -07:00
Michael Buch
034eaeddc3
[lldb][DataFormatters] Adjust retrieval of unordered_map element type (#140256)
A user ran into an issue where the libc++ `std::unordered_map` formatter
fails because it can't deduce the `element_type`. That happens because
the `node_type` is a forwad declaration. And, in fact, dsymutil stripped
the definition for `std::__1::__hash_node<...>` for a particular
instantiation. While I'm still unclear whether this is a dsymutil bug,
this patch works around said issue by getting the element type from the
`__table_` member.

Drive-by:
- Set the `m_element_type` in `Update`, which is where the other members
are initialized

I don't have a reduced example of this unfortunately. But the crux of
the issue is that `std::__1::__hash_node<...>` only has a forward
declaration in the dsym. Then trying to call `GetTypeTemplateArgument`
on that `CompilerType` fails. And even if the definition was present in
the dsym it seems like we're stopped in a context where the CU only had
a forward declaration DIE for that type and the `node_type` never ends
up being completed with the definition that lives in another CU.

rdar://150813798
2025-05-20 09:44:26 +01:00
Charles Zablit
0d47a4548c
[lldb][DataFormatters] Change ExtractIndexFromString to return std::optional (#138297)
This PR is in continuation of
https://github.com/llvm/llvm-project/pull/136693.
2025-05-08 12:21:26 +01:00
Charles Zablit
b3d130279f
[lldb] Upgrade GetIndexOfChildWithName to use llvm::Expected (#136693)
This patch replaces the use of `UINT32_MAX` as the error return value of
`GetIndexOfChildWithName` with `llvm::Expected`.


# Tasks to do in another PR

1. Replace `CalculateNumChildrenIgnoringErrors` with
`CalculateNumChildren`. See [this
comment](https://github.com/llvm/llvm-project/pull/136693#discussion_r2056319358).
2. Update `lldb_private::formatters::ExtractIndexFromString` to use
`llvm::Expected`. See [this
comment](https://github.com/llvm/llvm-project/pull/136693#discussion_r2054217536).
3. Create a new class which carries both user and internal errors. See
[this
comment](https://github.com/llvm/llvm-project/pull/136693#discussion_r2056439608).
2025-04-30 11:44:19 +01:00
Michael Buch
ebeae6402d Reland "[lldb][Format] Make function name frame-format variables work without debug-info" (#137757)
This reverts commit da7099290cea7d11b83da01adda8afeb3bcd5362.

Same as the original PR. The failing test-case was resolved in https://github.com/llvm/llvm-project/pull/137763
2025-04-29 11:49:21 +01:00
Michael Buch
64b5bc876a
[lldb][Format] Add function.suffix frame-format variable (#137763)
This patch adds another frame-format variable (currently only
implemented in the CPlusPlus language plugin) that represents the
"suffix" of a function. The name is derived from the `DotSuffix` node of
LLVM's Itanium demangler.

For a function name such as `int foo() (.cold)`, the suffix would be
`(.cold)`.
2025-04-29 10:02:44 +01:00
Michael Buch
da7099290c
Revert "[lldb][Format] Make function name frame-format variables work without debug-info" (#137757)
Reverts llvm/llvm-project#137408

This change broke `lldb/test/Shell/Unwind/split-machine-functions.test`.

The test binary has a symbol named `_Z3foov.cold` and the test expects
the backtrace to print the name of the cold part of the function like
this:

```
# SPLIT: frame #1: {{.*}}`foo() (.cold) +
```
but now it gets

```
frame #1: 0x000055555555514f split-machine-functions.test.tmp`foo() + 12
```
2025-04-29 07:13:04 +01:00
Michael Buch
cebf86eb1d
[lldb][Format] Make function name frame-format variables work without debug-info (#137408)
This patch makes the frame-format variables introduced in
https://github.com/llvm/llvm-project/pull/131836 also work when no
debug-info is available. Previously, we assumed `sc.function` was
available, but without debug-info we might only have `sc.symbol`. We
don't really need the `sc.function` apart from when formatting
arguments.

For the function arguments case I added a fallback that will just print
the arguments we get from the demangler (which is what LLDB does for
stacktraces with no debug-info anyway). Ideally we'd have a separate
`FormatEntity::Entry::Type::FunctionArguments` that will just print the
arguments from the demangler and have something like the following in
the `plugin.cplusplus.display.function-name-format`:
```
{ ${function.formatted-arguments} || ${function.arguments} }
```
I.e., when we can't format the arguments, print the ones from the
demangler. But we currently don't have the `||` operator in the
frame-format language yet.
2025-04-28 10:46:00 +01:00
Michael Buch
e665d95426
[lldb] Highlight basenames in backtraces (#137301)
Also changes the PC value color so it doesn't visually clash with the
function names

Before:
<img width="1510" alt="Screenshot 2025-04-25 at 10 38 58 AM"
src="https://github.com/user-attachments/assets/1ec35ba3-a3d9-4e5b-bac9-fc738bfe6d25"
/>

After:
![Screenshot 2025-04-25 at 4 34
27 PM](https://github.com/user-attachments/assets/3de6e778-ff97-4f47-b361-360e4bbfaede)
2025-04-28 08:29:31 +01:00
Michael Buch
b571aa49b1 [lldb][NFC] Add missing newline between function definitions 2025-04-25 22:52:05 +01:00
Michael Buch
d555b9f9a0 [lldb][CPlusPlus] Add plugin.cplusplus.display.function-name-format setting (#131836)
Adds the new `plugin.cplusplus.display.function-name-format` setting and makes the `${function.name-with-args}` query it for formatting the function name.

One caveat is that the setting can't itself be set to `${function.name-with-args}` because that would cause infinite recursion and blow the stack. I added an XFAILed test-case for it and will address it in a follow-up patch.

https://github.com/llvm/llvm-project/pull/131836
2025-04-25 10:04:27 +01:00
Michael Buch
8b91b44a3b [lldb][Format] Introduce new frame-format variables for function parts (#131836)
Adds new frame-format variables and implements them in the CPlusPlusLanguage plugin.

We use the `DemangledNameInfo` type to retrieve the necessary part of the demangled name.

https://github.com/llvm/llvm-project/pull/131836
2025-04-25 10:04:27 +01:00
Michael Buch
96519028d5 [lldb][DataFormatters] Make data-formatters log to the DataFormatters channel
Currently the data-formatters log to either DataFormatters or Types. The
former is probably more sensible, so log there consistently from all
formatters.
2025-04-23 16:27:23 +01:00
Michael Buch
419fa1b06a
[lldb][DataFormatter] Surface CalculateNumChildren errors in std::vector summary (#135944)
When the data-formatters happen to break (e.g., due to layout changes in
libc++), there's no clear indicator of them failing from a user's
perspective. E.g., for `std::vector`s we would just show:
```
(std::vector<int>) v = size=0 {}
```
which is highly misleading, especially if `v.size()` returns a non-zero
size.

This patch surfaces the various errors that could occur when calculating
the number of children of a vector.

rdar://146964266
2025-04-16 17:57:51 +02:00
Dmitry Vasilyev
e4a672bc17
[LLDB] Reapply refactored CPlusPlusLanguage::MethodName to break lldb-server dependencies (#135033)
The original PR is #132274.

Co-authored-by: @bulbazord Alex Langford
2025-04-14 14:30:09 +04:00
Michael Buch
1e153b782e
[lldb][Format] Display only the inlined frame name in backtraces if available (#135343)
When a frame is inlined, LLDB will display its name in backtraces as
follows:
```
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.3
  * frame #0: 0x0000000100000398 a.out`func() [inlined] baz(x=10) at inline.cpp:1:42
    frame #1: 0x0000000100000398 a.out`func() [inlined] bar() at inline.cpp:2:37
    frame #2: 0x0000000100000398 a.out`func() at inline.cpp:4:15
    frame #3: 0x00000001000003c0 a.out`main at inline.cpp:7:5
    frame #4: 0x000000026eb29ab8 dyld`start + 6812
```
The longer the names get the more confusing this gets because the first
function name that appears is the parent frame. My assumption (which may
need some more surveying) is that for the majority of cases we only care
about the actual frame name (not the parent). So this patch removes all
the special logic that prints the parent frame.

Another quirk of the current format is that the inlined frame name does
not abide by the `${function.name-XXX}` format variables. We always just
print the raw demangled name. With this patch, we would format the
inlined frame name according to the `frame-format` setting (see the
test-cases).

If we really want to have the `parentFrame [inlined] inlinedFrame`
format, we could expose it through a new `frame-format` variable (e..g.,
`${function.inlined-at-name}` and let the user decide where to place
things.
2025-04-13 23:21:52 +01:00
Michael Buch
52e45a79ad
[lldb][Language] Change GetFunctionDisplayName to take SymbolContext by reference (#135536)
Both the `CPlusPlusLanguage` plugins and the Swift language plugin
already assume the `sc != nullptr`. And all `FormatEntity` callsites of
`GetFunctionDisplayName` already check for nullptr before passing `sc`.
This patch makes this pre-condition explicit by changing the parameter
to `const SymbolContext &`. This will help with some upcoming changes in
this area.
2025-04-13 23:19:26 +01:00
Michael Buch
b656915d5a
[lldb][Format][NFCI] Refactor CPlusPlusLanguage::GetFunctionDisplayName into helpers and use LLVM style (#135331)
Same cleanup as in https://github.com/llvm/llvm-project/pull/135031. It
pretty much is the same code that we had to duplicate in the language
plugin. Maybe eventually we'll find a way of getting rid of the
duplication.
2025-04-11 11:01:27 +01:00
David Spickett
a29be9f28e
Revert "[LLDB] Refactored CPlusPlusLanguage::MethodName to break lldb-server dependencies" (#134995)
Reverts llvm/llvm-project#132274

Broke a test on LLDB Widows on Arm:
https://lab.llvm.org/buildbot/#/builders/141/builds/7726
```
FAIL: test_dwarf (lldbsuite.test.lldbtest.TestExternCSymbols.test_dwarf)
<...>
    self.assertTrue(self.res.Succeeded(), msg + output)

AssertionError: False is not true : Command 'expression -- foo()' did not return successfully

Error output:

error: Couldn't look up symbols:

  int foo(void)

Hint: The expression tried to call a function that is not present in the target, perhaps because it was optimized out by the compiler.
```
2025-04-09 13:16:23 +01:00
Dmitry Vasilyev
fbc6241d3a
[LLDB] Refactored CPlusPlusLanguage::MethodName to break lldb-server dependencies (#132274)
This patch addresses the issue #129543.
After this patch the size of lldb-server is reduced by 9MB.

Co-authored-by: @bulbazord Alex Langford
2025-04-09 09:11:56 +04:00
Adrian Prantl
878a64f94a
[lldb] Upgrade CompilerType::GetBitSize to return llvm::Expected (#129601)
This patch pushes the error handling boundary for the GetBitSize()
methods from Runtime into the Type and CompilerType APIs. This makes it
easier to diagnose problems thanks to more meaningful error messages
being available. GetBitSize() is often the first thing LLDB asks about a
type, so this method is particularly important for a better user
experience.

rdar://145667239
2025-03-05 10:21:19 -08:00
Michael Buch
a377cdd23d
[lldb][TypeSystemClang] Add support for floating point template argument constants (#127206)
This patch adds support for template arguments of
`clang::TemplateArgument::ArgKind::StructuralValue` kind (added in
https://github.com/llvm/llvm-project/pull/78041). These are used for
non-type template parameters such as floating point constants. When LLDB
created `clang::NonTypeTemplateParmDecl`s, it previously assumed
integral values, this patch accounts for structural values too.

Anywhere LLDB assumed a `DW_TAG_template_value_parameter` was
`Integral`, it will now also check for `StructuralValue`, and will
unpack the `TemplateArgument` value and type accordingly.

We can rely on the fact that any `TemplateArgument` of `StructuralValue`
kind that the `DWARFASTParserClang` creates will have a valid value,
because it gets those from `DW_AT_const_value`.
2025-02-17 22:03:53 +00:00
Dave Lee
6fde8fe9ad
[lldb] Provide default impl for MightHaveChildren (NFC) (#119977)
The vast majority of `SyntheticChildrenFrontEnd` subclasses provide
children, and as such implement `MightHaveChildren` with a constant
value of `true`. This change makes `true` the default value. With this
change, `MightHaveChildren` only needs to be implemented by synthetic
providers that can return `false`, which is only 3 subclasses.
2025-02-17 11:19:14 -08:00
Zequan Wu
e269c2b5fa
[lldb] Show value for libcxx and libstdcxx summary and remove pointer value in libcxx container summary (#125294)
This has two changes:
1. Set show value for libcxx and libstdcxx summary provider. This will
print the pointer value for both pointer type and reference type.
2. Remove pointer value printing in libcxx container summary.

Discussion:

https://discourse.llvm.org/t/lldb-hides-raw-pointer-value-for-libcxx-and-libstdcxx-pointer-types-in-summary-string/84226
2025-02-03 14:34:20 -05:00
Greg Clayton
b7722fbcab
[lldb] Fix std::unordered_* synthetic children when typedefs are used. (#123125)
There was a bug in both the GNU and libc++ library synthetic child
providers when a typedef was used in the type of the variable. Previous
code was looking at the top level typename to try and determine if
std::unordered_ was a map or set and this failed when typedefs were
being used. This patch fixes both C++ library synthetic child providers
with updated tests.
2025-01-15 16:30:45 -08:00
Jonas Devlieghere
b852fb1ec5
[lldb] Move ValueObject into its own library (NFC) (#113393)
ValueObject is part of lldbCore for historical reasons, but conceptually
it deserves to be its own library. This does introduce a (link-time) circular
dependency between lldbCore and lldbValueObject, which is unfortunate
but probably unavoidable because so many things in LLDB rely on
ValueObject. We already have cycles and these libraries are never built
as dylibs so while this doesn't improve the situation, it also doesn't
make things worse.

The header includes were updated with the following command:

```
find . -type f -exec sed -i.bak "s%include \"lldb/Core/ValueObject%include \"lldb/ValueObject/ValueObject%" '{}' \;
```
2024-10-24 20:20:48 -07:00
Michael Buch
9e9b1178ca
[lldb] Support new libc++ __compressed_pair layout (#96538)
This patch is in preparation for the `__compressed_pair` refactor in
https://github.com/llvm/llvm-project/pull/76756.

This is mostly reviewable now. With the new layout we no longer need to
unwrap the `__compressed_pair`. Instead, we just need to look for child
members. E.g., to get to the underlying pointer of `std::unique_ptr` we
no longer do,
```
GetFirstValueOfCXXCompressedPair(GetChildMemberWithName("__ptr_"))

```
but instead do
```
GetChildMemberWithName("__ptr_")
```

We need to be slightly careful because previously the
`__compressed_pair` had a member called `__value_`, whereas now
`__value_` might be a member of the class that used to hold the
`__compressed_pair`. So before unwrapping the pair, we added checks for
`isOldCompressedLayout` (not sure yet whether folding this check into
`GetFirstValueOfCXXCompressedPair` is better).
2024-09-16 10:11:49 +01:00
Adrian Prantl
a0dd90eb7d
[lldb] Make conversions from llvm::Error explicit with Status::FromEr… (#107163)
…ror() [NFC]
2024-09-05 12:19:31 -07:00
Pavel Labath
a5f03b4adc
[lldb] Support "dereferencing" std::optional in frame var (#107077) 2024-09-03 13:22:31 +02:00
Michael Buch
fe8933ba21
[lldb][DataFormatter] Simplify std::map formatter (#97579)
Depends on:
* https://github.com/llvm/llvm-project/pull/97544
* https://github.com/llvm/llvm-project/pull/97549
* https://github.com/llvm/llvm-project/pull/97551

This patch tries to simplify the way in which the `std::map` formatter
goes from the root `__tree` pointer to a specific key/value pair.

Previously we would:
1. synthesize a structure that mimicked what `__iter_pointer` looked
like in memory
2. call `GetChildCompilerTypeAtIndex` on it to find the byte offset at
which the pair was located in the synthesized structure
3. finally, use that offset through a call to
`GetSyntheticChildAtOffset` to retrieve the key/value pair

Not only was this logic hard to follow, and encoded the libc++ layout in
non-obvious ways, it was also fragile to alignment miscalculations
(https://github.com/llvm/llvm-project/pull/97443); this would break once
the new layout of std::map landed as part of
https://github.com/https://github.com/llvm/llvm-project/issues/93069.

Instead, this patch simply casts the `__iter_pointer` to the
`__node_pointer` and uses a straightforward
`GetChildMemberWithName("__value_")` to get to the key/value we care
about. This allows us to get rid of some support infrastructure/class
state.

Ideally we would fix the underlying alignment issue, but this unblocks
the libc++ refactor in the interim, while also benefitting the formatter
in terms of readability (in my opinion).
2024-07-08 17:19:25 +01:00
Michael Buch
9dca3ac2ef
[lldb][DataFormatter] Simplify libc++ std::map::iterator formatter (#97713)
Depends on https://github.com/llvm/llvm-project/pull/97687

Similar to https://github.com/llvm/llvm-project/pull/97579, this patch
simplifies the way in which we retrieve the key/value pair of a
`std::map` (in this case of the `std::map::iterator`).

We do this for the same reason: not only was the old logic hard to
follow, and encoded the libc++ layout in non-obvious ways, it was also
fragile to alignment miscalculations
(https://github.com/llvm/llvm-project/pull/97443); this would break once
the new layout of std::map landed as part of
https://github.com/llvm/llvm-project/issues/93069.

Instead, this patch simply casts the `__iter_pointer` to the
`__node_pointer` and uses a straightforward
`GetChildMemberWithName("__value_")` to get to the key/value we care
about.

We can eventually re-use the core-part of the `std::map` and
`std::map::iterator` formatters. But it will be an easier to change to
review once both simplifications landed.
2024-07-08 15:56:05 +01:00
Michael Buch
da827d0896
[lldb][DataFormatter] Simplify std::unordered_map::iterator formatter (#97754)
Depends on https://github.com/llvm/llvm-project/pull/97752

This patch changes the way we retrieve the key/value pair in the
`std::unordered_map::iterator` formatter (similar to how we are changing
it for `std::map::iterator` in
https://github.com/llvm/llvm-project/pull/97713, the motivations being
the same).

The old logic was not very easy to follow, and encoded the libc++ layout
in non-obvious ways. But mainly it was also fragile to alignment
miscalculations (https://github.com/llvm/llvm-project/pull/97443); this
would break once the new layout of `std::unordered_map` landed as part
of https://github.com/llvm/llvm-project/issues/93069.

Instead, this patch simply casts the `__hash_iterator` to a
`__node_pointer` (which is what libc++ does too) and uses a
straightforward `GetChildMemberWithName("__value_")` to get to the
key/value we care about.

The `std::unordered_map` already does it this way, so we align the
iterator counterpart to do the same. We can eventually re-use the
core-part of the `std::unordered_map` and `std::unordered_map::iterator`
formatters. But it will be an easier to change to review once both
simplifications landed.
2024-07-08 14:38:58 +01:00
Michael Buch
cb72aecea6
[lldb][DataFormatter] Move std::unordered_map::iterator formatter into LibCxxUnorderedMap.cpp (#97752)
Similar to how we moved the `std::map::iterator` formatter in
https://github.com/llvm/llvm-project/pull/97687, do the same for
`std::unordered_map::iterator`.

Again the `unordered_map` and `unordered_map::iterator` formatters try
to do very similar things: retrieve data out of the map. The iterator
formatter does this in a fragile way (similar to how `std::map` does it,
see https://github.com/llvm/llvm-project/pull/97579). Thus we will be
refactoring the `std::unordered_map::iterator` in upcoming patches.
Having it in `LibCxxUnorderedMap` will allow us to re-use some of the
logic (and we won't have to repeat some of the clarification comments).
2024-07-08 13:48:06 +01:00
Michael Buch
1e6dfc6248
[lldb][DataFormatter] Remove support for old std::map layout (#97549)
We currently supported the layout from pre-2016 (before the layout
change in
[14caaddd3f08e798dcd9ac0ddfc](https://github.com/llvm/llvm-project/commit/14caaddd3f08e798dcd9ac0ddfc)).
We have another upcoming layout change in `__tree` and `map` (as part of
https://github.com/llvm/llvm-project/issues/93069) which will likely
require rewriting parts of this formatter. Removing the support for the
pre-2016 layout will make those changes more straightforward to
review/maintain.

Being backward compatible would be great but we have no tests that
actually verify that the old layout still works (and our oldest matrix
bot tests clang-15). If anyone feels strongly about keeping this layout,
we could possibly factor out that logic and keep it around.
2024-07-08 13:47:44 +01:00
Michael Buch
fbd1b6567a
[lldb][DataFormatter][NFC] Move std::map iterator formatter into LibCxxMap.cpp (#97687)
The two formatters follow very similar techniques to retrieve data out
of the map. We're changing this for `std::map` in
https://github.com/llvm/llvm-project/pull/97579 and plan to change it in
the same way for the iterator formatter. Having them in the same place
will allow us to re-use some of the logic (and we won't have to repeat
some of the clarification comments).
2024-07-04 17:06:10 +01:00
Michael Buch
30df62992e [lldb][DataFormatter][NFC] Remove duplicate null-check in std::map iterator formatter
The nullness is already checked a few lines before this.
2024-07-04 08:51:28 +02:00
Michael Buch
a017653376
[lldb][DataFormatter][NFC] Factor out MapIterator logic into separate helper (#97544)
This patch factors all the logic for advancing the `MapIterator` out of
`GetChildAtIndex`. This, in my opinion, helps readability, and will be
useful for upcoming cleanups in this area.

While here, some drive-by changes:
* added a couple of clarification comments
* fixed a variable name typo
* turned the `return lldb::ValueObjectSP()` into `return nullptr`
* added an assertion to make sure we keep the iterator cache in a valid
state
2024-07-03 19:54:20 +02:00