mirror of
https://github.com/encounter/msvc-demangler-rust.git
synced 2026-07-10 12:18:38 -07:00
handle RTTI type descriptors
This commit is contained in:
committed by
Jeff Muizelaar
parent
73912bccd5
commit
f2ec54ee5c
+41
-5
@@ -109,7 +109,7 @@ bitflags! {
|
||||
// Represents an identifier which may be a template.
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
pub enum Name<'a> {
|
||||
Operator(Operator),
|
||||
Operator(Operator<'a>),
|
||||
NonTemplate(&'a [u8]),
|
||||
Template(Box<Name<'a>>, Params<'a>),
|
||||
Discriminator(i32),
|
||||
@@ -118,7 +118,7 @@ pub enum Name<'a> {
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
pub enum Operator {
|
||||
pub enum Operator<'a> {
|
||||
Ctor,
|
||||
Dtor,
|
||||
New,
|
||||
@@ -191,6 +191,8 @@ pub enum Operator {
|
||||
|
||||
CoroutineAwait,
|
||||
LiteralOperatorName,
|
||||
|
||||
RTTITypeDescriptor(StorageClass, Box<Type<'a>>),
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
@@ -256,6 +258,7 @@ pub enum Type<'a> {
|
||||
VarArgs,
|
||||
EmptyParameterPack,
|
||||
Nullptr,
|
||||
RTTIType,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
@@ -357,6 +360,9 @@ impl<'a> ParserState<'a> {
|
||||
let calling_conv = self.read_calling_conv()?;
|
||||
Type::VCallThunk(vftable_offset, calling_conv)
|
||||
}
|
||||
b'8' => {
|
||||
Type::RTTIType
|
||||
}
|
||||
c => {
|
||||
// Read a member function.
|
||||
let func_class = self.read_func_class(c)?;
|
||||
@@ -701,8 +707,9 @@ impl<'a> ParserState<'a> {
|
||||
fn read_name(&mut self, function: bool) -> Result<Symbol<'a>> {
|
||||
// println!("read_name on {}", str::from_utf8(self.input)?);
|
||||
let name = self.read_unqualified_name(function)?;
|
||||
let scope = self.read_scope()?;
|
||||
|
||||
Ok(Symbol{name, scope: self.read_scope()? })
|
||||
Ok(Symbol{name, scope})
|
||||
}
|
||||
|
||||
fn read_func_type(&mut self) -> Result<Type<'a>> {
|
||||
@@ -718,7 +725,7 @@ impl<'a> ParserState<'a> {
|
||||
Ok(Name::Operator(self.read_operator_name()?))
|
||||
}
|
||||
|
||||
fn read_operator_name(&mut self) -> Result<Operator> {
|
||||
fn read_operator_name(&mut self) -> Result<Operator<'a>> {
|
||||
let orig = self.input;
|
||||
|
||||
Ok(match self.get()? {
|
||||
@@ -784,6 +791,18 @@ impl<'a> ParserState<'a> {
|
||||
b'M' => Operator::EHVectorDtorIterator,
|
||||
b'N' => Operator::EHVectorVBaseCtorIterator,
|
||||
b'O' => Operator::CopyCtorClosure,
|
||||
b'R' => {
|
||||
let c = self.get()?;
|
||||
match c {
|
||||
b'0' => {
|
||||
self.expect(b"?")?;
|
||||
let storage_class = self.read_storage_class();
|
||||
let t = self.read_var_type(storage_class)?;
|
||||
Operator::RTTITypeDescriptor(storage_class, Box::new(t))
|
||||
}
|
||||
_ => panic!("unknown RTTI Operator Name"),
|
||||
}
|
||||
}
|
||||
b'S' => Operator::LocalVFTable,
|
||||
b'T' => Operator::LocalVFTableCtorClosure,
|
||||
b'U' => Operator::ArrayNew,
|
||||
@@ -1500,7 +1519,10 @@ impl<'a> Serializer<'a> {
|
||||
}
|
||||
&Type::EmptyParameterPack => {
|
||||
return Ok(())
|
||||
},
|
||||
}
|
||||
&Type::RTTIType => {
|
||||
return Ok(())
|
||||
}
|
||||
};
|
||||
|
||||
if storage_class.contains(StorageClass::CONST) {
|
||||
@@ -1731,6 +1753,12 @@ impl<'a> Serializer<'a> {
|
||||
|
||||
&Operator::CoroutineAwait => " co_await",
|
||||
&Operator::LiteralOperatorName => " CXXLiteralOperatorName",
|
||||
|
||||
&Operator::RTTITypeDescriptor(_, ref inner) => {
|
||||
self.write_pre(inner)?;
|
||||
write!(self.w, "::`RTTI Type Descriptor'")?;
|
||||
return Ok(());
|
||||
},
|
||||
};
|
||||
write!(self.w, "{}", s)?;
|
||||
Ok(())
|
||||
@@ -2061,6 +2089,14 @@ mod tests {
|
||||
"??_9nsDocument@@$BDMI@AE",
|
||||
"[thunk]: __thiscall nsDocument::`vcall'{968,{flat}}' }",
|
||||
);
|
||||
expect(
|
||||
"??_R0?AUCollationCacheEntry@icu_61@@@8",
|
||||
"struct icu_61::CollationCacheEntry::`RTTI Type Descriptor\'",
|
||||
);
|
||||
expect(
|
||||
"??_R0?AV?$KxTree@V?$KxSpe@DI@@I@@@8",
|
||||
"class KxTree<class KxSpe<char,unsigned int>,unsigned int>::`RTTI Type Descriptor'",
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
||||
Reference in New Issue
Block a user