Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-05-10 08:43:42

0001 //===-- LVElement.h ---------------------------------------------*- C++ -*-===//
0002 //
0003 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
0004 // See https://llvm.org/LICENSE.txt for license information.
0005 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
0006 //
0007 //===----------------------------------------------------------------------===//
0008 //
0009 // This file defines the LVElement class, which is used to describe a debug
0010 // information element.
0011 //
0012 //===----------------------------------------------------------------------===//
0013 
0014 #ifndef LLVM_DEBUGINFO_LOGICALVIEW_CORE_LVELEMENT_H
0015 #define LLVM_DEBUGINFO_LOGICALVIEW_CORE_LVELEMENT_H
0016 
0017 #include "llvm/DebugInfo/LogicalView/Core/LVObject.h"
0018 #include "llvm/Support/Casting.h"
0019 #include <map>
0020 #include <set>
0021 #include <vector>
0022 
0023 namespace llvm {
0024 namespace logicalview {
0025 
0026 // RTTI Subclasses ID.
0027 enum class LVSubclassID : unsigned char {
0028   LV_ELEMENT,
0029   LV_LINE_FIRST,
0030   LV_LINE,
0031   LV_LINE_DEBUG,
0032   LV_LINE_ASSEMBLER,
0033   LV_LINE_LAST,
0034   lV_SCOPE_FIRST,
0035   LV_SCOPE,
0036   LV_SCOPE_AGGREGATE,
0037   LV_SCOPE_ALIAS,
0038   LV_SCOPE_ARRAY,
0039   LV_SCOPE_COMPILE_UNIT,
0040   LV_SCOPE_ENUMERATION,
0041   LV_SCOPE_FORMAL_PACK,
0042   LV_SCOPE_FUNCTION,
0043   LV_SCOPE_FUNCTION_INLINED,
0044   LV_SCOPE_FUNCTION_TYPE,
0045   LV_SCOPE_NAMESPACE,
0046   LV_SCOPE_ROOT,
0047   LV_SCOPE_TEMPLATE_PACK,
0048   LV_SCOPE_LAST,
0049   LV_SYMBOL_FIRST,
0050   LV_SYMBOL,
0051   LV_SYMBOL_LAST,
0052   LV_TYPE_FIRST,
0053   LV_TYPE,
0054   LV_TYPE_DEFINITION,
0055   LV_TYPE_ENUMERATOR,
0056   LV_TYPE_IMPORT,
0057   LV_TYPE_PARAM,
0058   LV_TYPE_SUBRANGE,
0059   LV_TYPE_LAST
0060 };
0061 
0062 enum class LVElementKind { Discarded, Global, Optimized, LastEntry };
0063 using LVElementKindSet = std::set<LVElementKind>;
0064 using LVElementDispatch = std::map<LVElementKind, LVElementGetFunction>;
0065 using LVElementRequest = std::vector<LVElementGetFunction>;
0066 
0067 class LVElement : public LVObject {
0068   enum class Property {
0069     IsLine,   // A logical line.
0070     IsScope,  // A logical scope.
0071     IsSymbol, // A logical symbol.
0072     IsType,   // A logical type.
0073     IsEnumClass,
0074     IsExternal,
0075     HasType,
0076     HasAugmentedName,
0077     IsTypedefReduced,
0078     IsArrayResolved,
0079     IsMemberPointerResolved,
0080     IsTemplateResolved,
0081     IsInlined,
0082     IsInlinedAbstract,
0083     InvalidFilename,
0084     HasReference,
0085     HasReferenceAbstract,
0086     HasReferenceExtension,
0087     HasReferenceSpecification,
0088     QualifiedResolved,
0089     IncludeInPrint,
0090     IsStatic,
0091     TransformName,
0092     IsScoped,        // CodeView local type.
0093     IsNested,        // CodeView nested type.
0094     IsScopedAlready, // CodeView nested type inserted in correct scope.
0095     IsArtificial,
0096     IsReferencedType,
0097     IsSystem,
0098     OffsetFromTypeIndex,
0099     IsAnonymous,
0100     LastEntry
0101   };
0102   // Typed bitvector with properties for this element.
0103   LVProperties<Property> Properties;
0104   static LVElementDispatch Dispatch;
0105 
0106   /// RTTI.
0107   const LVSubclassID SubclassID;
0108 
0109   // Indexes in the String Pool.
0110   size_t NameIndex = 0;
0111   size_t QualifiedNameIndex = 0;
0112   size_t FilenameIndex = 0;
0113 
0114   uint16_t AccessibilityCode : 2; // DW_AT_accessibility.
0115   uint16_t InlineCode : 2;        // DW_AT_inline.
0116   uint16_t VirtualityCode : 2;    // DW_AT_virtuality.
0117 
0118   // The given Specification points to an element that is connected via the
0119   // DW_AT_specification, DW_AT_abstract_origin or DW_AT_extension attribute.
0120   void setFileLine(LVElement *Specification);
0121 
0122   // Get the qualified name that include its parents name.
0123   void resolveQualifiedName();
0124 
0125 protected:
0126   // Type of this element.
0127   LVElement *ElementType = nullptr;
0128 
0129   // Print the FileName Index.
0130   void printFileIndex(raw_ostream &OS, bool Full = true) const override;
0131 
0132 public:
0133   LVElement(LVSubclassID ID)
0134       : LVObject(), SubclassID(ID), AccessibilityCode(0), InlineCode(0),
0135         VirtualityCode(0) {}
0136   LVElement(const LVElement &) = delete;
0137   LVElement &operator=(const LVElement &) = delete;
0138   virtual ~LVElement() = default;
0139 
0140   LVSubclassID getSubclassID() const { return SubclassID; }
0141 
0142   PROPERTY(Property, IsLine);
0143   PROPERTY(Property, IsScope);
0144   PROPERTY(Property, IsSymbol);
0145   PROPERTY(Property, IsType);
0146   PROPERTY(Property, IsEnumClass);
0147   PROPERTY(Property, IsExternal);
0148   PROPERTY(Property, HasType);
0149   PROPERTY(Property, HasAugmentedName);
0150   PROPERTY(Property, IsTypedefReduced);
0151   PROPERTY(Property, IsArrayResolved);
0152   PROPERTY(Property, IsMemberPointerResolved);
0153   PROPERTY(Property, IsTemplateResolved);
0154   PROPERTY(Property, IsInlined);
0155   PROPERTY(Property, IsInlinedAbstract);
0156   PROPERTY(Property, InvalidFilename);
0157   PROPERTY(Property, HasReference);
0158   PROPERTY(Property, HasReferenceAbstract);
0159   PROPERTY(Property, HasReferenceExtension);
0160   PROPERTY(Property, HasReferenceSpecification);
0161   PROPERTY(Property, QualifiedResolved);
0162   PROPERTY(Property, IncludeInPrint);
0163   PROPERTY(Property, IsStatic);
0164   PROPERTY(Property, TransformName);
0165   PROPERTY(Property, IsScoped);
0166   PROPERTY(Property, IsNested);
0167   PROPERTY(Property, IsScopedAlready);
0168   PROPERTY(Property, IsArtificial);
0169   PROPERTY(Property, IsReferencedType);
0170   PROPERTY(Property, IsSystem);
0171   PROPERTY(Property, OffsetFromTypeIndex);
0172   PROPERTY(Property, IsAnonymous);
0173 
0174   bool isNamed() const override { return NameIndex != 0; }
0175   bool isTyped() const override { return ElementType != nullptr; }
0176   bool isFiled() const override { return FilenameIndex != 0; }
0177 
0178   // The Element class type can point to a Type or Scope.
0179   bool getIsKindType() const { return ElementType && ElementType->getIsType(); }
0180   bool getIsKindScope() const {
0181     return ElementType && ElementType->getIsScope();
0182   }
0183 
0184   StringRef getName() const override {
0185     return getStringPool().getString(NameIndex);
0186   }
0187   void setName(StringRef ElementName) override;
0188 
0189   // Get pathname associated with the Element.
0190   StringRef getPathname() const {
0191     return getStringPool().getString(getFilenameIndex());
0192   }
0193 
0194   // Set filename associated with the Element.
0195   void setFilename(StringRef Filename);
0196 
0197   // Set the Element qualified name.
0198   void setQualifiedName(StringRef Name) {
0199     QualifiedNameIndex = getStringPool().getIndex(Name);
0200   }
0201   StringRef getQualifiedName() const {
0202     return getStringPool().getString(QualifiedNameIndex);
0203   }
0204 
0205   size_t getNameIndex() const { return NameIndex; }
0206   size_t getQualifiedNameIndex() const { return QualifiedNameIndex; }
0207 
0208   void setInnerComponent() { setInnerComponent(getName()); }
0209   void setInnerComponent(StringRef Name);
0210 
0211   // Element type name.
0212   StringRef getTypeName() const;
0213 
0214   virtual StringRef getProducer() const { return StringRef(); }
0215   virtual void setProducer(StringRef ProducerName) {}
0216 
0217   virtual bool isCompileUnit() const { return false; }
0218   virtual bool isRoot() const { return false; }
0219 
0220   virtual void setReference(LVElement *Element) {}
0221   virtual void setReference(LVScope *Scope) {}
0222   virtual void setReference(LVSymbol *Symbol) {}
0223   virtual void setReference(LVType *Type) {}
0224 
0225   virtual void setLinkageName(StringRef LinkageName) {}
0226   virtual StringRef getLinkageName() const { return StringRef(); }
0227   virtual size_t getLinkageNameIndex() const { return 0; }
0228 
0229   virtual uint32_t getCallLineNumber() const { return 0; }
0230   virtual void setCallLineNumber(uint32_t Number) {}
0231   virtual size_t getCallFilenameIndex() const { return 0; }
0232   virtual void setCallFilenameIndex(size_t Index) {}
0233   size_t getFilenameIndex() const { return FilenameIndex; }
0234   void setFilenameIndex(size_t Index) { FilenameIndex = Index; }
0235 
0236   // Set the File location for the Element.
0237   void setFile(LVElement *Reference = nullptr);
0238 
0239   virtual bool isBase() const { return false; }
0240   virtual bool isTemplateParam() const { return false; }
0241 
0242   virtual uint32_t getBitSize() const { return 0; }
0243   virtual void setBitSize(uint32_t Size) {}
0244 
0245   virtual int64_t getCount() const { return 0; }
0246   virtual void setCount(int64_t Value) {}
0247   virtual int64_t getLowerBound() const { return 0; }
0248   virtual void setLowerBound(int64_t Value) {}
0249   virtual int64_t getUpperBound() const { return 0; }
0250   virtual void setUpperBound(int64_t Value) {}
0251   virtual std::pair<unsigned, unsigned> getBounds() const { return {}; }
0252   virtual void setBounds(unsigned Lower, unsigned Upper) {}
0253 
0254   // Access DW_AT_GNU_discriminator attribute.
0255   virtual uint32_t getDiscriminator() const { return 0; }
0256   virtual void setDiscriminator(uint32_t Value) {}
0257 
0258   // Process the values for a DW_TAG_enumerator.
0259   virtual StringRef getValue() const { return {}; }
0260   virtual void setValue(StringRef Value) {}
0261   virtual size_t getValueIndex() const { return 0; }
0262 
0263   // DWARF Accessibility Codes.
0264   uint32_t getAccessibilityCode() const { return AccessibilityCode; }
0265   void setAccessibilityCode(uint32_t Access) { AccessibilityCode = Access; }
0266   StringRef
0267   accessibilityString(uint32_t Access = dwarf::DW_ACCESS_private) const;
0268 
0269   // CodeView Accessibility Codes.
0270   std::optional<uint32_t> getAccessibilityCode(codeview::MemberAccess Access);
0271   void setAccessibilityCode(codeview::MemberAccess Access) {
0272     if (std::optional<uint32_t> Code = getAccessibilityCode(Access))
0273       AccessibilityCode = Code.value();
0274   }
0275 
0276   // DWARF Inline Codes.
0277   uint32_t getInlineCode() const { return InlineCode; }
0278   void setInlineCode(uint32_t Code) { InlineCode = Code; }
0279   StringRef inlineCodeString(uint32_t Code) const;
0280 
0281   // DWARF Virtuality Codes.
0282   uint32_t getVirtualityCode() const { return VirtualityCode; }
0283   void setVirtualityCode(uint32_t Virtuality) { VirtualityCode = Virtuality; }
0284   StringRef
0285   virtualityString(uint32_t Virtuality = dwarf::DW_VIRTUALITY_none) const;
0286 
0287   // CodeView Virtuality Codes.
0288   std::optional<uint32_t> getVirtualityCode(codeview::MethodKind Virtuality);
0289   void setVirtualityCode(codeview::MethodKind Virtuality) {
0290     if (std::optional<uint32_t> Code = getVirtualityCode(Virtuality))
0291       VirtualityCode = Code.value();
0292   }
0293 
0294   // DWARF Extern Codes.
0295   StringRef externalString() const;
0296 
0297   LVElement *getType() const { return ElementType; }
0298   LVType *getTypeAsType() const;
0299   LVScope *getTypeAsScope() const;
0300 
0301   void setType(LVElement *Element = nullptr) {
0302     ElementType = Element;
0303     if (Element) {
0304       setHasType();
0305       Element->setIsReferencedType();
0306     }
0307   }
0308 
0309   // Set the type for the element, handling template parameters.
0310   void setGenericType(LVElement *Element);
0311 
0312   StringRef getTypeQualifiedName() const {
0313     return ElementType ? ElementType->getQualifiedName() : "";
0314   }
0315 
0316   StringRef typeAsString() const;
0317   std::string typeOffsetAsString() const;
0318   std::string discriminatorAsString() const;
0319 
0320   LVScope *traverseParents(LVScopeGetFunction GetFunction) const;
0321 
0322   LVScope *getFunctionParent() const;
0323   virtual LVScope *getCompileUnitParent() const;
0324 
0325   // Print any referenced element.
0326   void printReference(raw_ostream &OS, bool Full, LVElement *Parent) const;
0327 
0328   // Print the linkage name (Symbols and functions).
0329   void printLinkageName(raw_ostream &OS, bool Full, LVElement *Parent,
0330                         LVScope *Scope) const;
0331   void printLinkageName(raw_ostream &OS, bool Full, LVElement *Parent) const;
0332 
0333   // Generate the full name for the Element.
0334   void resolveFullname(LVElement *BaseType, StringRef Name = emptyString());
0335 
0336   // Generate a name for unnamed elements.
0337   void generateName(std::string &Prefix) const;
0338   void generateName();
0339 
0340   virtual bool removeElement(LVElement *Element) { return false; }
0341   virtual void updateLevel(LVScope *Parent, bool Moved = false);
0342 
0343   // During the parsing of the debug information, the logical elements are
0344   // created with information extracted from its description entries (DIE).
0345   // But they are not complete for the logical view concept. A second pass
0346   // is executed in order to collect their additional information.
0347   // The following functions 'resolve' some of their properties, such as
0348   // name, references, parents, extra information based on the element kind.
0349   virtual void resolve();
0350   virtual void resolveExtra() {}
0351   virtual void resolveName();
0352   virtual void resolveReferences() {}
0353   void resolveParents();
0354 
0355   bool referenceMatch(const LVElement *Element) const;
0356 
0357   // Returns true if current element is logically equal to the given 'Element'.
0358   bool equals(const LVElement *Element) const;
0359 
0360   // Report the current element as missing or added during comparison.
0361   virtual void report(LVComparePass Pass) {}
0362 
0363   static LVElementDispatch &getDispatch() { return Dispatch; }
0364 };
0365 
0366 } // end namespace logicalview
0367 } // end namespace llvm
0368 
0369 #endif // LLVM_DEBUGINFO_LOGICALVIEW_CORE_LVELEMENT_H