[lldb] Support for DWARF-5 atomic types

Summary:
This patch adds support for atomic types (DW_TAG_atomic_type) to LLDB. It's mostly just filling out all the switch-statements that didn't implement Atomic case with the usual boilerplate.

Thanks Pavel for writing the test case.

Reviewers: labath, aprantl, shafik

Reviewed By: labath

Subscribers: jfb, abidh, JDevlieghere, lldb-commits

Tags: #lldb

Differential Revision: https://reviews.llvm.org/D71183
This commit is contained in:
Raphael Isemann 2019-12-09 10:27:32 +01:00
parent f3696533f2
commit d0fb7a478d
10 changed files with 163 additions and 2 deletions

View File

@ -644,6 +644,8 @@ public:
CompilerType
GetRValueReferenceType(lldb::opaque_compiler_type_t type) override;
CompilerType GetAtomicType(lldb::opaque_compiler_type_t type) override;
CompilerType AddConstModifier(lldb::opaque_compiler_type_t type) override;
CompilerType AddVolatileModifier(lldb::opaque_compiler_type_t type) override;

View File

@ -218,6 +218,11 @@ public:
// an invalid type.
CompilerType AddVolatileModifier() const;
// Return a new CompilerType that is the atomic type of this type. If this
// type is not valid or the type system doesn't support atomic types, this
// returns an invalid type.
CompilerType GetAtomicType() const;
// Return a new CompilerType adds a restrict modifier to this type if this
// type is valid and the type system supports restrict modifiers, else return
// an invalid type.

View File

@ -80,7 +80,9 @@ public:
eEncodingIsLValueReferenceUID, ///< This type is L value reference to a type
/// whose UID is m_encoding_uid
eEncodingIsRValueReferenceUID, ///< This type is R value reference to a type
/// whose UID is m_encoding_uid
/// whose UID is m_encoding_uid,
eEncodingIsAtomicUID, ///< This type is the type whose UID is
/// m_encoding_uid as an atomic type.
eEncodingIsSyntheticUID
};

View File

@ -228,6 +228,8 @@ public:
virtual CompilerType
GetRValueReferenceType(lldb::opaque_compiler_type_t type);
virtual CompilerType GetAtomicType(lldb::opaque_compiler_type_t type);
virtual CompilerType AddConstModifier(lldb::opaque_compiler_type_t type);
virtual CompilerType AddVolatileModifier(lldb::opaque_compiler_type_t type);

View File

