diff options
| author | Chris Lattner <sabre@nondot.org> | 2009-12-30 21:42:11 +0000 | 
|---|---|---|
| committer | Chris Lattner <sabre@nondot.org> | 2009-12-30 21:42:11 +0000 | 
| commit | 30ae06be1495734d4679cdd7db732e02cf56a61c (patch) | |
| tree | 53d2c04144e9b72b4b4289fbe744231b5ad674c4 /llvm | |
| parent | 1563a76fd3ff23bb10f6f918ff2c92c10740fb68 (diff) | |
| download | bcm5719-llvm-30ae06be1495734d4679cdd7db732e02cf56a61c.tar.gz bcm5719-llvm-30ae06be1495734d4679cdd7db732e02cf56a61c.zip | |
do not bother reuniquing mdnodes whose operands drop to null.  Doing
so can be a huge performance issue when tearing down modules and mdnodes
are not guaranteed to be unique anyway.  This speeds up:
$ time ~/llvm/Release/bin/clang gcc.c -w -S -g
from 72 to 35s, where gcc.c is from:
http://people.csail.mit.edu/smcc/projects/single-file-programs/
llvm-svn: 92315
Diffstat (limited to 'llvm')
| -rw-r--r-- | llvm/include/llvm/Metadata.h | 18 | ||||
| -rw-r--r-- | llvm/lib/VMCore/Metadata.cpp | 36 | 
2 files changed, 42 insertions, 12 deletions
| diff --git a/llvm/include/llvm/Metadata.h b/llvm/include/llvm/Metadata.h index 86eba354e2c..b53fd49b6cc 100644 --- a/llvm/include/llvm/Metadata.h +++ b/llvm/include/llvm/Metadata.h @@ -85,8 +85,6 @@ class MDNodeElement;  //===----------------------------------------------------------------------===//  /// MDNode - a tuple of other values. -/// These contain a list of the values that represent the metadata.  -/// MDNode is always unnamed.  class MDNode : public MetadataBase, public FoldingSetNode {    MDNode(const MDNode &);                // DO NOT IMPLEMENT    void operator=(const MDNode &);        // DO NOT IMPLEMENT @@ -97,7 +95,14 @@ class MDNode : public MetadataBase, public FoldingSetNode {    // Subclass data enums.    enum { -    FunctionLocalBit = 1 +    /// FunctionLocalBit - This bit is set if this MDNode is function local. +    /// This is true when it (potentially transitively) contains a reference to +    /// something in a function, like an argument, basicblock, or instruction. +    FunctionLocalBit = 1 << 0, +     +    /// NotUniquedBit - This is set on MDNodes that are not uniqued because they +    /// have a null perand. +    NotUniquedBit    = 1 << 1    };    // Replace each instance of F from the element list of this node with T. @@ -138,6 +143,13 @@ public:      return V->getValueID() == MDNodeVal;    }  private: +  bool isNotUniqued() const {  +    return (getSubclassDataFromValue() & NotUniquedBit) != 0; +  } +  void setIsNotUniqued() { +    setValueSubclassData(getSubclassDataFromValue() | NotUniquedBit); +  } +      // Shadow Value::setValueSubclassData with a private forwarding method so that    // any future subclasses cannot accidentally use it.    void setValueSubclassData(unsigned short D) { diff --git a/llvm/lib/VMCore/Metadata.cpp b/llvm/lib/VMCore/Metadata.cpp index d5c1dba2d7b..0bed865bbae 100644 --- a/llvm/lib/VMCore/Metadata.cpp +++ b/llvm/lib/VMCore/Metadata.cpp @@ -87,8 +87,10 @@ void MDNodeElement::allUsesReplacedWith(Value *NV) {  /// ~MDNode - Destroy MDNode.  MDNode::~MDNode() { -  LLVMContextImpl *pImpl = getType()->getContext().pImpl; -  pImpl->MDNodeSet.RemoveNode(this); +  if (!isNotUniqued()) { +    LLVMContextImpl *pImpl = getType()->getContext().pImpl; +    pImpl->MDNodeSet.RemoveNode(this); +  }    delete [] Operands;    Operands = NULL;  } @@ -97,6 +99,7 @@ MDNode::MDNode(LLVMContext &C, Value *const *Vals, unsigned NumVals,                 bool isFunctionLocal)    : MetadataBase(Type::getMetadataTy(C), Value::MDNodeVal) {    NumOperands = NumVals; +  // FIXME: Coallocate the operand list.  These have fixed arity.    Operands = new MDNodeElement[NumOperands];    for (unsigned i = 0; i != NumVals; ++i)  @@ -146,25 +149,40 @@ void MDNode::replaceElement(MDNodeElement *Op, Value *To) {    if (From == To)      return; +  // Update the operand. +  Op->set(To, this); + +  // If this node is already not being uniqued (because one of the operands +  // already went to null), then there is nothing else to do here. +  if (isNotUniqued()) return; +      LLVMContextImpl *pImpl = getType()->getContext().pImpl;    // Remove "this" from the context map.  FoldingSet doesn't have to reprofile    // this node to remove it, so we don't care what state the operands are in.    pImpl->MDNodeSet.RemoveNode(this); -  // Update the operand. -  Op->set(To, this); - -  // Insert updated "this" into the context's folding node set. -  // If a node with same element list already exist then before inserting  -  // updated "this" into the folding node set, replace all uses of existing  -  // node with updated "this" node. +  // If we are dropping an argument to null, we choose to not unique the MDNode +  // anymore.  This commonly occurs during destruction, and uniquing these +  // brings little reuse. +  if (To == 0) { +    setIsNotUniqued(); +    return; +  } +   +  // Now that the node is out of the folding set, get ready to reinsert it. +  // First, check to see if another node with the same operands already exists +  // in the set.  If it doesn't exist, this returns the position to insert it.    FoldingSetNodeID ID;    Profile(ID);    void *InsertPoint;    MDNode *N = pImpl->MDNodeSet.FindNodeOrInsertPos(ID, InsertPoint);    if (N) { +    // FIXME: +    // If it already exists in the set, we don't reinsert it, we just claim it +    // isn't uniqued. +          N->replaceAllUsesWith(this);      delete N;      N = pImpl->MDNodeSet.FindNodeOrInsertPos(ID, InsertPoint); | 

