Home | History | Annotate | Download | only in DWARF
      1 //===- DWARFFormValue.h -----------------------------------------*- C++ -*-===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 
     10 #ifndef LLVM_DEBUGINFO_DWARFFORMVALUE_H
     11 #define LLVM_DEBUGINFO_DWARFFORMVALUE_H
     12 
     13 #include "llvm/ADT/ArrayRef.h"
     14 #include "llvm/ADT/None.h"
     15 #include "llvm/ADT/Optional.h"
     16 #include "llvm/Support/DataExtractor.h"
     17 #include "llvm/Support/Dwarf.h"
     18 #include <cstdint>
     19 
     20 namespace llvm {
     21 
     22 class DWARFUnit;
     23 class raw_ostream;
     24 
     25 class DWARFFormValue {
     26 public:
     27   enum FormClass {
     28     FC_Unknown,
     29     FC_Address,
     30     FC_Block,
     31     FC_Constant,
     32     FC_String,
     33     FC_Flag,
     34     FC_Reference,
     35     FC_Indirect,
     36     FC_SectionOffset,
     37     FC_Exprloc
     38   };
     39 
     40 private:
     41   struct ValueType {
     42     ValueType() {
     43       uval = 0;
     44     }
     45 
     46     union {
     47       uint64_t uval;
     48       int64_t sval;
     49       const char* cstr;
     50     };
     51     const uint8_t* data = nullptr;
     52   };
     53 
     54   dwarf::Form Form; // Form for this value.
     55   ValueType Value; // Contains all data for the form.
     56   const DWARFUnit *U = nullptr; // Remember the DWARFUnit at extract time.
     57 
     58 public:
     59   DWARFFormValue(dwarf::Form F = dwarf::Form(0)) : Form(F) {}
     60 
     61   dwarf::Form getForm() const { return Form; }
     62   void setForm(dwarf::Form F) { Form = F; }
     63   void setUValue(uint64_t V) { Value.uval = V; }
     64   void setSValue(int64_t V) { Value.sval = V; }
     65   void setPValue(const char *V) { Value.cstr = V; }
     66 
     67   void setBlockValue(const ArrayRef<uint8_t> &Data) {
     68     Value.data = Data.data();
     69     setUValue(Data.size());
     70   }
     71 
     72   bool isFormClass(FormClass FC) const;
     73   const DWARFUnit *getUnit() const { return U; }
     74   void dump(raw_ostream &OS) const;
     75 
     76   /// \brief extracts a value in data at offset *offset_ptr.
     77   ///
     78   /// The passed DWARFUnit is allowed to be nullptr, in which
     79   /// case no relocation processing will be performed and some
     80   /// kind of forms that depend on Unit information are disallowed.
     81   /// \returns whether the extraction succeeded.
     82   bool extractValue(const DataExtractor &Data, uint32_t *OffsetPtr,
     83                     const DWARFUnit *U);
     84 
     85   bool isInlinedCStr() const {
     86     return Value.data != nullptr && Value.data == (const uint8_t*)Value.cstr;
     87   }
     88 
     89   /// getAsFoo functions below return the extracted value as Foo if only
     90   /// DWARFFormValue has form class is suitable for representing Foo.
     91   Optional<uint64_t> getAsReference() const;
     92   Optional<uint64_t> getAsUnsignedConstant() const;
     93   Optional<int64_t> getAsSignedConstant() const;
     94   Optional<const char *> getAsCString() const;
     95   Optional<uint64_t> getAsAddress() const;
     96   Optional<uint64_t> getAsSectionOffset() const;
     97   Optional<ArrayRef<uint8_t>> getAsBlock() const;
     98   Optional<uint64_t> getAsCStringOffset() const;
     99   Optional<uint64_t> getAsReferenceUVal() const;
    100 
    101   /// Get the fixed byte size for a given form.
    102   ///
    103   /// If the form always has a fixed valid byte size that doesn't depend on a
    104   /// DWARFUnit, then an Optional with a value will be returned. If the form
    105   /// can vary in size depending on the DWARFUnit (DWARF version, address byte
    106   /// size, or DWARF 32/64) and the DWARFUnit is valid, then an Optional with a
    107   /// valid value is returned. If the form is always encoded using a variable
    108   /// length storage format (ULEB or SLEB numbers or blocks) or the size
    109   /// depends on a DWARFUnit and the DWARFUnit is NULL, then None will be
    110   /// returned.
    111   /// \param Form The DWARF form to get the fixed byte size for
    112   /// \param U The DWARFUnit that can be used to help determine the byte size.
    113   ///
    114   /// \returns Optional<uint8_t> value with the fixed byte size or None if
    115   /// \p Form doesn't have a fixed byte size or a DWARFUnit wasn't supplied
    116   /// and was needed to calculate the byte size.
    117   static Optional<uint8_t> getFixedByteSize(dwarf::Form Form,
    118                                             const DWARFUnit *U = nullptr);
    119 
    120   /// Get the fixed byte size for a given form.
    121   ///
    122   /// If the form has a fixed byte size given a valid DWARF version and address
    123   /// byte size, then an Optional with a valid value is returned. If the form
    124   /// is always encoded using a variable length storage format (ULEB or SLEB
    125   /// numbers or blocks) then None will be returned.
    126   ///
    127   /// \param Form DWARF form to get the fixed byte size for
    128   /// \param Version DWARF version number.
    129   /// \param AddrSize size of an address in bytes.
    130   /// \param Format enum value from llvm::dwarf::DwarfFormat.
    131   /// \returns Optional<uint8_t> value with the fixed byte size or None if
    132   /// \p Form doesn't have a fixed byte size.
    133   static Optional<uint8_t> getFixedByteSize(dwarf::Form Form, uint16_t Version,
    134                                             uint8_t AddrSize,
    135                                             llvm::dwarf::DwarfFormat Format);
    136 
    137   /// Skip a form in \p debug_info_data at offset specified by \p offset_ptr.
    138   ///
    139   /// Skips the bytes for this form in the debug info and updates the offset.
    140   ///
    141   /// \param debug_info_data the .debug_info data to use to skip the value.
    142   /// \param offset_ptr a reference to the offset that will be updated.
    143   /// \param U the DWARFUnit to use when skipping the form in case the form
    144   /// size differs according to data in the DWARFUnit.
    145   /// \returns true on success, false if the form was not skipped.
    146   bool skipValue(DataExtractor debug_info_data, uint32_t *offset_ptr,
    147                  const DWARFUnit *U) const;
    148 
    149   /// Skip a form in \p debug_info_data at offset specified by \p offset_ptr.
    150   ///
    151   /// Skips the bytes for this form in the debug info and updates the offset.
    152   ///
    153   /// \param form the DW_FORM enumeration that indicates the form to skip.
    154   /// \param debug_info_data the .debug_info data to use to skip the value.
    155   /// \param offset_ptr a reference to the offset that will be updated.
    156   /// \param U the DWARFUnit to use when skipping the form in case the form
    157   /// size differs according to data in the DWARFUnit.
    158   /// \returns true on success, false if the form was not skipped.
    159   static bool skipValue(dwarf::Form form, DataExtractor debug_info_data,
    160                         uint32_t *offset_ptr, const DWARFUnit *U);
    161 
    162   /// Skip a form in \p debug_info_data at offset specified by \p offset_ptr.
    163   ///
    164   /// Skips the bytes for this form in the debug info and updates the offset.
    165   ///
    166   /// \param form the DW_FORM enumeration that indicates the form to skip.
    167   /// \param debug_info_data the .debug_info data to use to skip the value.
    168   /// \param offset_ptr a reference to the offset that will be updated.
    169   /// \param Version DWARF version number.
    170   /// \param AddrSize size of an address in bytes.
    171   /// \param Format enum value from llvm::dwarf::DwarfFormat.
    172   /// \returns true on success, false if the form was not skipped.
    173   static bool skipValue(dwarf::Form form, DataExtractor debug_info_data,
    174                         uint32_t *offset_ptr, uint16_t Version,
    175                         uint8_t AddrSize, llvm::dwarf::DwarfFormat Format);
    176 
    177 private:
    178   void dumpString(raw_ostream &OS) const;
    179 };
    180 
    181 namespace dwarf {
    182 
    183   /// Take an optional DWARFFormValue and try to extract a string value from it.
    184   ///
    185   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    186   /// \returns an optional value that contains a value if the form value
    187   /// was valid and was a string.
    188   inline Optional<const char*> toString(const Optional<DWARFFormValue>& V) {
    189     if (V)
    190       return V->getAsCString();
    191     return None;
    192   }
    193 
    194   /// Take an optional DWARFFormValue and extract a string value from it.
    195   ///
    196   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    197   /// \param Default the default value to return in case of failure.
    198   /// \returns the string value or Default if the V doesn't have a value or the
    199   /// form value's encoding wasn't a string.
    200   inline const char*
    201   toString(const Optional<DWARFFormValue>& V, const char *Default) {
    202     return toString(V).getValueOr(Default);
    203   }
    204 
    205   /// Take an optional DWARFFormValue and try to extract an unsigned constant.
    206   ///
    207   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    208   /// \returns an optional value that contains a value if the form value
    209   /// was valid and has a unsigned constant form.
    210   inline Optional<uint64_t> toUnsigned(const Optional<DWARFFormValue>& V) {
    211     if (V)
    212       return V->getAsUnsignedConstant();
    213     return None;
    214   }
    215 
    216   /// Take an optional DWARFFormValue and extract a unsigned constant.
    217   ///
    218   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    219   /// \param Default the default value to return in case of failure.
    220   /// \returns the extracted unsigned value or Default if the V doesn't have a
    221   /// value or the form value's encoding wasn't an unsigned constant form.
    222   inline uint64_t
    223   toUnsigned(const Optional<DWARFFormValue>& V, uint64_t Default) {
    224     return toUnsigned(V).getValueOr(Default);
    225   }
    226 
    227   /// Take an optional DWARFFormValue and try to extract an reference.
    228   ///
    229   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    230   /// \returns an optional value that contains a value if the form value
    231   /// was valid and has a reference form.
    232   inline Optional<uint64_t> toReference(const Optional<DWARFFormValue>& V) {
    233     if (V)
    234       return V->getAsReference();
    235     return None;
    236   }
    237 
    238   /// Take an optional DWARFFormValue and extract a reference.
    239   ///
    240   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    241   /// \param Default the default value to return in case of failure.
    242   /// \returns the extracted reference value or Default if the V doesn't have a
    243   /// value or the form value's encoding wasn't a reference form.
    244   inline uint64_t
    245   toReference(const Optional<DWARFFormValue>& V, uint64_t Default) {
    246     return toReference(V).getValueOr(Default);
    247   }
    248 
    249   /// Take an optional DWARFFormValue and try to extract an signed constant.
    250   ///
    251   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    252   /// \returns an optional value that contains a value if the form value
    253   /// was valid and has a signed constant form.
    254   inline Optional<int64_t> toSigned(const Optional<DWARFFormValue>& V) {
    255     if (V)
    256       return V->getAsSignedConstant();
    257     return None;
    258   }
    259 
    260   /// Take an optional DWARFFormValue and extract a signed integer.
    261   ///
    262   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    263   /// \param Default the default value to return in case of failure.
    264   /// \returns the extracted signed integer value or Default if the V doesn't
    265   /// have a value or the form value's encoding wasn't a signed integer form.
    266   inline int64_t
    267   toSigned(const Optional<DWARFFormValue>& V, int64_t Default) {
    268     return toSigned(V).getValueOr(Default);
    269   }
    270 
    271   /// Take an optional DWARFFormValue and try to extract an address.
    272   ///
    273   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    274   /// \returns an optional value that contains a value if the form value
    275   /// was valid and has a address form.
    276   inline Optional<uint64_t> toAddress(const Optional<DWARFFormValue>& V) {
    277     if (V)
    278       return V->getAsAddress();
    279     return None;
    280   }
    281 
    282   /// Take an optional DWARFFormValue and extract a address.
    283   ///
    284   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    285   /// \param Default the default value to return in case of failure.
    286   /// \returns the extracted address value or Default if the V doesn't have a
    287   /// value or the form value's encoding wasn't an address form.
    288   inline uint64_t
    289   toAddress(const Optional<DWARFFormValue>& V, uint64_t Default) {
    290     return toAddress(V).getValueOr(Default);
    291   }
    292 
    293   /// Take an optional DWARFFormValue and try to extract an section offset.
    294   ///
    295   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    296   /// \returns an optional value that contains a value if the form value
    297   /// was valid and has a section offset form.
    298   inline Optional<uint64_t> toSectionOffset(const Optional<DWARFFormValue>& V) {
    299     if (V)
    300       return V->getAsSectionOffset();
    301     return None;
    302   }
    303 
    304   /// Take an optional DWARFFormValue and extract a section offset.
    305   ///
    306   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    307   /// \param Default the default value to return in case of failure.
    308   /// \returns the extracted section offset value or Default if the V doesn't
    309   /// have a value or the form value's encoding wasn't a section offset form.
    310   inline uint64_t
    311   toSectionOffset(const Optional<DWARFFormValue>& V, uint64_t Default) {
    312     return toSectionOffset(V).getValueOr(Default);
    313   }
    314 
    315   /// Take an optional DWARFFormValue and try to extract block data.
    316   ///
    317   /// \param V and optional DWARFFormValue to attempt to extract the value from.
    318   /// \returns an optional value that contains a value if the form value
    319   /// was valid and has a block form.
    320   inline Optional<ArrayRef<uint8_t>>
    321   toBlock(const Optional<DWARFFormValue>& V) {
    322     if (V)
    323       return V->getAsBlock();
    324     return None;
    325   }
    326 
    327 } // end namespace dwarf
    328 
    329 } // end namespace llvm
    330 
    331 #endif // LLVM_DEBUGINFO_DWARFFORMVALUE_H
    332