Index: lldb/lit/SymbolFile/NativePDB/Inputs/stack_unwinding01.lldbinit =================================================================== --- /dev/null +++ lldb/lit/SymbolFile/NativePDB/Inputs/stack_unwinding01.lldbinit @@ -0,0 +1,8 @@ +b stack_unwinding01.cpp:12 +run +thread backtrace +c +thread backtrace +c +thread backtrace +quit \ No newline at end of file Index: lldb/lit/SymbolFile/NativePDB/stack_unwinding01.cpp =================================================================== --- /dev/null +++ lldb/lit/SymbolFile/NativePDB/stack_unwinding01.cpp @@ -0,0 +1,48 @@ +// clang-format off +// REQUIRES: lld + +// RUN: %build --compiler=clang-cl --nodefaultlib -o %t.exe -- %s +// RUN: env LLDB_USE_NATIVE_PDB_READER=1 %lldb -f %t.exe -s \ +// RUN: %p/Inputs/stack_unwinding01.lldbinit 2>&1 | FileCheck %s + + +struct Struct { + void simple_method(int a, int b) { + a += 1; + simple_method(a, b); + } +}; + + + +int main(int argc, char **argv) { + Struct s; + s.simple_method(1,2); + return 0; +} + + +// CHECK: (lldb) thread backtrace +// CHECK-NEXT: * thread #1, stop reason = breakpoint 1.1 +// CHECK-NEXT: * frame #0: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #1: {{.*}} stack_unwinding01.cpp.tmp.exe`main(argc={{.*}}, argv={{.*}}) at stack_unwinding01.cpp:20 +// CHECK-NEXT: frame #2: {{.*}} kernel32.dll`BaseThreadInitThunk + 34 +// CHECK-NEXT: frame #3: {{.*}} ntdll.dll`RtlUserThreadStart + 52 + + +// CHECK: (lldb) thread backtrace +// CHECK-NEXT: * thread #1, stop reason = breakpoint 1.1 +// CHECK-NEXT: * frame #0: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #1: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #2: {{.*}} stack_unwinding01.cpp.tmp.exe`main(argc={{.*}}, argv={{.*}}) at stack_unwinding01.cpp:20 +// CHECK-NEXT: frame #3: {{.*}} kernel32.dll`BaseThreadInitThunk + 34 +// CHECK-NEXT: frame #4: {{.*}} ntdll.dll`RtlUserThreadStart + 52 + +// CHECK: (lldb) thread backtrace +// CHECK-NEXT: * thread #1, stop reason = breakpoint 1.1 +// CHECK-NEXT: * frame #0: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #1: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #2: {{.*}} stack_unwinding01.cpp.tmp.exe`Struct::simple_method at stack_unwinding01.cpp:12 +// CHECK-NEXT: frame #3: {{.*}} stack_unwinding01.cpp.tmp.exe`main(argc={{.*}}, argv={{.*}}) at stack_unwinding01.cpp:20 +// CHECK-NEXT: frame #4: {{.*}} kernel32.dll`BaseThreadInitThunk + 34 +// CHECK-NEXT: frame #5: {{.*}} ntdll.dll`RtlUserThreadStart + 52 \ No newline at end of file Index: lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h =================================================================== --- lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h +++ lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h @@ -180,6 +180,9 @@ lldb::TypeSP CreateArrayType(PdbTypeSymId type_id, const llvm::codeview::ArrayRecord &ar, CompilerType ct); + lldb::TypeSP CreateFunctionType(PdbTypeSymId type_id, + const llvm::codeview::MemberFunctionRecord &pr, + CompilerType ct); lldb::TypeSP CreateProcedureType(PdbTypeSymId type_id, const llvm::codeview::ProcedureRecord &pr, CompilerType ct); Index: lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp +++ lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp @@ -595,6 +595,17 @@ return array_sp; } + +TypeSP SymbolFileNativePDB::CreateFunctionType(PdbTypeSymId type_id, + const MemberFunctionRecord &mfr, + CompilerType ct) { + Declaration decl; + return std::make_shared( + toOpaqueUid(type_id), this, ConstString(), 0, nullptr, LLDB_INVALID_UID, + lldb_private::Type::eEncodingIsUID, decl, ct, + lldb_private::Type::eResolveStateFull); +} + TypeSP SymbolFileNativePDB::CreateProcedureType(PdbTypeSymId type_id, const ProcedureRecord &pr, CompilerType ct) { @@ -655,6 +666,11 @@ llvm::cantFail(TypeDeserializer::deserializeAs(cvt, pr)); return CreateProcedureType(type_id, pr, ct); } + if (cvt.kind() == LF_MFUNCTION) { + MemberFunctionRecord mfr; + llvm::cantFail(TypeDeserializer::deserializeAs(cvt, mfr)); + return CreateFunctionType(type_id, mfr, ct); + } return nullptr; }