@ -474,6 +474,7 @@ TypeSP DWARFASTParserClang::ParseTypeFromDWARF(const SymbolContext &sc,
case DW_TAG_const_type:
case DW_TAG_restrict_type:
case DW_TAG_volatile_type:
case DW_TAG_atomic_type:
case DW_TAG_unspecified_type: {
type_sp = ParseTypeModifier(sc, die, attrs);
break;
@ -618,6 +619,9 @@ DWARFASTParserClang::ParseTypeModifier(const SymbolContext &sc,
case DW_TAG_volatile_type:
encoding_data_type = Type::eEncodingIsVolatileUID;
break;
case DW_TAG_atomic_type:
encoding_data_type = Type::eEncodingIsAtomicUID;
break;
}
if (!clang_type && (encoding_data_type == Type::eEncodingIsPointerUID ||

View File

@ -4066,6 +4066,11 @@ ClangASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type,
->getUnderlyingType()
.getAsOpaquePtr())
.GetTypeInfo(pointee_or_element_clang_type);
case clang::Type::Atomic:
return CompilerType(this, llvm::cast<clang::AtomicType>(qual_type)
->getValueType()
.getAsOpaquePtr())
.GetTypeInfo(pointee_or_element_clang_type);
case clang::Type::UnresolvedUsing:
return 0;
@ -4760,6 +4765,13 @@ ClangASTContext::GetRValueReferenceType(lldb::opaque_compiler_type_t type) {
return CompilerType();
}
CompilerType ClangASTContext::GetAtomicType(lldb::opaque_compiler_type_t type) {
if (!type)
return CompilerType();
return CompilerType(
this, getASTContext()->getAtomicType(GetQualType(type)).getAsOpaquePtr());
}
CompilerType
ClangASTContext::AddConstModifier(lldb::opaque_compiler_type_t type) {
if (type) {
@ -5364,6 +5376,11 @@ lldb::Format ClangASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
->getUnderlyingType()
.getAsOpaquePtr())
.GetFormat();
case clang::Type::Atomic:
return CompilerType(this, llvm::cast<clang::AtomicType>(qual_type)
->getValueType()
.getAsOpaquePtr())
.GetFormat();
case clang::Type::DependentSizedArray:
case clang::Type::DependentSizedExtVector:
case clang::Type::UnresolvedUsing:
@ -5379,7 +5396,6 @@ lldb::Format ClangASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
case clang::Type::TemplateSpecialization:
case clang::Type::DeducedTemplateSpecialization:
case clang::Type::Atomic:
case clang::Type::Adjusted:
case clang::Type::Pipe:
break;

View File

@ -427,6 +427,12 @@ CompilerType CompilerType::GetRValueReferenceType() const {
return CompilerType();
}
CompilerType CompilerType::GetAtomicType() const {
if (IsValid())
return m_type_system->GetAtomicType(m_type);
return CompilerType();
}
CompilerType CompilerType::AddConstModifier() const {
if (IsValid())
return m_type_system->AddConstModifier(m_type);

View File

@ -213,6 +213,9 @@ void Type::GetDescription(Stream *s, lldb::DescriptionLevel level,
case eEncodingIsVolatileUID:
s->PutCString(" (unresolved volatile type)");
break;
case eEncodingIsAtomicUID:
s->PutCString(" (unresolved atomic type)");
break;
case eEncodingIsTypedefUID:
s->PutCString(" (unresolved typedef)");
break;
@ -271,6 +274,9 @@ void Type::Dump(Stream *s, bool show_context) {
case eEncodingIsVolatileUID:
s->PutCString(" (unresolved volatile type)");
break;
case eEncodingIsAtomicUID:
s->PutCString(" (unresolved atomic type)");
break;
case eEncodingIsTypedefUID:
s->PutCString(" (unresolved typedef)");
break;
@ -343,6 +349,7 @@ llvm::Optional<uint64_t> Type::GetByteSize() {
case eEncodingIsConstUID:
case eEncodingIsRestrictUID:
case eEncodingIsVolatileUID:
case eEncodingIsAtomicUID:
case eEncodingIsTypedefUID: {
Type *encoding_type = GetEncodingType();
if (encoding_type)
@ -491,6 +498,11 @@ bool Type::ResolveClangType(ResolveState compiler_type_resolve_state) {
encoding_type->GetForwardCompilerType().AddVolatileModifier();
break;
case eEncodingIsAtomicUID:
m_compiler_type =
encoding_type->GetForwardCompilerType().GetAtomicType();
break;
case eEncodingIsTypedefUID:
m_compiler_type = encoding_type->GetForwardCompilerType().CreateTypedef(
m_name.AsCString("__lldb_invalid_typedef_name"),
@ -545,6 +557,10 @@ bool Type::ResolveClangType(ResolveState compiler_type_resolve_state) {
m_compiler_type = void_compiler_type.AddVolatileModifier();
break;
case eEncodingIsAtomicUID:
m_compiler_type = void_compiler_type.GetAtomicType();
break;
case eEncodingIsTypedefUID:
m_compiler_type = void_compiler_type.CreateTypedef(
m_name.AsCString("__lldb_invalid_typedef_name"),

View File

@ -89,6 +89,10 @@ TypeSystem::GetRValueReferenceType(lldb::opaque_compiler_type_t type) {
return CompilerType();
}
CompilerType TypeSystem::GetAtomicType(lldb::opaque_compiler_type_t type) {
return CompilerType();
}
CompilerType TypeSystem::AddConstModifier(lldb::opaque_compiler_type_t type) {
return CompilerType();
}

View File

@ -0,0 +1,104 @@
# REQUIRES: x86
# RUN: llvm-mc -triple=x86_64-pc-linux -filetype=obj %s > %t
# RUN: %lldb %t -o "target variable integer structure" -o exit | FileCheck %s
# CHECK: (_Atomic(int)) integer = 14159
# CHECK: (_Atomic(struct_type)) structure = {}
.data
integer:
.long 14159
structure:
.byte 0
.section .debug_abbrev,"",@progbits
.byte 1 # Abbreviation Code
.byte 17 # DW_TAG_compile_unit
.byte 1 # DW_CHILDREN_yes
.byte 37 # DW_AT_producer
.byte 8 # DW_FORM_string
.byte 19 # DW_AT_language
.byte 5 # DW_FORM_data2
.byte 0 # EOM(1)
.byte 0 # EOM(2)
.byte 2 # Abbreviation Code
.byte 52 # DW_TAG_variable
.byte 0 # DW_CHILDREN_no
.byte 3 # DW_AT_name
.byte 8 # DW_FORM_string
.byte 73 # DW_AT_type
.byte 19 # DW_FORM_ref4
.byte 2 # DW_AT_location
.byte 24 # DW_FORM_exprloc
.byte 0 # EOM(1)
.byte 0 # EOM(2)
.byte 3 # Abbreviation Code
.byte 71 # DW_TAG_atomic_type
.byte 0 # DW_CHILDREN_no
.byte 73 # DW_AT_type
.byte 19 # DW_FORM_ref4
.byte 0 # EOM(1)
.byte 0 # EOM(2)
.byte 4 # Abbreviation Code
.byte 36 # DW_TAG_base_type
.byte 0 # DW_CHILDREN_no
.byte 3 # DW_AT_name
.byte 8 # DW_FORM_string
.byte 62 # DW_AT_encoding
.byte 11 # DW_FORM_data1
.byte 11 # DW_AT_byte_size
.byte 11 # DW_FORM_data1
.byte 0 # EOM(1)
.byte 0 # EOM(2)
.byte 5 # Abbreviation Code
.byte 19 # DW_TAG_structure_type
.byte 0 # DW_CHILDREN_no
.byte 3 # DW_AT_name
.byte 8 # DW_FORM_string
.byte 11 # DW_AT_byte_size
.byte 11 # DW_FORM_data1
.byte 0 # EOM(1)
.byte 0 # EOM(2)
.byte 0 # EOM(3)
.section .debug_info,"",@progbits
.Lcu_begin0:
.long .Ldebug_info_end0-.Ldebug_info_start0 # Length of Unit
.Ldebug_info_start0:
.short 5 # DWARF version number
.byte 1 # DWARF Unit Type
.byte 8 # Address Size (in bytes)
.long .debug_abbrev # Offset Into Abbrev. Section
.byte 1 # Abbrev [1] 0xb:0x50 DW_TAG_compile_unit
.asciz "Hand-written DWARF" # DW_AT_producer
.short 12 # DW_AT_language
.byte 2 # Abbrev [2] DW_TAG_variable
.asciz "integer" # DW_AT_name
.long .Latomic_int # DW_AT_type
.byte 9 # DW_AT_location
.byte 3
.quad integer
.byte 2 # Abbrev [2] DW_TAG_variable
.asciz "structure" # DW_AT_name
.long .Latomic_struct # DW_AT_type
.byte 9 # DW_AT_location
.byte 3
.quad structure
.Latomic_int:
.byte 3 # Abbrev [3] DW_TAG_atomic_type
.long .Lint # DW_AT_type
.Lint:
.byte 4 # Abbrev [4] 0x53:0x7 DW_TAG_base_type
.asciz "int" # DW_AT_name
.byte 5 # DW_AT_encoding
.byte 4 # DW_AT_byte_size
.Latomic_struct:
.byte 3 # Abbrev [3] DW_TAG_atomic_type
.long .Lstruct # DW_AT_type
.Lstruct:
.byte 5 # Abbrev [5] DW_TAG_structure_type
.asciz "struct_type" # DW_AT_name
.byte 0 # DW_AT_byte_size
.byte 0 # End Of Children Mark
.Ldebug_info_end0: