pub enum VariableNodeType {
    ReferenceOffset(UnitOffset),
    TypeOffset(UnitOffset),
    DirectLookup,
    DoNotRecurse,
    RecurseToBaseType,
    SvdPeripheral,
    SvdRegister,
    SvdField,
}
Expand description

Encode the nature of the Debug Information Entry in a way that we can resolve child nodes of a Variable The rules for ‘lazy loading’/deferred recursion of Variable children are described under each of the enum values.

Variants

ReferenceOffset(UnitOffset)

For pointer values, their referenced variables are found at an gimli::UnitOffset in the DebugInfo.

  • Rule: Pointers to struct variables WILL NOT BE recursed, because this may lead to infinite loops/stack overflows in structs that self-reference.
  • Rule: Pointers to “base” datatypes SHOULD BE, but ARE NOT resolved, because it would keep the UX simple, but DWARF doesn’t make it easy to determine when a pointer points to a base data type. We can read ahead in the DIE children, but that feels rather inefficient.

TypeOffset(UnitOffset)

Use the header_offset and type_offset as direct references for recursing the variable children. With the current implementation, the type_offset will point to a DIE with a tag of DW_TAG_structure_type.

  • Rule: For structured variables, we WILL NOT automatically expand their children, but we have enough information to expand it on demand. Except if they fall into one of the special cases handled by [VariableNodeType::RecurseAsIntermediate]

DirectLookup

Use the header_offset and entries_offset as direct references for recursing the variable children.

  • Rule: All top level variables in a StackFrame are automatically deferred, i.e [VariableName::StaticScope], [VariableName::Registers], [VariableName::LocalScope].

DoNotRecurse

Sometimes it doesn’t make sense to recurse the children of a specific node type

  • Rule: Pointers to unit datatypes WILL NOT BE resolved, because it doesn’t make sense.
  • Rule: Once we determine that a variable can not be recursed further, we update the variable_node_type to indicate that no further recursion is possible/required. This can be because the variable is a ‘base’ data type, or because there was some kind of error in processing the current node, so we don’t want to incur cascading errors. TODO: Find code instances where we use magic values (e.g. u32::MAX) and replace with DoNotRecurse logic if appropriate.

RecurseToBaseType

Unless otherwise specified, always recurse the children of every node until we get to the base data type.

  • Rule: (Default) Unless it is prevented by any of the other rules, we always recurse the children of these variables.
  • Rule: Certain structured variables (e.g. &str, Some, Ok, Err, etc.) are set to VariableNodeType::RecurseToBaseType to improve the debugger UX.
  • Rule: Pointers to const variables WILL ALWAYS BE recursed, because they provide essential information, for example about the length of strings, or the size of arrays.
  • Rule: Enumerated types WILL ALWAYS BE recursed, because we only ever want to see the ‘active’ child as the value.
  • Rule: For now, Array types WILL ALWAYS BE recursed. TODO: Evaluate if it is beneficial to defer these.
  • Rule: For now, Union types WILL ALWAYS BE recursed. TODO: Evaluate if it is beneficial to defer these.

SvdPeripheral

SVD Device Peripherals

SvdRegister

SVD Peripheral Registers

SvdField

SVD Register Fields

Implementations

Will return true if any of the variable_node_type value implies that the variable will be ‘lazy’ resolved.

Trait Implementations

Returns a copy of the value. Read more

Performs copy-assignment from source. Read more

Formats the value using the given formatter. Read more

Returns the “default value” for a type. Read more

This method tests for self and other values to be equal, and is used by ==. Read more

This method tests for !=.

Auto Trait Implementations

Blanket Implementations

Gets the TypeId of self. Read more

Immutably borrows from an owned value. Read more

Mutably borrows from an owned value. Read more

Returns the argument unchanged.

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

The resulting type after obtaining ownership.

Creates owned data from borrowed data, usually by cloning. Read more

Uses borrowed data to replace owned data, usually by cloning. Read more

The type returned in the event of a conversion error.

Performs the conversion.

The type returned in the event of a conversion error.

Performs the conversion.