OSDN Git Service

IR: Prepare for a new UniquableMDNode subclass, NFC
authorDuncan P. N. Exon Smith <dexonsmith@apple.com>
Mon, 12 Jan 2015 20:56:33 +0000 (20:56 +0000)
committerDuncan P. N. Exon Smith <dexonsmith@apple.com>
Mon, 12 Jan 2015 20:56:33 +0000 (20:56 +0000)
Add generic dispatch for the parts of `UniquableMDNode` that cast to
`MDTuple`.  This makes adding other subclasses (like PR21433's
`MDLocation`) easier.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@225697 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/IR/Metadata.def
include/llvm/IR/Metadata.h
lib/IR/LLVMContextImpl.cpp
lib/IR/Metadata.cpp

index 33b9ca0..2d5d91e 100644 (file)
@@ -12,7 +12,8 @@
 //===----------------------------------------------------------------------===//
 
 #if !(defined HANDLE_METADATA || defined HANDLE_METADATA_LEAF ||               \
-      defined HANDLE_METADATA_BRANCH)
+      defined HANDLE_METADATA_BRANCH || defined HANDLE_UNIQUABLE_LEAF ||       \
+      defined HANDLE_UNIQUABLE_BRANCH)
 #error "Missing macro definition of HANDLE_METADATA*"
 #endif
 
 #define HANDLE_METADATA_BRANCH(CLASS) HANDLE_METADATA(CLASS)
 #endif
 
+// Handler for leaf nodes under UniquableMDNode.
+#ifndef HANDLE_UNIQUABLE_LEAF
+#define HANDLE_UNIQUABLE_LEAF(CLASS) HANDLE_METADATA_LEAF(CLASS)
+#endif
+
+// Handler for non-leaf nodes under UniquableMDNode.
+#ifndef HANDLE_UNIQUABLE_BRANCH
+#define HANDLE_UNIQUABLE_BRANCH(CLASS) HANDLE_METADATA_BRANCH(CLASS)
+#endif
+
 HANDLE_METADATA_LEAF(MDString)
 HANDLE_METADATA_BRANCH(ValueAsMetadata)
 HANDLE_METADATA_LEAF(ConstantAsMetadata)
 HANDLE_METADATA_LEAF(LocalAsMetadata)
 HANDLE_METADATA_BRANCH(MDNode)
 HANDLE_METADATA_LEAF(MDNodeFwdDecl)
-HANDLE_METADATA_BRANCH(UniquableMDNode)
-HANDLE_METADATA_LEAF(MDTuple)
+HANDLE_UNIQUABLE_BRANCH(UniquableMDNode)
+HANDLE_UNIQUABLE_LEAF(MDTuple)
 
 #undef HANDLE_METADATA
 #undef HANDLE_METADATA_LEAF
 #undef HANDLE_METADATA_BRANCH
+#undef HANDLE_UNIQUABLE_LEAF
+#undef HANDLE_UNIQUABLE_BRANCH
index cc193df..e813ae9 100644 (file)
@@ -755,6 +755,10 @@ private:
   void resolve();
   void resolveAfterOperandChange(Metadata *Old, Metadata *New);
   void decrementUnresolvedOperandCount();
+
+  void deleteAsSubclass();
+  UniquableMDNode *uniquify();
+  void eraseFromStore();
 };
 
 /// \brief Tuple of metadata.
@@ -794,6 +798,10 @@ public:
   static bool classof(const Metadata *MD) {
     return MD->getMetadataID() == MDTupleKind;
   }
