LLVM API Documentation

DataExtractor.h
Go to the documentation of this file.
00001 //===-- DataExtractor.h -----------------------------------------*- C++ -*-===//
00002 //
00003 //                     The LLVM Compiler Infrastructure
00004 //
00005 // This file is distributed under the University of Illinois Open Source
00006 // License. See LICENSE.TXT for details.
00007 //
00008 //===----------------------------------------------------------------------===//
00009 
00010 #ifndef LLVM_SUPPORT_DATAEXTRACTOR_H
00011 #define LLVM_SUPPORT_DATAEXTRACTOR_H
00012 
00013 #include "llvm/ADT/DenseMap.h"
00014 #include "llvm/ADT/StringRef.h"
00015 #include "llvm/Support/DataTypes.h"
00016 
00017 namespace llvm {
00018 class DataExtractor {
00019   StringRef Data;
00020   uint8_t IsLittleEndian;
00021   uint8_t AddressSize;
00022 public:
00023   /// Construct with a buffer that is owned by the caller.
00024   ///
00025   /// This constructor allows us to use data that is owned by the
00026   /// caller. The data must stay around as long as this object is
00027   /// valid.
00028   DataExtractor(StringRef Data, bool IsLittleEndian, uint8_t AddressSize)
00029     : Data(Data), IsLittleEndian(IsLittleEndian), AddressSize(AddressSize) {}
00030 
00031   /// \brief Get the data pointed to by this extractor.
00032   StringRef getData() const { return Data; }
00033   /// \brief Get the endianess for this extractor.
00034   bool isLittleEndian() const { return IsLittleEndian; }
00035   /// \brief Get the address size for this extractor.
00036   uint8_t getAddressSize() const { return AddressSize; }
00037   /// \brief Set the address size for this extractor.
00038   void setAddressSize(uint8_t Size) { AddressSize = Size; }
00039 
00040   /// Extract a C string from \a *offset_ptr.
00041   ///
00042   /// Returns a pointer to a C String from the data at the offset
00043   /// pointed to by \a offset_ptr. A variable length NULL terminated C
00044   /// string will be extracted and the \a offset_ptr will be
00045   /// updated with the offset of the byte that follows the NULL
00046   /// terminator byte.
00047   ///
00048   /// @param[in,out] offset_ptr
00049   ///     A pointer to an offset within the data that will be advanced
00050   ///     by the appropriate number of bytes if the value is extracted
00051   ///     correctly. If the offset is out of bounds or there are not
00052   ///     enough bytes to extract this value, the offset will be left
00053   ///     unmodified.
00054   ///
00055   /// @return
00056   ///     A pointer to the C string value in the data. If the offset
00057   ///     pointed to by \a offset_ptr is out of bounds, or if the
00058   ///     offset plus the length of the C string is out of bounds,
00059   ///     NULL will be returned.
00060   const char *getCStr(uint32_t *offset_ptr) const;
00061 
00062   /// Extract an unsigned integer of size \a byte_size from \a
00063   /// *offset_ptr.
00064   ///
00065   /// Extract a single unsigned integer value and update the offset
00066   /// pointed to by \a offset_ptr. The size of the extracted integer
00067   /// is specified by the \a byte_size argument. \a byte_size should
00068   /// have a value greater than or equal to one and less than or equal
00069   /// to eight since the return value is 64 bits wide. Any
00070   /// \a byte_size values less than 1 or greater than 8 will result in
00071   /// nothing being extracted, and zero being returned.
00072   ///
00073   /// @param[in,out] offset_ptr
00074   ///     A pointer to an offset within the data that will be advanced
00075   ///     by the appropriate number of bytes if the value is extracted
00076   ///     correctly. If the offset is out of bounds or there are not
00077   ///     enough bytes to extract this value, the offset will be left
00078   ///     unmodified.
00079   ///
00080   /// @param[in] byte_size
00081   ///     The size in byte of the integer to extract.
00082   ///
00083   /// @return
00084   ///     The unsigned integer value that was extracted, or zero on
00085   ///     failure.
00086   uint64_t getUnsigned(uint32_t *offset_ptr, uint32_t byte_size) const;
00087 
00088   /// Extract an signed integer of size \a byte_size from \a *offset_ptr.
00089   ///
00090   /// Extract a single signed integer value (sign extending if required)
00091   /// and update the offset pointed to by \a offset_ptr. The size of
00092   /// the extracted integer is specified by the \a byte_size argument.
00093   /// \a byte_size should have a value greater than or equal to one
00094   /// and less than or equal to eight since the return value is 64
00095   /// bits wide. Any \a byte_size values less than 1 or greater than
00096   /// 8 will result in nothing being extracted, and zero being returned.
00097   ///
00098   /// @param[in,out] offset_ptr
00099   ///     A pointer to an offset within the data that will be advanced
00100   ///     by the appropriate number of bytes if the value is extracted
00101   ///     correctly. If the offset is out of bounds or there are not
00102   ///     enough bytes to extract this value, the offset will be left
00103   ///     unmodified.
00104   ///
00105   /// @param[in] size
00106   ///     The size in bytes of the integer to extract.
00107   ///
00108   /// @return
00109   ///     The sign extended signed integer value that was extracted,
00110   ///     or zero on failure.
00111   int64_t getSigned(uint32_t *offset_ptr, uint32_t size) const;
00112 
00113   //------------------------------------------------------------------
00114   /// Extract an pointer from \a *offset_ptr.
00115   ///
00116   /// Extract a single pointer from the data and update the offset
00117   /// pointed to by \a offset_ptr. The size of the extracted pointer
00118   /// is \a getAddressSize(), so the address size has to be
00119   /// set correctly prior to extracting any pointer values.
00120   ///
00121   /// @param[in,out] offset_ptr
00122   ///     A pointer to an offset within the data that will be advanced
00123   ///     by the appropriate number of bytes if the value is extracted
00124   ///     correctly. If the offset is out of bounds or there are not
00125   ///     enough bytes to extract this value, the offset will be left
00126   ///     unmodified.
00127   ///
00128   /// @return
00129   ///     The extracted pointer value as a 64 integer.
00130   uint64_t getAddress(uint32_t *offset_ptr) const {
00131     return getUnsigned(offset_ptr, AddressSize);
00132   }
00133 
00134   /// Extract a uint8_t value from \a *offset_ptr.
00135   ///
00136   /// Extract a single uint8_t from the binary data at the offset
00137   /// pointed to by \a offset_ptr, and advance the offset on success.
00138   ///
00139   /// @param[in,out] offset_ptr
00140   ///     A pointer to an offset within the data that will be advanced
00141   ///     by the appropriate number of bytes if the value is extracted
00142   ///     correctly. If the offset is out of bounds or there are not
00143   ///     enough bytes to extract this value, the offset will be left
00144   ///     unmodified.
00145   ///
00146   /// @return
00147   ///     The extracted uint8_t value.
00148   uint8_t getU8(uint32_t *offset_ptr) const;
00149 
00150   /// Extract \a count uint8_t values from \a *offset_ptr.
00151   ///
00152   /// Extract \a count uint8_t values from the binary data at the
00153   /// offset pointed to by \a offset_ptr, and advance the offset on
00154   /// success. The extracted values are copied into \a dst.
00155   ///
00156   /// @param[in,out] offset_ptr
00157   ///     A pointer to an offset within the data that will be advanced
00158   ///     by the appropriate number of bytes if the value is extracted
00159   ///     correctly. If the offset is out of bounds or there are not
00160   ///     enough bytes to extract this value, the offset will be left
00161   ///     unmodified.
00162   ///
00163   /// @param[out] dst
00164   ///     A buffer to copy \a count uint8_t values into. \a dst must
00165   ///     be large enough to hold all requested data.
00166   ///
00167   /// @param[in] count
00168   ///     The number of uint8_t values to extract.
00169   ///
00170   /// @return
00171   ///     \a dst if all values were properly extracted and copied,
00172   ///     NULL otherise.
00173   uint8_t *getU8(uint32_t *offset_ptr, uint8_t *dst, uint32_t count) const;
00174 
00175   //------------------------------------------------------------------
00176   /// Extract a uint16_t value from \a *offset_ptr.
00177   ///
00178   /// Extract a single uint16_t from the binary data at the offset
00179   /// pointed to by \a offset_ptr, and update the offset on success.
00180   ///
00181   /// @param[in,out] offset_ptr
00182   ///     A pointer to an offset within the data that will be advanced
00183   ///     by the appropriate number of bytes if the value is extracted
00184   ///     correctly. If the offset is out of bounds or there are not
00185   ///     enough bytes to extract this value, the offset will be left
00186   ///     unmodified.
00187   ///
00188   /// @return
00189   ///     The extracted uint16_t value.
00190   //------------------------------------------------------------------
00191   uint16_t getU16(uint32_t *offset_ptr) const;
00192 
00193   /// Extract \a count uint16_t values from \a *offset_ptr.
00194   ///
00195   /// Extract \a count uint16_t values from the binary data at the
00196   /// offset pointed to by \a offset_ptr, and advance the offset on
00197   /// success. The extracted values are copied into \a dst.
00198   ///
00199   /// @param[in,out] offset_ptr
00200   ///     A pointer to an offset within the data that will be advanced
00201   ///     by the appropriate number of bytes if the value is extracted
00202   ///     correctly. If the offset is out of bounds or there are not
00203   ///     enough bytes to extract this value, the offset will be left
00204   ///     unmodified.
00205   ///
00206   /// @param[out] dst
00207   ///     A buffer to copy \a count uint16_t values into. \a dst must
00208   ///     be large enough to hold all requested data.
00209   ///
00210   /// @param[in] count
00211   ///     The number of uint16_t values to extract.
00212   ///
00213   /// @return
00214   ///     \a dst if all values were properly extracted and copied,
00215   ///     NULL otherise.
00216   uint16_t *getU16(uint32_t *offset_ptr, uint16_t *dst, uint32_t count) const;
00217 
00218   /// Extract a uint32_t value from \a *offset_ptr.
00219   ///
00220   /// Extract a single uint32_t from the binary data at the offset
00221   /// pointed to by \a offset_ptr, and update the offset on success.
00222   ///
00223   /// @param[in,out] offset_ptr
00224   ///     A pointer to an offset within the data that will be advanced
00225   ///     by the appropriate number of bytes if the value is extracted
00226   ///     correctly. If the offset is out of bounds or there are not
00227   ///     enough bytes to extract this value, the offset will be left
00228   ///     unmodified.
00229   ///
00230   /// @return
00231   ///     The extracted uint32_t value.
00232   uint32_t getU32(uint32_t *offset_ptr) const;
00233 
00234   /// Extract \a count uint32_t values from \a *offset_ptr.
00235   ///
00236   /// Extract \a count uint32_t values from the binary data at the
00237   /// offset pointed to by \a offset_ptr, and advance the offset on
00238   /// success. The extracted values are copied into \a dst.
00239   ///
00240   /// @param[in,out] offset_ptr
00241   ///     A pointer to an offset within the data that will be advanced
00242   ///     by the appropriate number of bytes if the value is extracted
00243   ///     correctly. If the offset is out of bounds or there are not
00244   ///     enough bytes to extract this value, the offset will be left
00245   ///     unmodified.
00246   ///
00247   /// @param[out] dst
00248   ///     A buffer to copy \a count uint32_t values into. \a dst must
00249   ///     be large enough to hold all requested data.
00250   ///
00251   /// @param[in] count
00252   ///     The number of uint32_t values to extract.
00253   ///
00254   /// @return
00255   ///     \a dst if all values were properly extracted and copied,
00256   ///     NULL otherise.
00257   uint32_t *getU32(uint32_t *offset_ptr, uint32_t *dst, uint32_t count) const;
00258 
00259   /// Extract a uint64_t value from \a *offset_ptr.
00260   ///
00261   /// Extract a single uint64_t from the binary data at the offset
00262   /// pointed to by \a offset_ptr, and update the offset on success.
00263   ///
00264   /// @param[in,out] offset_ptr
00265   ///     A pointer to an offset within the data that will be advanced
00266   ///     by the appropriate number of bytes if the value is extracted
00267   ///     correctly. If the offset is out of bounds or there are not
00268   ///     enough bytes to extract this value, the offset will be left
00269   ///     unmodified.
00270   ///
00271   /// @return
00272   ///     The extracted uint64_t value.
00273   uint64_t getU64(uint32_t *offset_ptr) const;
00274 
00275   /// Extract \a count uint64_t values from \a *offset_ptr.
00276   ///
00277   /// Extract \a count uint64_t values from the binary data at the
00278   /// offset pointed to by \a offset_ptr, and advance the offset on
00279   /// success. The extracted values are copied into \a dst.
00280   ///
00281   /// @param[in,out] offset_ptr
00282   ///     A pointer to an offset within the data that will be advanced
00283   ///     by the appropriate number of bytes if the value is extracted
00284   ///     correctly. If the offset is out of bounds or there are not
00285   ///     enough bytes to extract this value, the offset will be left
00286   ///     unmodified.
00287   ///
00288   /// @param[out] dst
00289   ///     A buffer to copy \a count uint64_t values into. \a dst must
00290   ///     be large enough to hold all requested data.
00291   ///
00292   /// @param[in] count
00293   ///     The number of uint64_t values to extract.
00294   ///
00295   /// @return
00296   ///     \a dst if all values were properly extracted and copied,
00297   ///     NULL otherise.
00298   uint64_t *getU64(uint32_t *offset_ptr, uint64_t *dst, uint32_t count) const;
00299 
00300   /// Extract a signed LEB128 value from \a *offset_ptr.
00301   ///
00302   /// Extracts an signed LEB128 number from this object's data
00303   /// starting at the offset pointed to by \a offset_ptr. The offset
00304   /// pointed to by \a offset_ptr will be updated with the offset of
00305   /// the byte following the last extracted byte.
00306   ///
00307   /// @param[in,out] offset_ptr
00308   ///     A pointer to an offset within the data that will be advanced
00309   ///     by the appropriate number of bytes if the value is extracted
00310   ///     correctly. If the offset is out of bounds or there are not
00311   ///     enough bytes to extract this value, the offset will be left
00312   ///     unmodified.
00313   ///
00314   /// @return
00315   ///     The extracted signed integer value.
00316   int64_t getSLEB128(uint32_t *offset_ptr) const;
00317 
00318   /// Extract a unsigned LEB128 value from \a *offset_ptr.
00319   ///
00320   /// Extracts an unsigned LEB128 number from this object's data
00321   /// starting at the offset pointed to by \a offset_ptr. The offset
00322   /// pointed to by \a offset_ptr will be updated with the offset of
00323   /// the byte following the last extracted byte.
00324   ///
00325   /// @param[in,out] offset_ptr
00326   ///     A pointer to an offset within the data that will be advanced
00327   ///     by the appropriate number of bytes if the value is extracted
00328   ///     correctly. If the offset is out of bounds or there are not
00329   ///     enough bytes to extract this value, the offset will be left
00330   ///     unmodified.
00331   ///
00332   /// @return
00333   ///     The extracted unsigned integer value.
00334   uint64_t getULEB128(uint32_t *offset_ptr) const;
00335 
00336   /// Test the validity of \a offset.
00337   ///
00338   /// @return
00339   ///     \b true if \a offset is a valid offset into the data in this
00340   ///     object, \b false otherwise.
00341   bool isValidOffset(uint32_t offset) const { return Data.size() > offset; }
00342 
00343   /// Test the availability of \a length bytes of data from \a offset.
00344   ///
00345   /// @return
00346   ///     \b true if \a offset is a valid offset and there are \a
00347   ///     length bytes available at that offset, \b false otherwise.
00348   bool isValidOffsetForDataOfSize(uint32_t offset, uint32_t length) const {
00349     return offset + length >= offset && isValidOffset(offset + length - 1);
00350   }
00351 };
00352 
00353 } // namespace llvm
00354 
00355 #endif