mirror of
https://github.com/boostorg/unordered.git
synced 2025-05-09 23:23:59 +00:00
Write docs for GDB pretty-printers
This commit is contained in:
parent
7f9aa8505f
commit
0bca47c690
@ -12,6 +12,7 @@
|
||||
`boost::concurrent_flat_set` operations to allow for safe mutable modification of elements
|
||||
({github-pr-url}/265[PR#265^]).
|
||||
* In Visual Studio Natvis, supported any container with an allocator that uses fancy pointers. This applies to any fancy pointer type, as long as the proper Natvis customization point "Intrinsic" functions are written for the fancy pointer type.
|
||||
* Added GDB pretty-printers for all containers and iterators. For a container with an allocator that uses fancy pointers, these only work if the proper pretty-printer is written for the fancy pointer type itself.
|
||||
|
||||
== Release 1.86.0
|
||||
|
||||
|
@ -24,3 +24,67 @@ Iterators are displayed similarly to their standard counterparts. An iterator is
|
||||
=== Fancy pointers
|
||||
|
||||
The container visualizations also work if you are using fancy pointers in your allocator, such as `boost::interprocess::offset_ptr`. While this is rare, Boost.Unordered has natvis customization points to support any type of fancy pointer. `boost::interprocess::offset_ptr` has support already defined in the Boost.Interprocess library, and you can add support to your own type by following the instructions contained in a comment near the end of the file link:https://github.com/boostorg/unordered/blob/develop/extra/boost_unordered.natvis[/extra/boost_unordered.natvis].
|
||||
|
||||
== GDB Pretty-Printers
|
||||
|
||||
All containers and iterators have a custom GDB pretty-printer.
|
||||
|
||||
=== Using in your project
|
||||
|
||||
Always, when using pretty-printers, you must enable pretty-printing like below. This is typically a one-time setup.
|
||||
|
||||
```plaintext
|
||||
(gdb) set print pretty on
|
||||
```
|
||||
|
||||
By default, if you compile into an ELF binary format, your binary will contain the Boost.Unordered pretty-printers. To use the embedded pretty-printers, ensure you allow auto-loading like below. This must be done every time you load GDB, or add it to a ".gdbinit" file.
|
||||
|
||||
```plaintext
|
||||
(gdb) add-auto-load-safe-path [/path/to/executable]
|
||||
```
|
||||
|
||||
You can choose to compile your binary _without_ embedding the pretty-printers by defining `BOOST_ALL_NO_EMBEDDED_GDB_PRINTERS`, which disables the embedded GDB pretty-printers for all Boost libraries that have this feature.
|
||||
|
||||
You can load the pretty-printers externally from the non-embedded Python script. Add the script, link:https://github.com/boostorg/unordered/blob/develop/extra/boost_unordered_printers.py[/extra/boost_unordered_printers.py], using the `source` command as shown below.
|
||||
|
||||
```plaintext
|
||||
(gdb) source [/path/to/boost]/libs/unordered/extra/boost_unordered_printers.py
|
||||
```
|
||||
|
||||
=== Visualization structure
|
||||
|
||||
The visualizations mirror the standard unordered containers. The map containers display an association from key to mapped value. The set containers display an association from index to value. An iterator is either displayed with its item, or as an end iterator. Here is what may be shown for an example `boost::unordered_map`, an example `boost::unordered_set`, and their respective begin and end iterators.
|
||||
|
||||
```plaintext
|
||||
(gdb) print example_unordered_map
|
||||
$1 = boost::unordered_map with 3 elements = {["C"] = "c", ["B"] = "b", ["A"] = "a"}
|
||||
(gdb) print example_unordered_map_begin
|
||||
$2 = iterator = { {first = "C", second = "c"} }
|
||||
(gdb) print example_unordered_map_end
|
||||
$3 = iterator = { end iterator }
|
||||
(gdb) print example_unordered_set
|
||||
$4 = boost::unordered_set with 3 elements = {[0] = "c", [1] = "b", [2] = "a"}
|
||||
(gdb) print example_unordered_set_begin
|
||||
$5 = iterator = { "c" }
|
||||
(gdb) print example_unordered_set_end
|
||||
$6 = iterator = { end iterator }
|
||||
```
|
||||
|
||||
The other containers are identical other than replacing "`boost::unordered_{map|set}`" with the appropriate template name when displaying the container itself. Note that each sub-element (i.e. the key, the mapped value, or the value) is displayed based on its own printing settings which may include its own pretty-printer.
|
||||
|
||||
Both the SIMD and the non-SIMD implementations are viewable through the GDB pretty-printers.
|
||||
|
||||
For open-addressing containers where xref:#hash_quality_container_statistics[container statistics] are enabled, you can obtain these statistics by calling `get_stats()` on the container, from within GDB. This is overridden in GDB as an link:https://sourceware.org/gdb/current/onlinedocs/gdb.html/Xmethod-API.html[xmethod], so it will not invoke any C++ synchronization code. See the following printout as an example for the expected format.
|
||||
|
||||
```plaintext
|
||||
(gdb) print example_flat_map.get_stats()
|
||||
$1 = [stats] = {[insertion] = {[count] = 5, [probe_length] = {avg = 1.0, var = 0.0, dev = 0.0}},
|
||||
[successful_lookup] = {[count] = 0, [probe_length] = {avg = 0.0, var = 0.0, dev = 0.0},
|
||||
[num_comparisons] = {avg = 0.0, var = 0.0, dev = 0.0}}, [unsuccessful_lookup] = {[count] = 5,
|
||||
[probe_length] = {avg = 1.0, var = 0.0, dev = 0.0},
|
||||
[num_comparisons] = {avg = 0.0, var = 0.0, dev = 0.0}}}
|
||||
```
|
||||
|
||||
=== Fancy pointers
|
||||
|
||||
The pretty-printers also work if you are using fancy pointers in your allocator, such as `boost::interprocess::offset_ptr`. While this is rare, Boost.Unordered has GDB pretty-printer customization points to support any type of fancy pointer. `boost::interprocess::offset_ptr` has support already defined in the Boost.Interprocess library, and you can add support to your own type by following the instructions contained in a comment near the end of the file link:https://github.com/boostorg/unordered/blob/develop/extra/boost_unordered_printers.py[/extra/boost_unordered_printers.py].
|
||||
|
@ -233,3 +233,52 @@ def boost_unordered_build_pretty_printer():
|
||||
return pp
|
||||
|
||||
gdb.printing.register_pretty_printer(gdb.current_objfile(), boost_unordered_build_pretty_printer())
|
||||
|
||||
|
||||
|
||||
""" Fancy pointer support """
|
||||
|
||||
"""
|
||||
To allow your own fancy pointer type to interact with Boost.Unordered GDB pretty-printers,
|
||||
create a pretty-printer for your own type with the following additional methods.
|
||||
|
||||
(Note, this is assuming the presence of a type alias `pointer` for the underlying
|
||||
raw pointer type, Substitute whichever name is applicable in your case.)
|
||||
|
||||
`boost_to_address(fancy_ptr)`
|
||||
* A static method, but `@staticmethod` is not required
|
||||
* Parameter `fancy_ptr` of type `gdb.Value`
|
||||
* Its `.type` will be your fancy pointer type
|
||||
* Returns a `gdb.Value` with the raw pointer equivalent to your fancy pointer
|
||||
* This method should be equivalent to calling `operator->()` on your fancy pointer in C++
|
||||
|
||||
`boost_next(raw_ptr, offset)`
|
||||
* Parameter `raw_ptr` of type `gdb.Value`
|
||||
* Its `.type` will be `pointer`
|
||||
* Parameter `offset`
|
||||
* Either has integer type, or is of type `gdb.Value` with an underlying integer
|
||||
* Returns a `gdb.Value` with the raw pointer equivalent to your fancy pointer, as if you did the following operations
|
||||
1. Convert the incoming raw pointer to your fancy pointer
|
||||
2. Use operator+= to add the offset to the fancy pointer
|
||||
3. Convert back to the raw pointer
|
||||
* Note, you will not actually do these operations as stated. You will do equivalent lower-level operations that emulate having done the above
|
||||
* Ultimately, it will be as if you called `operator+()` on your fancy pointer in C++, but using only raw pointers
|
||||
|
||||
Example
|
||||
```
|
||||
class MyFancyPtrPrinter:
|
||||
...
|
||||
|
||||
# Equivalent to `operator->()`
|
||||
def boost_to_address(fancy_ptr):
|
||||
...
|
||||
return ...
|
||||
|
||||
# Equivalent to `operator+()`
|
||||
def boost_next(raw_ptr, offset):
|
||||
...
|
||||
return ...
|
||||
|
||||
...
|
||||
```
|
||||
"""
|
||||
|
Loading…
x
Reference in New Issue
Block a user