Skip to content

Commit 7bb6f3f

Browse files
committed
move to debugger page, modify style
1 parent 5a6670d commit 7bb6f3f

File tree

3 files changed

+153
-149
lines changed

3 files changed

+153
-149
lines changed

src/attributes.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -224,7 +224,6 @@ The following is an index of all built-in attributes.
224224
- [`allow`], [`warn`], [`deny`], [`forbid`] — Alters the default lint level.
225225
- [`deprecated`] — Generates deprecation notices.
226226
- [`must_use`] — Generates a lint for unused values.
227-
- [`debugger_visualizer`] — Embeds a file that specifies debugger output for a type
228227
- ABI, linking, symbols, and FFI
229228
- [`link`] — Specifies a native library to link with an `extern` block.
230229
- [`link_name`] — Specifies the name of the symbol for functions or statics
@@ -272,6 +271,8 @@ The following is an index of all built-in attributes.
272271
- Type System
273272
- [`non_exhaustive`] — Indicate that a type will have more fields/variants
274273
added in future.
274+
- Debugger
275+
- [`debugger_visualizer`] — Embeds a file that specifies debugger output for a type
275276

276277
[Doc comments]: comments.md#doc-comments
277278
[ECMA-334]: https://www.ecma-international.org/publications/standards/Ecma-334.htm
@@ -292,7 +293,7 @@ The following is an index of all built-in attributes.
292293
[`cold`]: attributes/codegen.md#the-cold-attribute
293294
[`crate_name`]: crates-and-source-files.md#the-crate_name-attribute
294295
[`crate_type`]: linkage.md
295-
[`debugger_visualizer`]: attributes/diagnostics.md#the-debugger_visualizer-attribute
296+
[`debugger_visualizer`]: attributes/debugger.md#the-debugger_visualizer-attribute
296297
[`deny`]: attributes/diagnostics.md#lint-check-attributes
297298
[`deprecated`]: attributes/diagnostics.md#the-deprecated-attribute
298299
[`derive`]: attributes/derive.md

