diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2017-04-16 16:01:22 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2017-04-16 16:01:22 +0000 |
commit | 71d5a2540a98c81f5bcaeb48805e0e2881f530ef (patch) | |
tree | 5343938942df402b49ec7300a1c25a2d4ccd5821 /lib/IR/DebugInfo.cpp | |
parent | 31bbf64f3a4974a2d6c8b3b27ad2f519caf74057 (diff) | |
download | src-test2-71d5a2540a98c81f5bcaeb48805e0e2881f530ef.tar.gz src-test2-71d5a2540a98c81f5bcaeb48805e0e2881f530ef.zip |
Notes
Diffstat (limited to 'lib/IR/DebugInfo.cpp')
-rw-r--r-- | lib/IR/DebugInfo.cpp | 88 |
1 files changed, 75 insertions, 13 deletions
diff --git a/lib/IR/DebugInfo.cpp b/lib/IR/DebugInfo.cpp index 6b9bc689a446..c5d39c544304 100644 --- a/lib/IR/DebugInfo.cpp +++ b/lib/IR/DebugInfo.cpp @@ -79,9 +79,19 @@ void DebugInfoFinder::processModule(const Module &M) { processScope(M->getScope()); } } - for (auto &F : M.functions()) + for (auto &F : M.functions()) { if (auto *SP = cast_or_null<DISubprogram>(F.getSubprogram())) processSubprogram(SP); + // There could be subprograms from inlined functions referenced from + // instructions only. Walk the function to find them. + for (const BasicBlock &BB : F) { + for (const Instruction &I : BB) { + if (!I.getDebugLoc()) + continue; + processLocation(M, I.getDebugLoc().get()); + } + } + } } void DebugInfoFinder::processLocation(const Module &M, const DILocation *Loc) { @@ -239,6 +249,38 @@ bool DebugInfoFinder::addScope(DIScope *Scope) { return true; } +static llvm::MDNode *stripDebugLocFromLoopID(llvm::MDNode *N) { + assert(N->op_begin() != N->op_end() && "Missing self reference?"); + + // if there is no debug location, we do not have to rewrite this MDNode. + if (std::none_of(N->op_begin() + 1, N->op_end(), [](const MDOperand &Op) { + return isa<DILocation>(Op.get()); + })) + return N; + + // If there is only the debug location without any actual loop metadata, we + // can remove the metadata. + if (std::none_of(N->op_begin() + 1, N->op_end(), [](const MDOperand &Op) { + return !isa<DILocation>(Op.get()); + })) + return nullptr; + + SmallVector<Metadata *, 4> Args; + // Reserve operand 0 for loop id self reference. + auto TempNode = MDNode::getTemporary(N->getContext(), None); + Args.push_back(TempNode.get()); + // Add all non-debug location operands back. + for (auto Op = N->op_begin() + 1; Op != N->op_end(); Op++) { + if (!isa<DILocation>(*Op)) + Args.push_back(*Op); + } + + // Set the first operand to itself. + MDNode *LoopID = MDNode::get(N->getContext(), Args); + LoopID->replaceOperandWith(0, LoopID); + return LoopID; +} + bool llvm::stripDebugInfo(Function &F) { bool Changed = false; if (F.getSubprogram()) { @@ -246,6 +288,7 @@ bool llvm::stripDebugInfo(Function &F) { F.setSubprogram(nullptr); } + llvm::DenseMap<llvm::MDNode*, llvm::MDNode*> LoopIDsMap; for (BasicBlock &BB : F) { for (auto II = BB.begin(), End = BB.end(); II != End;) { Instruction &I = *II++; // We may delete the instruction, increment now. @@ -259,6 +302,15 @@ bool llvm::stripDebugInfo(Function &F) { I.setDebugLoc(DebugLoc()); } } + + auto *TermInst = BB.getTerminator(); + if (auto *LoopID = TermInst->getMetadata(LLVMContext::MD_loop)) { + auto *NewLoopID = LoopIDsMap.lookup(LoopID); + if (!NewLoopID) + NewLoopID = LoopIDsMap[LoopID] = stripDebugLocFromLoopID(LoopID); + if (NewLoopID != LoopID) + TermInst->setMetadata(LLVMContext::MD_loop, NewLoopID); + } } return Changed; } @@ -410,7 +462,8 @@ private: CU->isOptimized(), CU->getFlags(), CU->getRuntimeVersion(), CU->getSplitDebugFilename(), DICompileUnit::LineTablesOnly, EnumTypes, RetainedTypes, GlobalVariables, ImportedEntities, CU->getMacros(), - CU->getDWOId(), CU->getSplitDebugInlining()); + CU->getDWOId(), CU->getSplitDebugInlining(), + CU->getDebugInfoForProfiling()); } DILocation *getReplacementMDLocation(DILocation *MLD) { @@ -558,17 +611,26 @@ bool llvm::stripNonLineTableDebugInfo(Module &M) { } for (auto &BB : F) { for (auto &I : BB) { - if (I.getDebugLoc() == DebugLoc()) - continue; - - // Make a replacement. - auto &DL = I.getDebugLoc(); - auto *Scope = DL.getScope(); - MDNode *InlinedAt = DL.getInlinedAt(); - Scope = remap(Scope); - InlinedAt = remap(InlinedAt); - I.setDebugLoc( - DebugLoc::get(DL.getLine(), DL.getCol(), Scope, InlinedAt)); + auto remapDebugLoc = [&](DebugLoc DL) -> DebugLoc { + auto *Scope = DL.getScope(); + MDNode *InlinedAt = DL.getInlinedAt(); + Scope = remap(Scope); + InlinedAt = remap(InlinedAt); + return DebugLoc::get(DL.getLine(), DL.getCol(), Scope, InlinedAt); + }; + + if (I.getDebugLoc() != DebugLoc()) + I.setDebugLoc(remapDebugLoc(I.getDebugLoc())); + + // Remap DILocations in untyped MDNodes (e.g., llvm.loop). + SmallVector<std::pair<unsigned, MDNode *>, 2> MDs; + I.getAllMetadata(MDs); + for (auto Attachment : MDs) + if (auto *T = dyn_cast_or_null<MDTuple>(Attachment.second)) + for (unsigned N = 0; N < T->getNumOperands(); ++N) + if (auto *Loc = dyn_cast_or_null<DILocation>(T->getOperand(N))) + if (Loc != DebugLoc()) + T->replaceOperandWith(N, remapDebugLoc(Loc)); } } } |