From 834f85c5e6f87aeaeab1311498e1fc9fae0580ac Mon Sep 17 00:00:00 2001 From: Peter Collingbourne Date: Wed, 25 Nov 2015 02:54:07 +0000 Subject: [PATCH] AsmParser: Make the code for parsing unnamed aliases more closely resemble that for unnamed globals. This fixes parsing of forward references to unnamed aliases. While here, remove an unnecessary isa check. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@254054 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/AsmParser/LLParser.cpp | 45 +++++++++++++++++----------- test/Assembler/alias-redefinition.ll | 2 +- test/Assembler/unnamed-alias.ll | 4 +-- 3 files changed, 30 insertions(+), 21 deletions(-) diff --git a/lib/AsmParser/LLParser.cpp b/lib/AsmParser/LLParser.cpp index 399364e5eb2..307ed397834 100644 --- a/lib/AsmParser/LLParser.cpp +++ b/lib/AsmParser/LLParser.cpp @@ -713,6 +713,24 @@ bool LLParser::ParseAlias(const std::string &Name, LocTy NameLoc, unsigned L, ExplicitTypeLoc, "explicit pointee type doesn't match operand's pointee type"); + GlobalValue *GVal = nullptr; + + // See if the alias was forward referenced, if so, prepare to replace the + // forward reference. + if (!Name.empty()) { + GVal = M->getNamedValue(Name); + if (GVal) { + if (!ForwardRefVals.erase(Name)) + return Error(NameLoc, "redefinition of global '@" + Name + "'"); + } + } else { + auto I = ForwardRefValIDs.find(NumberedVals.size()); + if (I != ForwardRefValIDs.end()) { + GVal = I->second.first; + ForwardRefValIDs.erase(I); + } + } + // Okay, create the alias but do not insert it into the module yet. std::unique_ptr GA( GlobalAlias::create(Ty, AddrSpace, (GlobalValue::LinkageTypes)Linkage, @@ -725,26 +743,17 @@ bool LLParser::ParseAlias(const std::string &Name, LocTy NameLoc, unsigned L, if (Name.empty()) NumberedVals.push_back(GA.get()); - // See if this value already exists in the symbol table. If so, it is either - // a redefinition or a definition of a forward reference. - if (GlobalValue *Val = M->getNamedValue(Name)) { - // See if this was a redefinition. If so, there is no entry in - // ForwardRefVals. - auto I = ForwardRefVals.find(Name); - if (I == ForwardRefVals.end()) - return Error(NameLoc, "redefinition of global named '@" + Name + "'"); - - // Otherwise, this was a definition of forward ref. Verify that types - // agree. - if (Val->getType() != GA->getType()) - return Error(NameLoc, - "forward reference and definition of alias have different types"); + if (GVal) { + // Verify that types agree. + if (GVal->getType() != GA->getType()) + return Error( + ExplicitTypeLoc, + "forward reference and definition of alias have different types"); // If they agree, just RAUW the old value with the alias and remove the // forward ref info. - Val->replaceAllUsesWith(GA.get()); - Val->eraseFromParent(); - ForwardRefVals.erase(I); + GVal->replaceAllUsesWith(GA.get()); + GVal->eraseFromParent(); } // Insert into the module, we know its name won't collide now. @@ -809,7 +818,7 @@ bool LLParser::ParseGlobal(const std::string &Name, LocTy NameLoc, if (!Name.empty()) { GVal = M->getNamedValue(Name); if (GVal) { - if (!ForwardRefVals.erase(Name) || !isa(GVal)) + if (!ForwardRefVals.erase(Name)) return Error(NameLoc, "redefinition of global '@" + Name + "'"); } } else { diff --git a/test/Assembler/alias-redefinition.ll b/test/Assembler/alias-redefinition.ll index 7c57b63b66f..3c36c81d813 100644 --- a/test/Assembler/alias-redefinition.ll +++ b/test/Assembler/alias-redefinition.ll @@ -1,6 +1,6 @@ ; RUN: not llvm-as %s 2>&1 | FileCheck %s -; CHECK: error: redefinition of global named '@bar' +; CHECK: error: redefinition of global '@bar' @foo = global i32 0 @bar = alias i32, i32* @foo diff --git a/test/Assembler/unnamed-alias.ll b/test/Assembler/unnamed-alias.ll index ebba091d770..121e54b7d07 100644 --- a/test/Assembler/unnamed-alias.ll +++ b/test/Assembler/unnamed-alias.ll @@ -5,7 +5,7 @@ @1 = private constant i32 1 ; CHECK: @1 = private constant i32 1 -@2 = private alias i32, i32* @0 -; CHECK: @2 = private alias i32, i32* @0 +@2 = private alias i32, i32* @3 +; CHECK: @2 = private alias i32, i32* @3 @3 = private alias i32, i32* @1 ; CHECK: @3 = private alias i32, i32* @1 -- 2.34.1