diff options
5 files changed, 108 insertions, 3 deletions
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp index 72d70ef99c2..f33b6446def 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp @@ -2396,6 +2396,7 @@ SymbolFileDWARF::ParseChildParameters DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *parent_die, bool skip_artificial, + bool &is_static, TypeList* type_list, std::vector<clang_type_t>& function_param_types, std::vector<clang::ParmVarDecl*>& function_param_decls, @@ -2481,7 +2482,7 @@ SymbolFileDWARF::ParseChildParameters const DWARFDebugInfoEntry *grandparent_die = parent_die->GetParent(); if (grandparent_die && (grandparent_die->Tag() == DW_TAG_structure_type || grandparent_die->Tag() == DW_TAG_class_type)) - { + { LanguageType language = sc.comp_unit->GetLanguage(); if (language == eLanguageTypeObjC_plus_plus || language == eLanguageTypeC_plus_plus) { @@ -2492,10 +2493,12 @@ SymbolFileDWARF::ParseChildParameters { Type *this_type = ResolveTypeUID (param_type_die_offset); if (this_type) - { + { uint32_t encoding_mask = this_type->GetEncodingMask(); if (encoding_mask & Type::eEncodingIsPointerUID) { + is_static = false; + if (encoding_mask & (1u << Type::eEncodingIsConstUID)) type_quals |= clang::Qualifiers::Const; if (encoding_mask & (1u << Type::eEncodingIsVolatileUID)) @@ -3567,6 +3570,12 @@ SymbolFileDWARF::ParseType (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, std::vector<clang::ParmVarDecl*> function_param_decls; // Parse the function children for the parameters + + const DWARFDebugInfoEntry *class_die = die->GetParent(); + if (class_die && (class_die->Tag() == DW_TAG_structure_type || + class_die->Tag() == DW_TAG_class_type)) + is_static = true; + if (die->HasChildren()) { bool skip_artificial = true; @@ -3574,7 +3583,8 @@ SymbolFileDWARF::ParseType (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, type_sp, dwarf_cu, die, - skip_artificial, + skip_artificial, + is_static, type_list, function_param_types, function_param_decls, diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h index 2f6fa783ad1..56e7abed291 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h +++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h @@ -275,6 +275,7 @@ protected: DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *parent_die, bool skip_artificial, + bool &is_static, lldb_private::TypeList* type_list, std::vector<lldb::clang_type_t>& function_args, std::vector<clang::ParmVarDecl*>& function_param_decls, diff --git a/lldb/test/lang/cpp/static_methods/Makefile b/lldb/test/lang/cpp/static_methods/Makefile new file mode 100644 index 00000000000..314f1cb2f07 --- /dev/null +++ b/lldb/test/lang/cpp/static_methods/Makefile @@ -0,0 +1,5 @@ +LEVEL = ../../../make + +CXX_SOURCES := main.cpp + +include $(LEVEL)/Makefile.rules diff --git a/lldb/test/lang/cpp/static_methods/TestCPPStaticMethods.py b/lldb/test/lang/cpp/static_methods/TestCPPStaticMethods.py new file mode 100644 index 00000000000..c1a03d47590 --- /dev/null +++ b/lldb/test/lang/cpp/static_methods/TestCPPStaticMethods.py @@ -0,0 +1,51 @@ +""" +Tests expressions that distinguish between static and non-static methods. +""" + +from lldbtest import * + +class CPPStaticMethodsTestCase(TestBase): + + mydir = os.path.join("lang", "cpp", "static_methods") + + @unittest2.skipUnless(sys.platform.startswith("darwin"), "requires Darwin") + def test_with_dsym_and_run_command(self): + """Test that static methods are properly distinguished from regular methods""" + self.buildDsym() + self.static_method_commands() + + def test_with_dwarf_and_run_command(self): + """Test that static methods are properly distinguished from regular methods""" + self.buildDwarf() + self.static_method_commands() + + def setUp(self): + TestBase.setUp(self) + self.line = line_number('main.cpp', '// Break at this line') + + def static_method_commands(self): + """Test that static methods are properly distinguished from regular methods""" + self.runCmd("file a.out", CURRENT_EXECUTABLE_SET) + + self.expect("breakpoint set -f main.cpp -l %d" % self.line, + BREAKPOINT_CREATED, + startstr = "Breakpoint created: 1: file ='main.cpp', line = %d, locations = 1" % self.line) + + self.runCmd("process launch", RUN_SUCCEEDED) + + # The stop reason of the thread should be breakpoint. + self.expect("thread list", + STOPPED_DUE_TO_BREAKPOINT, + substrs = ['stopped', 'stop reason = breakpoint']) + + self.expect("expression -- A::getStaticValue()", + startstr = "(int) $0 = 5") + + self.expect("expression -- my_a.getMemberValue()", + startstr = "(int) $1 = 3") + +if __name__ == '__main__': + import atexit + lldb.SBDebugger.Initialize() + atexit.register(lambda: lldb.SBDebugger.Terminate()) + unittest2.main()
\ No newline at end of file diff --git a/lldb/test/lang/cpp/static_methods/main.cpp b/lldb/test/lang/cpp/static_methods/main.cpp new file mode 100644 index 00000000000..5141a407d11 --- /dev/null +++ b/lldb/test/lang/cpp/static_methods/main.cpp @@ -0,0 +1,38 @@ +//===-- main.cpp ------------------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include <stdio.h> + +class A +{ +public: + static int getStaticValue(); + int getMemberValue(); + int a; +}; + +int A::getStaticValue() +{ + return 5; +} + +int A::getMemberValue() +{ + return a; +} + +int main() +{ + A my_a; + + my_a.a = 3; + + printf("%d\n", A::getStaticValue()); // Break at this line + printf("%d\n", my_a.getMemberValue()); +} |