Skip to content

Commit f835c96

Browse files
committed
various documentation improvements
1 parent ea46e16 commit f835c96

2 files changed

Lines changed: 54 additions & 16 deletions

File tree

src/etc/lldb_batchmode/common.py

Lines changed: 23 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
# Contains the class definitions outlining the schema of the test data
1+
"""Contains the class definitions outlining the schema of the test data. For LLDB conversion
2+
from/into these types, see `./from_lldb.py`"""
23

34
import enum
45
import json
@@ -78,7 +79,7 @@ def from_dict(ty: type[Any], data: JsonType):
7879
"""Translates a dictionary into an instance of the given dataclass type (with possibly nested
7980
dataclasses).
8081
81-
Relies on accurate type hints for the dataclass's fields, and the standard `dataclass.__init__`
82+
Relies on accurate type hints for the dataclass's fields, and the default `dataclass.__init__`
8283
definition."""
8384

8485
# Optional isn't a constructor, so we have to "unwrap" it.
@@ -295,19 +296,31 @@ def initialize() -> "TargetData":
295296
return result
296297

297298
def save_blessing(self, metadata: BlessMetadata):
298-
"""Writes the entirety of `self` to the input file. Used to finalize changes made by
299-
one or more `TestData.bless_variable` calls."""
299+
"""Writes the entirety of `self` to the env var `LLDB_BATCHMODE_INPUT_DATA_PATH`, which is
300+
set by `compiletest` before running `lldb_batchmode. Used to finalize changes made by one or
301+
more `from_lldb.bless_variable` calls.
302+
303+
This function should be called exactly once, right before
304+
`lldb_batchmode.runner.main` exits if the following conditions are met:
305+
306+
1. No other exceptions or error states occurred
307+
2. `BLESS == True`
308+
3. At least one `repr` pseudo-command was processed
309+
310+
This prevents us from saving incomplete data or invalid data. It also prevents us from
311+
creating input data files for tests that do not need it.
312+
"""
300313

301314
self.bless_metadata = metadata
302315
path = os.environ["LLDB_BATCHMODE_INPUT_DATA_PATH"]
303-
# dumping directly to a file is somewhat unsafe. If the json ends up malformed, we could
304-
# end up overwriting valid test data with a complete mess. Since the in-memory data
305-
# typically *isn't* malformed, the `--bless` will pass and make it seem like nothing is
306-
# wrong.
316+
# dumping directly to a file is somewhat unsafe. If the `Variable`/`Type` data ends up in a
317+
# state that cannot be serialized correctly, the json ends up malformed, and we could end up
318+
# overwriting valid test data with a complete mess. Since the in-memory data is typically
319+
# completely valid, the testing logic will pass and make it seem like nothing is wrong.
307320

308321
# While we could rely on git to help revert the test file, it's better to just not allow it
309-
# to save malformed json in the first place. Thus, we dump the JSON, re-read it, and then
310-
# only when that succeeds do we save it.
322+
# to save malformed json in the first place. Thus, we dump the JSON, re-read it to check
323+
# for `JSONDecodeError`, and write it to the target file if no error occurred.
311324
x = json.dumps(asdict(self), indent=" ")
312325
_ = json.loads(x)
313326

src/etc/lldb_batchmode/from_lldb.py

Lines changed: 31 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,12 @@
1-
# Contains LLDB conversion functions from LLDB's in-memory representations to the test classes
2-
# defined in `.common`
1+
"""Contains LLDB conversion functions from LLDB's in-memory representations to the test classes
2+
defined in `./common.py`.
3+
4+
We primarily interface with the following LLDB classes:
5+
6+
* [`SBValue`](https://lldb.llvm.org/python_api/lldb.SBValue.html)
7+
* [`SBType`](https://lldb.llvm.org/python_api/lldb.SBType.html)
8+
* [`SBTypeMember`](https://lldb.llvm.org/python_api/lldb.SBTypeMember.html)
9+
"""
310

411
from struct import unpack, calcsize
512

@@ -118,6 +125,7 @@ def get_summary_or_value(valobj: lldb.SBValue) -> str | None:
118125
want any printable representation at all, so this function falls back to `SBValue.GetValue`.
119126
That covers things like primitives and flat enums that typically don't have summary providers.
120127
"""
128+
121129
summary = valobj.GetSummary()
122130
if summary is None:
123131
return valobj.GetValue()
@@ -130,6 +138,22 @@ def field_from_lldb(field: lldb.SBTypeMember) -> Field:
130138

131139

132140
def get_generics(ty: lldb.SBType, sbtarget: lldb.SBTarget) -> list[lldb.SBType]:
141+
"""Platform-agnostic equivalent to `SBType.template_args`. `SBType`'s template functions do not
142+
work correctly with PDB debug info because PDB has no way to represent template parameters.
143+
144+
Due to the DWARF spec using
145+
C++-centric terminology (e.g. `DW_TAG_template_type_parameter`), the following terms are
146+
interchangable:
147+
148+
* template type param/arg <-> generic param
149+
* template value param/arg <-> const generic param
150+
151+
The difference between "param" and "arg" is largely irrelevant for our purposes.
152+
Pre-parameterized types (e.g. `Vec<T>`, which could be parameterized to `Vec<u8>`, LLDB calls
153+
this "template specialization") are not reflected in the DWARF data at all, and are largely an
154+
LLDB/clang implementation detail that isn't directly exposed to us.
155+
"""
156+
133157
name = ty.GetName()
134158
# FIXME Rust doesn't output template *values* (the `10` in `ArrayVec<u8, 10>`), only
135159
# template args (the `u8` in `ArrayVec<u8, 10>`). That means these can possibly have
@@ -232,10 +256,11 @@ def variable_from_lldb(var: lldb.SBValue) -> Variable:
232256
def bless_variable(
233257
target_data: TargetData, var_name: str, breakpoint_idx: int, frame: lldb.SBFrame
234258
):
235-
"""Updates the mapping with data generated from the given variable. Only affects the mapping
236-
of the current target and breakpoint. This function **does not** write to the input file.
237-
Update all necessary vars, then write the entire input data at once using
238-
`TestData.save_blessing`"""
259+
"""Updates the given `TargetData` with data generated from the given variable at the given
260+
breakpoint. This function **does not** write to the input file. Please see
261+
`TargetData.save_blessing` for more info on when and how to save the data.
262+
"""
263+
239264
valobj = frame.FindVariable(var_name)
240265
if not valobj.IsValid():
241266
# FIXME (todo) error handling

0 commit comments

Comments
 (0)