From fe14568a8122b7c9b832795594b7bae11b2b6cc4 Mon Sep 17 00:00:00 2001 From: Chris Lattner Date: Wed, 17 Apr 2002 03:24:59 +0000 Subject: [PATCH] Make data structure acurately get ALL edges, even loads of null fields of nodes that are not shadow nodes This fixes em3d to be _correct_ if not optimial git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@2274 91177308-0d34-0410-b5e6-96231b3b80d8 --- .../DataStructure/FunctionRepBuilder.cpp | 27 ++++++++++++------- .../DataStructure/FunctionRepBuilder.h | 9 ++++--- lib/Analysis/DataStructure/NodeImpl.cpp | 23 ++++++---------- 3 files changed, 30 insertions(+), 29 deletions(-) diff --git a/lib/Analysis/DataStructure/FunctionRepBuilder.cpp b/lib/Analysis/DataStructure/FunctionRepBuilder.cpp index 6dc2930243c..e9b6f199d7e 100644 --- a/lib/Analysis/DataStructure/FunctionRepBuilder.cpp +++ b/lib/Analysis/DataStructure/FunctionRepBuilder.cpp @@ -20,22 +20,30 @@ // chain.. // FIXME: This should not take a FunctionRepBuilder as an argument! // -ShadowDSNode *ShadowDSNode::synthesizeNode(const Type *Ty, - FunctionRepBuilder *Rep) { +ShadowDSNode *DSNode::synthesizeNode(const Type *Ty, + FunctionRepBuilder *Rep) { // If we are a derived shadow node, defer to our parent to synthesize the node - if (ShadowParent) return ShadowParent->synthesizeNode(Ty, Rep); + if (ShadowDSNode *Th = dyn_cast(this)) + if (Th->getShadowParent()) + return Th->getShadowParent()->synthesizeNode(Ty, Rep); // See if we have already synthesized a node of this type... for (unsigned i = 0, e = SynthNodes.size(); i != e; ++i) if (SynthNodes[i].first == Ty) return SynthNodes[i].second; // No we haven't. Do so now and add it to our list of saved nodes... - ShadowDSNode *SN = new ShadowDSNode(Ty, Mod, this); + ShadowDSNode *SN = Rep->makeSynthesizedShadow(Ty, this); SynthNodes.push_back(make_pair(Ty, SN)); - Rep->addShadowNode(SN); return SN; } +ShadowDSNode *FunctionRepBuilder::makeSynthesizedShadow(const Type *Ty, + DSNode *Parent) { + ShadowDSNode *Result = new ShadowDSNode(Ty, F->getFunction()->getParent(), + Parent); + ShadowNodes.push_back(Result); + return Result; +} @@ -195,7 +203,6 @@ PointerVal FunctionRepBuilder::getIndexedPointerDest(const PointerVal &InP, static PointerValSet &getField(const PointerVal &DestPtr) { assert(DestPtr.Node != 0); - return DestPtr.Node->getLink(DestPtr.Index); } @@ -232,8 +239,8 @@ void FunctionRepBuilder::visitReturnInst(ReturnInst *RI) { void FunctionRepBuilder::visitLoadInst(LoadInst *LI) { // Only loads that return pointers are interesting... - if (!isa(LI->getType())) return; - const PointerType *DestTy = cast(LI->getType()); + const PointerType *DestTy = dyn_cast(LI->getType()); + if (DestTy == 0) return; const PointerValSet &SrcPVS = ValueMap[LI->getOperand(0)]; PointerValSet &LIPVS = ValueMap[LI]; @@ -245,12 +252,12 @@ void FunctionRepBuilder::visitLoadInst(LoadInst *LI) { if (Field.size()) { // Field loaded wasn't null? Changed |= LIPVS.add(Field); - } else if (ShadowDSNode *Shad = dyn_cast(Ptr.Node)) { + } else { // If we are loading a null field out of a shadow node, we need to // synthesize a new shadow node and link it in... // ShadowDSNode *SynthNode = - Shad->synthesizeNode(DestTy->getElementType(), this); + Ptr.Node->synthesizeNode(DestTy->getElementType(), this); Field.add(SynthNode); Changed |= LIPVS.add(Field); diff --git a/lib/Analysis/DataStructure/FunctionRepBuilder.h b/lib/Analysis/DataStructure/FunctionRepBuilder.h index 54bfbba86df..e45ea419989 100644 --- a/lib/Analysis/DataStructure/FunctionRepBuilder.h +++ b/lib/Analysis/DataStructure/FunctionRepBuilder.h @@ -12,7 +12,7 @@ #include "llvm/Support/InstVisitor.h" // DEBUG_DATA_STRUCTURE_CONSTRUCTION - Define this to 1 if you want debug output -#define DEBUG_DATA_STRUCTURE_CONSTRUCTION 0 +//#define DEBUG_DATA_STRUCTURE_CONSTRUCTION 1 class FunctionRepBuilder; @@ -82,7 +82,8 @@ public: const std::vector &getGlobalNodes() const {return GlobalNodes;} const std::vector &getCallNodes() const { return CallNodes; } - void addShadowNode(ShadowDSNode *SN) { ShadowNodes.push_back(SN); } + + ShadowDSNode *makeSynthesizedShadow(const Type *Ty, DSNode *Parent); const PointerValSet &getRetNode() const { return RetNode; } @@ -96,12 +97,12 @@ private: // While the worklist still has instructions to process, process them! while (!WorkList.empty()) { Instruction *I = WorkList.back(); WorkList.pop_back(); -#if DEBUG_DATA_STRUCTURE_CONSTRUCTION +#ifdef DEBUG_DATA_STRUCTURE_CONSTRUCTION cerr << "Processing worklist inst: " << I; #endif visit(I); // Dispatch to a visitXXX function based on instruction type... -#if DEBUG_DATA_STRUCTURE_CONSTRUCTION +#ifdef DEBUG_DATA_STRUCTURE_CONSTRUCTION if (I->hasName() && ValueMap.count(I)) { cerr << "Inst %" << I->getName() << " value is:\n"; ValueMap[I].print(cerr); diff --git a/lib/Analysis/DataStructure/NodeImpl.cpp b/lib/Analysis/DataStructure/NodeImpl.cpp index 732ab6a9950..4451f6e59bb 100644 --- a/lib/Analysis/DataStructure/NodeImpl.cpp +++ b/lib/Analysis/DataStructure/NodeImpl.cpp @@ -208,6 +208,13 @@ void DSNode::mapNode(map &NodeMap, const DSNode *Old) { "Cloned nodes do not have the same number of links!"); for (unsigned j = 0, je = FieldLinks.size(); j != je; ++j) MapPVS(FieldLinks[j], Old->FieldLinks[j], NodeMap); + + // Map our SynthNodes... + assert(SynthNodes.empty() && "Synthnodes already mapped?"); + SynthNodes.reserve(Old->SynthNodes.size()); + for (unsigned i = 0, e = Old->SynthNodes.size(); i != e; ++i) + SynthNodes.push_back(std::make_pair(Old->SynthNodes[i].first, + (ShadowDSNode*)NodeMap[Old->SynthNodes[i].second])); } AllocDSNode::AllocDSNode(AllocationInst *V) @@ -251,7 +258,7 @@ ShadowDSNode::ShadowDSNode(const Type *Ty, Module *M) : DSNode(ShadowNode, Ty) { ShadowParent = 0; } -ShadowDSNode::ShadowDSNode(const Type *Ty, Module *M, ShadowDSNode *ShadParent) +ShadowDSNode::ShadowDSNode(const Type *Ty, Module *M, DSNode *ShadParent) : DSNode(ShadowNode, Ty) { Mod = M; ShadowParent = ShadParent; @@ -264,20 +271,6 @@ std::string ShadowDSNode::getCaption() const { return OS.str(); } -void ShadowDSNode::mapNode(map &NodeMap, - const DSNode *O) { - const ShadowDSNode *Old = (ShadowDSNode*)O; - DSNode::mapNode(NodeMap, Old); // Map base portions first... - - // Map our SynthNodes... - assert(SynthNodes.empty() && "Synthnodes already mapped?"); - SynthNodes.reserve(Old->SynthNodes.size()); - for (unsigned i = 0, e = Old->SynthNodes.size(); i != e; ++i) - SynthNodes.push_back(std::make_pair(Old->SynthNodes[i].first, - (ShadowDSNode*)NodeMap[Old->SynthNodes[i].second])); -} - - CallDSNode::CallDSNode(CallInst *ci) : DSNode(CallNode, ci->getType()), CI(ci) { unsigned NumPtrs = 0; for (unsigned i = 0, e = ci->getNumOperands(); i != e; ++i)