Exception-awareness for gnu_libstdcpp formatters ; Documentation update
git-svn-id: https://llvm.org/svn/llvm-project/llvdb/trunk@138236 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/www/varformats.html b/www/varformats.html
index 3b234c9..2a1540f 100755
--- a/www/varformats.html
+++ b/www/varformats.html
@@ -51,20 +51,21 @@
-> -2, z="3")<br>
</code> </p>
- <p>There are two kinds of printing options: <span
- style="font-style: italic;">summary</span> and <span
- style="font-style: italic;">format</span>. While a
- detailed description of both will be given below, one
- can briefly say that a summary is mainly used for
- aggregate types, while a format is attached to primitive
- types.</p>
+ <p>There are several features related to data visualization: <span
+ style="font-style: italic;">formats</span>, <span
+ style="font-style: italic;">summaries</span>, <span
+ style="font-style: italic;">filters</span>, <span
+ style="font-style: italic;">synthetic children</span>.</p>
- <p>To reflect this, the the <b>type</b> command has two
+ <p>To reflect this, the the <b>type</b> command has four
subcommands:<br>
</p>
<p><code>type format</code></p>
<p><code>type summary</code></p>
+ <p><code>type filter</code></p>
+ <p><code>type synthetic</code></p>
+
<p>These commands are meant to bind printing options to
types. When variables are printed, LLDB will first check
@@ -73,8 +74,7 @@
the default choices.<br>
</p>
- <p>The two commands <code>type format</code> and <code>type
- summary</code> each have four subcommands:<br>
+ <p>Each of the commands has four subcommands available:<br>
</p>
<p><code>add</code>: associates a new printing option to one
or more types</p>
@@ -524,6 +524,14 @@
<td><b>%L</b></td>
<td>Use this object's location (memory address, register name, ...)</td>
</tr>
+ <tr valign="top">
+ <td><b>%#</b></td>
+ <td>Use the count of the children of this object</td>
+ </tr>
+ <tr valign="top">
+ <td><b>%T</b></td>
+ <td>Use this object's datatype name</td>
+ </tr>
</tbody>
</table>
@@ -939,19 +947,77 @@
</div>
</div>
+ <div class="post">
+ <h1 class="postheader">Synthetic children</h1>
+ <div class="postcontent">
+ <p>Summaries work well when one is able to navigate through an expression path.
+ In order for LLDB to do so, appropriate debugging information must be available.</p>
+ <p>Some types are <i>opaque</i>, i.e. no knowledge of their internals is provided.
+ When that's the case, expression paths do not work correctly.</p>
+ <p>In other cases, the internals are available to use in expression paths, but they
+ do not provide a user-friendly representation of the object's value.</p>
+ <p>For instance, consider an STL vector:</p>
+ <code>
+ <b>(lldb)</b> frame variable numbers -T<br/>
+ (std::vector<int>) numbers = {<br/>
+ (std::_Vector_base<int, std::allocator<int> >) std::_Vector_base<int, std::allocator<int> > = {<br/>
+ (std::_Vector_base<int, std::allocator<int> >::_Vector_impl) _M_impl = {<br/>
+ (int *) _M_start = 0x00000001001008a0<br/>
+ (int *) _M_finish = 0x00000001001008a8<br/>
+ (int *) _M_end_of_storage = 0x00000001001008a8<br/>
+ }<br/>
+ }<br/>
+ }<br/>
+ </code>
+ <p>Here, you can see how the type is implemented, and you can write a summary for that implementation
+ but that is not going to help you infer what items are actually stored in the vector.</p>
+ <p>What you would like to see is probably something like:</p>
+ <code>
+ <b>(lldb)</b> frame variable numbers -T<br/>
+ (std::vector<int>) numbers = {<br/>
+ (int) [0] = 1<br/>
+ (int) [1] = 12<br/>
+ (int) [2] = 123<br/>
+ (int) [3] = 1234<br/>
+ }<br/>
+ </code>
+ <p>Synthetic children are a way to get that result.</p>
+ <p>The feature is based upon the idea of providing a new set of children for a variable that replaces the ones
+ available by default through the debug information. In the example, we can use synthetic children to provide
+ the vector items as children for the std::vector object.</p>
+ <p>In order to create synthetic children, you need to provide a Python class that adheres to a given <i>interface</i>
+ (the word is italicized because Python has no explicit notion of interface. By that word we mean a given set of methods
+ must be implemented by the Python class):</p>
+ <code>
+ <font color=blue>class</font> SyntheticChildrenProvider:<br/>
+ <font color=blue>def</font> __init__(self, valobj, dict):<br/>
+ this call should initialize the Python object using valobj as the variable to provide synthetic children for <br/>
+ <font color=blue>def</font> num_children(self): <br/>
+ this call should return the number of children that you want your object to have <br/>
+ <font color=blue>def</font> get_child_index(self,name): <br/>
+ this call should return the index of the synthetic child whose name is given as argument <br/>
+ <font color=blue>def</font> get_child_at_index(self,index): <br/>
+ this call should return a new LLDB SBValue object representing the child at the index given as argument <br/>
+ <font color=blue>def</font> update(self): <br/>
+ this call should be used to update the internal state of this Python object whenever the state of the variables in LLDB changes.
+ Currently this method is optional, because the internal state of synthetic children providers will not be preserved. However, this is meant to change in future versions
+ of LLDB.<br/>
+ </code>
+ <p>For examples of how synthetic children are created, you are encouraged to look at <a href="http://llvm.org/svn/llvm-project/lldb/trunk/examples/synthetic/">examples/synthetic</a> in the LLDB trunk.</p>
+ </div>
+ </div>
<div class="post">
- <h1 class="postheader">Finding summaries 101</h1>
+ <h1 class="postheader">Finding formatters 101</h1>
<div class="postcontent">
<p>While the rules for finding an appropriate format for a
type are relatively simple (just go through typedef
- hierarchies), summaries follow a more complicated
- process in finding the right summary string for a
- variable. Namely, what happens is:</p>
+ hierarchies), searching formatters for a type goes through
+ a rather intricate set of rules. Namely, what happens is:</p>
<ul>
- <li>If there is a summary for the type of the variable,
+ <li>If there is a formatter for the type of the variable,
use it</li>
- <li>If this object is a pointer, and there is a summary
+ <li>If this object is a pointer, and there is a formatter
for the pointee type that does not skip pointers, use
it</li>
<li>If this object is a reference, and there is a
@@ -959,7 +1025,11 @@
references, use it</li>
<li>If this object is an Objective-C class with a parent
class, look at the parent class (and parent of parent,
- ...)</li>
+ ...). This phase can be based upon the actual type of
+ the object as inferred by the value of its <code>isa</code>
+ pointer, or upon the debugging information inferred by the
+ debugger. The user can use the dynamic typing settings to
+ elect one or the other behavior.</li>
<li>If this object is a C++ class with base classes,
look at base classes (and bases of bases, ...)</li>
<li>If this object is a C++ class with virtual base
@@ -986,6 +1056,7 @@
<li>There's no way to do multiple dereferencing, and you
need to be careful what the dereferencing operation is
binding to in complicated scenarios</li>
+ <li>Synthetic children providers cannot have a permanent state</li>
<li><code>type format add</code> does not support the <code>-x</code>
option</li>
<strike><li>Object location cannot be printed in the summary