diff options
Diffstat (limited to 'include/llvm/IR/Metadata.h')
| -rw-r--r-- | include/llvm/IR/Metadata.h | 115 |
1 files changed, 96 insertions, 19 deletions
diff --git a/include/llvm/IR/Metadata.h b/include/llvm/IR/Metadata.h index c639625bf16c..2ea591383f82 100644 --- a/include/llvm/IR/Metadata.h +++ b/include/llvm/IR/Metadata.h @@ -18,10 +18,11 @@ #include "llvm/ADT/ArrayRef.h" #include "llvm/ADT/DenseMap.h" +#include "llvm/ADT/PointerUnion.h" #include "llvm/ADT/ilist_node.h" #include "llvm/ADT/iterator_range.h" #include "llvm/IR/Constant.h" -#include "llvm/IR/MetadataTracking.h" +#include "llvm/IR/LLVMContext.h" #include "llvm/IR/Value.h" #include "llvm/Support/ErrorHandling.h" #include <type_traits> @@ -32,9 +33,6 @@ class LLVMContext; class Module; class ModuleSlotTracker; -template<typename ValueSubClass, typename ItemParentClass> - class SymbolTableListTraits; - enum LLVMConstants : uint32_t { DEBUG_METADATA_VERSION = 3 // Current debug info version number. }; @@ -86,7 +84,9 @@ public: DIImportedEntityKind, ConstantAsMetadataKind, LocalAsMetadataKind, - MDStringKind + MDStringKind, + DIMacroKind, + DIMacroFileKind }; protected: @@ -126,9 +126,10 @@ public: /// If \c M is provided, metadata nodes will be numbered canonically; /// otherwise, pointer addresses are substituted. /// @{ - void print(raw_ostream &OS, const Module *M = nullptr) const; - void print(raw_ostream &OS, ModuleSlotTracker &MST, - const Module *M = nullptr) const; + void print(raw_ostream &OS, const Module *M = nullptr, + bool IsForDebug = false) const; + void print(raw_ostream &OS, ModuleSlotTracker &MST, const Module *M = nullptr, + bool IsForDebug = false) const; /// @} /// \brief Print as operand. @@ -196,6 +197,77 @@ private: void untrack(); }; +/// \brief API for tracking metadata references through RAUW and deletion. +/// +/// Shared API for updating \a Metadata pointers in subclasses that support +/// RAUW. +/// +/// This API is not meant to be used directly. See \a TrackingMDRef for a +/// user-friendly tracking reference. +class MetadataTracking { +public: + /// \brief Track the reference to metadata. + /// + /// Register \c MD with \c *MD, if the subclass supports tracking. If \c *MD + /// gets RAUW'ed, \c MD will be updated to the new address. If \c *MD gets + /// deleted, \c MD will be set to \c nullptr. + /// + /// If tracking isn't supported, \c *MD will not change. + /// + /// \return true iff tracking is supported by \c MD. + static bool track(Metadata *&MD) { + return track(&MD, *MD, static_cast<Metadata *>(nullptr)); + } + + /// \brief Track the reference to metadata for \a Metadata. + /// + /// As \a track(Metadata*&), but with support for calling back to \c Owner to + /// tell it that its operand changed. This could trigger \c Owner being + /// re-uniqued. + static bool track(void *Ref, Metadata &MD, Metadata &Owner) { + return track(Ref, MD, &Owner); + } + + /// \brief Track the reference to metadata for \a MetadataAsValue. + /// + /// As \a track(Metadata*&), but with support for calling back to \c Owner to + /// tell it that its operand changed. This could trigger \c Owner being + /// re-uniqued. + static bool track(void *Ref, Metadata &MD, MetadataAsValue &Owner) { + return track(Ref, MD, &Owner); + } + + /// \brief Stop tracking a reference to metadata. + /// + /// Stops \c *MD from tracking \c MD. + static void untrack(Metadata *&MD) { untrack(&MD, *MD); } + static void untrack(void *Ref, Metadata &MD); + + /// \brief Move tracking from one reference to another. + /// + /// Semantically equivalent to \c untrack(MD) followed by \c track(New), + /// except that ownership callbacks are maintained. + /// + /// Note: it is an error if \c *MD does not equal \c New. + /// + /// \return true iff tracking is supported by \c MD. + static bool retrack(Metadata *&MD, Metadata *&New) { + return retrack(&MD, *MD, &New); + } + static bool retrack(void *Ref, Metadata &MD, void *New); + + /// \brief Check whether metadata is replaceable. + static bool isReplaceable(const Metadata &MD); + + typedef PointerUnion<MetadataAsValue *, Metadata *> OwnerTy; + +private: + /// \brief Track a reference to metadata for an owner. + /// + /// Generalized version of tracking. + static bool track(void *Ref, Metadata &MD, OwnerTy Owner); +}; + /// \brief Shared implementation of use-lists for replaceable metadata. /// /// Most metadata cannot be RAUW'ed. This is a shared implementation of @@ -572,10 +644,12 @@ struct AAMDNodes { template<> struct DenseMapInfo<AAMDNodes> { static inline AAMDNodes getEmptyKey() { - return AAMDNodes(DenseMapInfo<MDNode *>::getEmptyKey(), 0, 0); + return AAMDNodes(DenseMapInfo<MDNode *>::getEmptyKey(), + nullptr, nullptr); } static inline AAMDNodes getTombstoneKey() { - return AAMDNodes(DenseMapInfo<MDNode *>::getTombstoneKey(), 0, 0); + return AAMDNodes(DenseMapInfo<MDNode *>::getTombstoneKey(), + nullptr, nullptr); } static unsigned getHashValue(const AAMDNodes &Val) { return DenseMapInfo<MDNode *>::getHashValue(Val.TBAA) ^ @@ -830,10 +904,11 @@ public: /// \brief Resolve cycles. /// /// Once all forward declarations have been resolved, force cycles to be - /// resolved. + /// resolved. If \p MDMaterialized is true, then any temporary metadata + /// is ignored, otherwise it asserts when encountering temporary metadata. /// /// \pre No operands (or operands' operands, etc.) have \a isTemporary(). - void resolveCycles(); + void resolveCycles(bool MDMaterialized = true); /// \brief Replace a temporary node with a permanent one. /// @@ -881,6 +956,7 @@ protected: void storeDistinctInContext(); template <class T, class StoreT> static T *storeImpl(T *N, StorageType Storage, StoreT &Store); + template <class T> static T *storeImpl(T *N, StorageType Storage); private: void handleChangedOperand(void *Ref, Metadata *New); @@ -913,13 +989,13 @@ private: N->recalculateHash(); } template <class NodeTy> - static void dispatchRecalculateHash(NodeTy *N, std::false_type) {} + static void dispatchRecalculateHash(NodeTy *, std::false_type) {} template <class NodeTy> static void dispatchResetHash(NodeTy *N, std::true_type) { N->setHash(0); } template <class NodeTy> - static void dispatchResetHash(NodeTy *N, std::false_type) {} + static void dispatchResetHash(NodeTy *, std::false_type) {} public: typedef const MDOperand *op_iterator; @@ -963,6 +1039,8 @@ public: static MDNode *getMostGenericFPMath(MDNode *A, MDNode *B); static MDNode *getMostGenericRange(MDNode *A, MDNode *B); static MDNode *getMostGenericAliasScope(MDNode *A, MDNode *B); + static MDNode *getMostGenericAlignmentOrDereferenceable(MDNode *A, MDNode *B); + }; /// \brief Tuple of metadata. @@ -1125,7 +1203,6 @@ public: /// /// TODO: Inherit from Metadata. class NamedMDNode : public ilist_node<NamedMDNode> { - friend class SymbolTableListTraits<NamedMDNode, Module>; friend struct ilist_traits<NamedMDNode>; friend class LLVMContextImpl; friend class Module; @@ -1193,7 +1270,7 @@ public: void addOperand(MDNode *M); void setOperand(unsigned I, MDNode *New); StringRef getName() const; - void print(raw_ostream &ROS) const; + void print(raw_ostream &ROS, bool IsForDebug = false) const; void dump() const; // --------------------------------------------------------------------------- @@ -1208,13 +1285,13 @@ public: const_op_iterator op_end() const { return const_op_iterator(this, getNumOperands()); } inline iterator_range<op_iterator> operands() { - return iterator_range<op_iterator>(op_begin(), op_end()); + return make_range(op_begin(), op_end()); } inline iterator_range<const_op_iterator> operands() const { - return iterator_range<const_op_iterator>(op_begin(), op_end()); + return make_range(op_begin(), op_end()); } }; } // end llvm namespace -#endif +#endif // LLVM_IR_METADATA_H |
