diff --git a/lib/AsmParser/LLParser.cpp b/lib/AsmParser/LLParser.cpp index 6e79960e3db..ed1d0ff9ee6 100644 --- a/lib/AsmParser/LLParser.cpp +++ b/lib/AsmParser/LLParser.cpp @@ -3041,7 +3041,9 @@ struct MDConstant : public MDFieldImpl { MDConstant() : ImplTy(nullptr) {} }; struct MDStringField : public MDFieldImpl { - MDStringField() : ImplTy(nullptr) {} + bool AllowEmpty; + MDStringField(bool AllowEmpty = true) + : ImplTy(nullptr), AllowEmpty(AllowEmpty) {} }; struct MDFieldList : public MDFieldImpl> { MDFieldList() : ImplTy(SmallVector()) {} @@ -3253,10 +3255,14 @@ bool LLParser::ParseMDField(LocTy Loc, StringRef Name, MDConstant &Result) { template <> bool LLParser::ParseMDField(LocTy Loc, StringRef Name, MDStringField &Result) { + LocTy ValueLoc = Lex.getLoc(); std::string S; if (ParseStringConstant(S)) return true; + if (!Result.AllowEmpty && S.empty()) + return Error(ValueLoc, "'" + Name + "' cannot be empty"); + Result.assign(S.empty() ? nullptr : MDString::get(Context, S)); return false; } @@ -3655,8 +3661,8 @@ bool LLParser::ParseMDTemplateValueParameter(MDNode *&Result, bool IsDistinct) { /// declaration: !3) bool LLParser::ParseMDGlobalVariable(MDNode *&Result, bool IsDistinct) { #define VISIT_MD_FIELDS(OPTIONAL, REQUIRED) \ + REQUIRED(name, MDStringField, (/* AllowEmpty */ false)); \ OPTIONAL(scope, MDField, ); \ - OPTIONAL(name, MDStringField, ); \ OPTIONAL(linkageName, MDStringField, ); \ OPTIONAL(file, MDField, ); \ OPTIONAL(line, LineField, ); \ diff --git a/lib/IR/DebugInfo.cpp b/lib/IR/DebugInfo.cpp index 4e5b5f1f975..91823773212 100644 --- a/lib/IR/DebugInfo.cpp +++ b/lib/IR/DebugInfo.cpp @@ -275,16 +275,6 @@ bool DISubprogram::Verify() const { if (!N) return false; - if (!isScopeRef(N->getScope())) - return false; - - if (auto *Op = N->getType()) - if (!isa(Op)) - return false; - - if (!isTypeRef(getContainingType())) - return false; - if (isLValueReference() && isRValueReference()) return false; @@ -315,38 +305,8 @@ bool DISubprogram::Verify() const { return true; } -bool DIGlobalVariable::Verify() const { - auto *N = dyn_cast_or_null(DbgNode); - - if (!N) - return false; - - if (N->getDisplayName().empty()) - return false; - - if (auto *Op = N->getScope()) - if (!isa(Op)) - return false; - - if (auto *Op = N->getStaticDataMemberDeclaration()) - if (!isa(Op)) - return false; - - return isTypeRef(N->getType()); -} - -bool DIVariable::Verify() const { - auto *N = dyn_cast_or_null(DbgNode); - - if (!N) - return false; - - if (auto *Op = N->getScope()) - if (!isa(Op)) - return false; - - return isTypeRef(N->getType()); -} +bool DIGlobalVariable::Verify() const { return isGlobalVariable(); } +bool DIVariable::Verify() const { return isVariable(); } bool DILocation::Verify() const { return dyn_cast_or_null(DbgNode); diff --git a/lib/IR/Verifier.cpp b/lib/IR/Verifier.cpp index 4bf24211963..19897d4c030 100644 --- a/lib/IR/Verifier.cpp +++ b/lib/IR/Verifier.cpp @@ -969,6 +969,7 @@ void Verifier::visitMDGlobalVariable(const MDGlobalVariable &N) { visitMDVariable(N); Assert(N.getTag() == dwarf::DW_TAG_variable, "invalid tag", &N); + Assert(!N.getName().empty(), "missing global variable name", &N); if (auto *V = N.getRawVariable()) { Assert(isa(V) && !isa(cast(V)->getValue()), diff --git a/test/Assembler/invalid-mdglobalvariable-empty-name.ll b/test/Assembler/invalid-mdglobalvariable-empty-name.ll new file mode 100644 index 00000000000..77a9f4d773e --- /dev/null +++ b/test/Assembler/invalid-mdglobalvariable-empty-name.ll @@ -0,0 +1,4 @@ +; RUN: not llvm-as < %s -disable-output 2>&1 | FileCheck %s + +; CHECK: :[[@LINE+1]]:30: error: 'name' cannot be empty +!0 = !MDGlobalVariable(name: "") diff --git a/test/Assembler/invalid-mdglobalvariable-missing-name.ll b/test/Assembler/invalid-mdglobalvariable-missing-name.ll new file mode 100644 index 00000000000..d57d71e2d95 --- /dev/null +++ b/test/Assembler/invalid-mdglobalvariable-missing-name.ll @@ -0,0 +1,4 @@ +; RUN: not llvm-as < %s -disable-output 2>&1 | FileCheck %s + +; CHECK: :[[@LINE+1]]:24: error: missing required field 'name' +!0 = !MDGlobalVariable() diff --git a/test/Assembler/mdglobalvariable.ll b/test/Assembler/mdglobalvariable.ll index d48fef93cda..2726f4f3510 100644 --- a/test/Assembler/mdglobalvariable.ll +++ b/test/Assembler/mdglobalvariable.ll @@ -17,8 +17,8 @@ file: !2, line: 7, type: !3, isLocal: true, isDefinition: false, variable: i32* @foo) -; CHECK: !6 = !MDGlobalVariable(scope: !0, isLocal: false, isDefinition: true) -!6 = !MDGlobalVariable(scope: !0) +; CHECK: !6 = !MDGlobalVariable(name: "foo", scope: !0, isLocal: false, isDefinition: true) +!6 = !MDGlobalVariable(name: "foo", scope: !0) !7 = !MDCompositeType(tag: DW_TAG_structure_type, name: "Class", size: 8, align: 8) !8 = !MDDerivedType(tag: DW_TAG_member, name: "mem", flags: DIFlagStaticMember, scope: !7, baseType: !3)