Linker: Copy metadata when linking declarations.

Differential Revision: http://reviews.llvm.org/D21624

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@273692 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Peter Collingbourne 2016-06-24 17:42:21 +00:00
parent b892430f09
commit 43c5139fd2
4 changed files with 36 additions and 4 deletions

View File

@ -114,6 +114,9 @@ public:
/// Erase all metadata attachments with the given kind. /// Erase all metadata attachments with the given kind.
void eraseMetadata(unsigned KindID); void eraseMetadata(unsigned KindID);
/// Copy metadata from Src.
void copyMetadata(const GlobalObject *Src);
void copyAttributesFrom(const GlobalValue *Src) override; void copyAttributesFrom(const GlobalValue *Src) override;
// Methods for support type inquiry through isa, cast, and dyn_cast: // Methods for support type inquiry through isa, cast, and dyn_cast:

View File

@ -1393,6 +1393,13 @@ MDNode *GlobalObject::getMetadata(StringRef Kind) const {
return getMetadata(getContext().getMDKindID(Kind)); return getMetadata(getContext().getMDKindID(Kind));
} }
void GlobalObject::copyMetadata(const GlobalObject *Other) {
SmallVector<std::pair<unsigned, MDNode *>, 8> MDs;
Other->getAllMetadata(MDs);
for (auto &MD : MDs)
addMetadata(MD.first, *MD.second);
}
void Function::setSubprogram(DISubprogram *SP) { void Function::setSubprogram(DISubprogram *SP) {
setMetadata(LLVMContext::MD_dbg, SP); setMetadata(LLVMContext::MD_dbg, SP);
} }

View File

@ -638,6 +638,12 @@ GlobalValue *IRLinker::copyGlobalValueProto(const GlobalValue *SGV,
NewGV->copyAttributesFrom(SGV); NewGV->copyAttributesFrom(SGV);
if (auto *NewGO = dyn_cast<GlobalObject>(NewGV)) {
// Metadata for global variables and function declarations is copied eagerly.
if (isa<GlobalVariable>(SGV) || SGV->isDeclaration())
NewGO->copyMetadata(cast<GlobalObject>(SGV));
}
// Remove these copied constants in case this stays a declaration, since // Remove these copied constants in case this stays a declaration, since
// they point to the source module. If the def is linked the values will // they point to the source module. If the def is linked the values will
// be mapped in during linkFunctionBody. // be mapped in during linkFunctionBody.
@ -961,10 +967,7 @@ Error IRLinker::linkFunctionBody(Function &Dst, Function &Src) {
Dst.setPersonalityFn(Src.getPersonalityFn()); Dst.setPersonalityFn(Src.getPersonalityFn());
// Copy over the metadata attachments without remapping. // Copy over the metadata attachments without remapping.
SmallVector<std::pair<unsigned, MDNode *>, 8> MDs; Dst.copyMetadata(&Src);
Src.getAllMetadata(MDs);
for (const auto &I : MDs)
Dst.setMetadata(I.first, I.second);
// Steal arguments and splice the body of Src into Dst. // Steal arguments and splice the body of Src into Dst.
Dst.stealArgumentListFrom(Src); Dst.stealArgumentListFrom(Src);

View File

@ -0,0 +1,19 @@
; RUN: llvm-link %s -S -o - | FileCheck %s
; CHECK: @g1 = global i32 0, !attach !0
@g1 = global i32 0, !attach !0
; CHECK: @g2 = external global i32, !attach !0
@g2 = external global i32, !attach !0
; CHECK: define void @f1() !attach !0
define void @f1() !attach !0 {
call void @f2()
store i32 0, i32* @g2
ret void
}
; CHECK: declare !attach !0 void @f2()
declare !attach !0 void @f2()
!0 = !{}