src/attributes/debugger.md

Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,150 @@
1+
# Debugger attributes
2+
3+
The following [attributes] are used for enhancing the debugging experience when using third-party debuggers like GDB or LLDB.
4+
5+
## The `debugger_visualizer` attribute
6+
7+
The `debugger_visualizer` attribute can be used to embed a debugger visualizer file into the debug information generated by `rustc`.
8+
This enables an improved debugger experience for types outside of Rust's standard library.
9+
10+
### Using `debugger_visualizer` with Natvis
11+
12+
Natvis is an XML-based framework for Microsoft debuggers (such as Visual Studio and WinDbg that uses declarative rules to customize the display of types.
13+
A Natvis file is embedded using the `natvis-file` meta item.
14+
For detailed information on the Natvis format, refer to Microsoft's [Natvis documentation].
15+
16+
<div class="warning">
17+
Currently, this attribute only supports embedding Natvis files on `-windows-msvc` targets.
18+
</div>
19+
20+
Consider a crate with this directory structure:
21+
22+
```text
23+
/Cargo.toml
24+
/Rectangle.natvis
25+
+-- src
26+
+-- main.rs
27+
```
28+
29+
Where `main.rs` contains:
30+
31+
```rust
32+
#![debugger_visualizer(natvis_file = "../Rectangle.natvis")]
33+
struct FancyRect {
34+
pub x: f32,
35+
pub y: f32,
36+
pub dx: f32,
37+
pub dy: f32,
38+
}
39+
40+
fn main() {
41+
let mut fancy_rect = FancyRect::new(10.0, 10.0, 5.0, 5.0);
42+
}
43+
```
44+
45+
and `Rectangle.natvis` contains:
46+
47+
```xml
48+
<?xml version="1.0" encoding="utf-8"?>
49+
<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
50+
<Type Name="Rectangle::FancyRect">
51+
<DisplayString>({x},{y}) + ({dx}, {dy})</DisplayString>
52+
<Expand>
53+
<Synthetic Name="LowerLeft">
54+
<DisplayString>({x}, {y})</DisplayString>
55+
</Synthetic>
56+
<Synthetic Name="UpperLeft">
57+
<DisplayString>({x}, {y + dy})</DisplayString>
58+
</Synthetic>
59+
<Synthetic Name="UpperRight">
60+
<DisplayString>({x + dx}, {y + dy})</DisplayString>
61+
</Synthetic>
62+
<Synthetic Name="LowerRight">
63+
<DisplayString>({x + dx}, {y})</DisplayString>
64+
</Synthetic>
65+
</Expand>
66+
</Type>
67+
</AutoVisualizer>
68+
```
69+
70+
When viewed under WinDbg, the `fancy_rect` variable would be shown as follows:
71+
72+
```text
73+
> Variables:
74+
> fancy_rect: (10, 10) + (5, 5)
75+
> LowerLeft: (10, 10)
76+
> UpperLeft: (10, 15)
77+
> UpperRight: (15, 15)
78+
> LowerRight: (15, 10)
79+
```
80+
81+
### Using `debugger_visualizer` with GDB
82+
83+
GDB supports the use of a structured Python script, called a *pretty printer*, that describes how a type should be visualized in the debugger view.
84+
These scripts are embedded using the `gdb_script_file` meta item.
85+
For detailed information on pretty printers, refer to GDB's [pretty print documentation].
86+
87+
Consider a crate with this directory structure:
88+
89+
```text
90+
/Cargo.toml
91+
/person_printer.py
92+
+-- src
93+
+-- main.rs
94+
```
95+
96+
Where `main.rs` contains:
97+
98+
```rust
99+
#![debugger_visualizer(gdb_script_file = "../bar.py")]
100+
mod person {
101+
pub struct Person {
102+
pub name: String,
103+
pub age: i32,
104+
}
105+
}
106+
107+
use person::Person;
108+
109+
fn main() {
110+
let person = Person::new(String::from("Bob"), 10);
111+
}
112+
```
113+
114+
and `person_printer.py` contains:
115+
116+
```python
117+
import gdb
118+
119+
class PersonPrinter:
120+
"Print a Person"
121+
122+
def __init__(self, val):
123+
self.val = val
124+
self.name = val["name"]
125+
self.age = int(val["age"])
126+
127+
def to_string(self):
128+
return "{} is {} years old.".format(self.name, self.age)
129+
130+
def lookup(val):
131+
lookup_tag = val.type.tag
132+
if lookup_tag is None:
133+
return None
134+
if "person::Person" == lookup_tag:
135+
return PersonPrinter(val)
136+
137+
return None
138+
139+
gdb.current_objfile().pretty_printers.append(lookup)
140+
```
141+
142+
When the crate's debug executable is passed into GDB, `print person` will display:
143+
144+
```
145+
"Bob" is 10 years old.
146+
```
147+
148+
[attributes]: ../attributes.md
149+
[Natvis documentation]: https://docs.microsoft.com/en-us/visualstudio/debugger/create-custom-views-of-native-objects
150+
[pretty print documentation]: https://sourceware.org/gdb/onlinedocs/gdb/Pretty-Printing.html

src/attributes/diagnostics.md

Lines changed: 0 additions & 147 deletions
Original file line numberDiff line numberDiff line change
@@ -301,154 +301,7 @@ When used on a function in a trait implementation, the attribute does nothing.
301301
> let _ = five();
302302
> ```
303303
304-
## The `debugger_visualizer` attribute
305-
306-
The `debugger_visualizer` attribute can be used to embed a debugger visualizer file into the PDB/ELF generated by `rustc`.
307-
This enables an improved debugger experience for types outside of Rust's standard library.
308-
309-
### Using `debugger_visualizer` with Natvis
310-
311-
Natvis is an XML-based framework, and a `.natvis` file declares how a type's fields should be displayed in the debugger view.
312-
A Natvis file is embedded using the `natvis-file` meta item.
313-
Microsoft's [Natvis documentation] can be referenced to help developers write their own `.natvis` files.
314-
315-
<div class="warning">
316-
Currently, this attribute only supports embedding Natvis files on `-windows-msvc` targets.
317-
`-windows-gnu` targets are not currently supported.
318-
</div>
319-
320-
Consider a crate with this directory structure:
321-
322-
```text
323-
/Cargo.toml
324-
/Foo.natvis (Note: the Natvis file does not have to match the name of the crate.)
325-
+-- src
326-
+-- main.rs
327-
```
328-
329-
Where `main.rs` contains:
330-
331-
```rust
332-
#![debugger_visualizer(natvis_file = "../Foo.natvis")]
333-
struct FancyRect {
334-
pub x: f32,
335-
pub y: f32,
336-
pub dx: f32,
337-
pub dy: f32,
338-
}
339-
340-
fn main() {
341-
let mut fancy_rect = FancyRect::new(10.0, 10.0, 5.0, 5.0);
342-
}
343-
```
344-
345-
and `Foo.natvis` contains:
346-
347-
```xml
348-
<?xml version="1.0" encoding="utf-8"?>
349-
<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
350-
<Type Name="foo::FancyRect">
351-
<DisplayString>({x},{y}) + ({dx}, {dy})</DisplayString>
352-
<Expand>
353-
<Synthetic Name="LowerLeft">
354-
<DisplayString>({x}, {y})</DisplayString>
355-
</Synthetic>
356-
<Synthetic Name="UpperLeft">
357-
<DisplayString>({x}, {y + dy})</DisplayString>
358-
</Synthetic>
359-
<Synthetic Name="UpperRight">
360-
<DisplayString>({x + dx}, {y + dy})</DisplayString>
361-
</Synthetic>
362-
<Synthetic Name="LowerRight">
363-
<DisplayString>({x + dx}, {y})</DisplayString>
364-
</Synthetic>
365-
</Expand>
366-
</Type>
367-
</AutoVisualizer>
368-
```
369-
370-
When viewed under WinDbg, the `fancy_rect` variable would be shown as follows:
371-
372-
```text
373-
> Variables:
374-
> fancy_rect: (10, 10) + (5, 5)
375-
> LowerLeft: (10, 10)
376-
> UpperLeft: (10, 15)
377-
> UpperRight: (15, 15)
378-
> LowerRight: (15, 10)
379-
```
380-
381-
### Using `debugger_visualizer` with GDB
382-
383-
Developers using GDB are able to embed *pretty printers* onto types.
384-
In GDB, a pretty printer is a structured Python script that describes how a type's fields should be displayed in the debugger view.
385-
These scripts are embedded using the `gdb_script_file` meta item.
386-
GDB's [pretty print documentation] can be referenced by developers to help them write their own `.py` scripts.
387-
388-
Consider a crate with this directory structure:
389-
390-
```text
391-
/Cargo.toml
392-
/bar.py (Note: the file does not have to match the name of the crate.)
393-
+-- src
394-
+-- main.rs
395-
```
396-
397-
Where `main.rs` contains:
398-
399-
```rust
400-
#![debugger_visualizer(gdb_script_file = "../bar.py")]
401-
mod person {
402-
pub struct Person {
403-
pub name: String,
404-
pub age: i32,
405-
}
406-
}
407-
408-
use person::Person;
409-
410-
fn main() {
411-
let person = Person::new(String::from("Bob"), 10);
412-
}
413-
```
414-
415-
and `bar.py` contains:
416-
417-
```python
418-
import gdb
419-
420-
class PersonPrinter:
421-
"Print a Person"
422-
423-
def __init__(self, val):
424-
self.val = val
425-
self.name = val["name"]
426-
self.age = int(val["age"])
427-
428-
def to_string(self):
429-
return "{} is {} years old.".format(self.name, self.age)
430-
431-
def lookup(val):
432-
lookup_tag = val.type.tag
433-
if lookup_tag is None:
434-
return None
435-
if "main::Person" == lookup_tag:
436-
return PersonPrinter(val)
437-
438-
return None
439-
440-
gdb.current_objfile().pretty_printers.append(lookup)
441-
```
442-
443-
When the crate's debug executable is passed into GDB, `print person` should display:
444-
445-
```
446-
"Bob" is 10 years old.
447-
```
448-
449304
[Clippy]: https://github.com/rust-lang/rust-clippy
450-
[Natvis documentation]: https://docs.microsoft.com/en-us/visualstudio/debugger/create-custom-views-of-native-objects
451-
[pretty print documentation]: https://sourceware.org/gdb/onlinedocs/gdb/Pretty-Printing.html
452305
[_MetaListNameValueStr_]: ../attributes.md#meta-item-attribute-syntax
453306
[_MetaListPaths_]: ../attributes.md#meta-item-attribute-syntax
454307
[_MetaNameValueStr_]: ../attributes.md#meta-item-attribute-syntax

0 commit comments

Comments
 (0)