+
+private:
+  MDTuple *uniquifyImpl();
+  void eraseFromStoreImpl();
 };
 
 MDNode *MDNode::get(LLVMContext &Context, ArrayRef<Metadata *> MDs) {
index c78b760..d47a0d3 100644 (file)
@@ -142,7 +142,7 @@ LLVMContextImpl::~LLVMContextImpl() {
     I->dropAllReferences();
 
   for (UniquableMDNode *I : DistinctMDNodes)
-    delete cast<MDTuple>(I);
+    I->deleteAsSubclass();
   for (MDTuple *I : MDTuples)
     delete I;
 
index fa1f302..1384431 100644 (file)
@@ -525,8 +525,8 @@ void UniquableMDNode::handleChangedOperand(void *Ref, Metadata *New) {
     return;
   }
 
-  auto &Store = getContext().pImpl->MDTuples;
-  Store.erase(cast<MDTuple>(this));
+  // This node is uniqued.
+  eraseFromStore();
 
   Metadata *Old = getOperand(Op);
   setOperand(Op, New);
@@ -540,15 +540,10 @@ void UniquableMDNode::handleChangedOperand(void *Ref, Metadata *New) {
   }
 
   // Re-unique the node.
-  cast<MDTuple>(this)->recalculateHash();
-  MDTupleInfo::KeyTy Key(cast<MDTuple>(this));
-  auto I = Store.find_as(Key);
-  if (I == Store.end()) {
-    Store.insert(cast<MDTuple>(this));
-
+  auto *Uniqued = uniquify();
+  if (Uniqued == this) {
     if (!isResolved())
       resolveAfterOperandChange(Old, New);
-
     return;
   }
 
@@ -560,8 +555,8 @@ void UniquableMDNode::handleChangedOperand(void *Ref, Metadata *New) {
     // dropAllReferences(), but we still need the use-list).
     for (unsigned O = 0, E = getNumOperands(); O != E; ++O)
       setOperand(O, nullptr);
-    ReplaceableUses->replaceAllUsesWith(*I);
-    delete cast<MDTuple>(this);
+    ReplaceableUses->replaceAllUsesWith(Uniqued);
+    deleteAsSubclass();
     return;
   }
 
@@ -569,6 +564,41 @@ void UniquableMDNode::handleChangedOperand(void *Ref, Metadata *New) {
   storeDistinctInContext();
 }
 
+void UniquableMDNode::deleteAsSubclass() {
+  switch (getMetadataID()) {
+  default:
+    llvm_unreachable("Invalid subclass of UniquableMDNode");
+#define HANDLE_UNIQUABLE_LEAF(CLASS)                                           \
+  case CLASS##Kind:                                                            \
+    delete cast<CLASS>(this);                                                  \
+    break;
+#include "llvm/IR/Metadata.def"
+  }
+}
+
+UniquableMDNode *UniquableMDNode::uniquify() {
+  switch (getMetadataID()) {
+  default:
+    llvm_unreachable("Invalid subclass of UniquableMDNode");
+#define HANDLE_UNIQUABLE_LEAF(CLASS)                                           \
+  case CLASS##Kind:                                                            \
+    return cast<CLASS>(this)->uniquifyImpl();
+#include "llvm/IR/Metadata.def"
+  }
+}
+
+void UniquableMDNode::eraseFromStore() {
+  switch (getMetadataID()) {
+  default:
+    llvm_unreachable("Invalid subclass of UniquableMDNode");
+#define HANDLE_UNIQUABLE_LEAF(CLASS)                                           \
+  case CLASS##Kind:                                                            \
+    cast<CLASS>(this)->eraseFromStoreImpl();                                   \
+    break;
+#include "llvm/IR/Metadata.def"
+  }
+}
+
 MDTuple *MDTuple::getImpl(LLVMContext &Context, ArrayRef<Metadata *> MDs,
                           bool ShouldCreate) {
   MDTupleInfo::KeyTy Key(MDs);
@@ -593,6 +623,21 @@ MDTuple *MDTuple::getDistinct(LLVMContext &Context, ArrayRef<Metadata *> MDs) {
   return N;
 }
 
+MDTuple *MDTuple::uniquifyImpl() {
+  recalculateHash();
+  MDTupleInfo::KeyTy Key(this);
+
+  auto &Store = getContext().pImpl->MDTuples;
+  auto I = Store.find_as(Key);
+  if (I == Store.end()) {
+    Store.insert(this);
+    return this;
+  }
+  return *I;
+}
+
+void MDTuple::eraseFromStoreImpl() { getContext().pImpl->MDTuples.erase(this); }
+
 MDNodeFwdDecl *MDNode::getTemporary(LLVMContext &Context,
                                     ArrayRef<Metadata *> MDs) {
   return MDNodeFwdDecl::get(Context, MDs);