[−][src]Struct pdb::TypeInformation
pub struct TypeInformation<'t> { /* fields omitted */ }
TypeInformation
provides zero-copy access to a PDB type data stream.
PDB type information is stored as a stream of length-prefixed Type
records, and thus the most
fundamental operation supported by TypeInformation
is to iterate over Type
s.
Types are uniquely identified by TypeIndex
, and types are stored within the PDB in ascending
order of TypeIndex
.
Many types refer to other types by TypeIndex
, and these references may refer to other types
forming a chain that's arbitrarily long. Fortunately, PDB format requires that types refer only
to types with lower TypeIndex
es; thus, the stream of types form a directed acyclic graph.
TypeInformation
can iterate by TypeIndex
, since that's essentially the only operation
permitted by the data. TypeFinder
is a secondary data structure to provide efficient
backtracking.
Examples
Iterating over the types while building a TypeFinder
:
let type_information = pdb.type_information()?; let mut type_finder = type_information.new_type_finder(); let mut iter = type_information.iter(); while let Some(typ) = iter.next()? { // build the type finder as we go type_finder.update(&iter); // parse the type record match typ.parse() { Ok(pdb::TypeData::Class(pdb::ClassType {name, properties, fields: Some(fields), ..})) => { // this Type describes a class-like type with fields println!("type {} is a class named {}", typ.type_index(), name); // `fields` is a TypeIndex which refers to a FieldList // To find information about the fields, find and parse that Type match type_finder.find(fields)?.parse()? { pdb::TypeData::FieldList(list) => { // `fields` is a Vec<TypeData> for field in list.fields { if let pdb::TypeData::Member(member) = field { // follow `member.field_type` as desired println!(" - field {} at offset {:x}", member.name, member.offset); } else { // handle member functions, nested types, etc. } } if let Some(more_fields) = list.continuation { // A FieldList can be split across multiple records // TODO: follow `more_fields` and handle the next FieldList } } _ => { } } }, Ok(_) => { // ignore everything that's not a class-like type }, Err(pdb::Error::UnimplementedTypeKind(_)) => { // found an unhandled type record // this probably isn't fatal in most use cases }, Err(e) => { // other error, probably is worth failing return Err(e); } } }
Methods
impl<'t> TypeInformation<'t>
[src]
impl<'t> TypeInformation<'t>
pub fn iter(&self) -> TypeIter
[src]
pub fn iter(&self) -> TypeIter
Returns an iterator that can traverse the type table in sequential order.
pub fn len(&self) -> usize
[src]
pub fn len(&self) -> usize
Returns the number of types contained in this TypeInformation
.
Note that primitive types are not stored in the PDB file, so the number of distinct types
reachable via this TypeInformation
will be higher than len()
.
pub fn new_type_finder(&self) -> TypeFinder
[src]
pub fn new_type_finder(&self) -> TypeFinder
Returns a TypeFinder
with a default time-space tradeoff.
The TypeFinder
is initially empty and must be populated by iterating.
Trait Implementations
impl<'t> Debug for TypeInformation<'t>
[src]
impl<'t> Debug for TypeInformation<'t>
Auto Trait Implementations
impl<'t> !Send for TypeInformation<'t>
impl<'t> !Send for TypeInformation<'t>
impl<'t> !Sync for TypeInformation<'t>
impl<'t> !Sync for TypeInformation<'t>