LCOV - code coverage report
Current view: top level - include/llvm/Support - MemoryBuffer.h (source / functions) Hit Total Coverage
Test: llvm-toolchain.info Lines: 8 13 61.5 %
Date: 2018-09-23 13:06:45 Functions: 0 6 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //===--- MemoryBuffer.h - Memory Buffer Interface ---------------*- 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             : //  This file defines the MemoryBuffer interface.
      11             : //
      12             : //===----------------------------------------------------------------------===//
      13             : 
      14             : #ifndef LLVM_SUPPORT_MEMORYBUFFER_H
      15             : #define LLVM_SUPPORT_MEMORYBUFFER_H
      16             : 
      17             : #include "llvm-c/Types.h"
      18             : #include "llvm/ADT/ArrayRef.h"
      19             : #include "llvm/ADT/StringRef.h"
      20             : #include "llvm/ADT/Twine.h"
      21             : #include "llvm/Support/CBindingWrapping.h"
      22             : #include "llvm/Support/ErrorOr.h"
      23             : #include "llvm/Support/FileSystem.h"
      24             : #include <cstddef>
      25             : #include <cstdint>
      26             : #include <memory>
      27             : 
      28             : namespace llvm {
      29             : 
      30             : class MemoryBufferRef;
      31             : 
      32             : /// This interface provides simple read-only access to a block of memory, and
      33             : /// provides simple methods for reading files and standard input into a memory
      34             : /// buffer.  In addition to basic access to the characters in the file, this
      35             : /// interface guarantees you can read one character past the end of the file,
      36             : /// and that this character will read as '\0'.
      37             : ///
      38             : /// The '\0' guarantee is needed to support an optimization -- it's intended to
      39             : /// be more efficient for clients which are reading all the data to stop
      40             : /// reading when they encounter a '\0' than to continually check the file
      41             : /// position to see if it has reached the end of the file.
      42             : class MemoryBuffer {
      43             :   const char *BufferStart; // Start of the buffer.
      44             :   const char *BufferEnd;   // End of the buffer.
      45             : 
      46             : protected:
      47             :   MemoryBuffer() = default;
      48             : 
      49             :   void init(const char *BufStart, const char *BufEnd,
      50             :             bool RequiresNullTerminator);
      51             : 
      52             :   static constexpr sys::fs::mapped_file_region::mapmode Mapmode =
      53             :       sys::fs::mapped_file_region::readonly;
      54             : 
      55             : public:
      56             :   MemoryBuffer(const MemoryBuffer &) = delete;
      57             :   MemoryBuffer &operator=(const MemoryBuffer &) = delete;
      58             :   virtual ~MemoryBuffer();
      59             : 
      60           0 :   const char *getBufferStart() const { return BufferStart; }
      61           0 :   const char *getBufferEnd() const   { return BufferEnd; }
      62    12500613 :   size_t getBufferSize() const { return BufferEnd-BufferStart; }
      63             : 
      64             :   StringRef getBuffer() const {
      65    20277655 :     return StringRef(BufferStart, getBufferSize());
      66             :   }
      67             : 
      68             :   /// Return an identifier for this buffer, typically the filename it was read
      69             :   /// from.
      70           0 :   virtual StringRef getBufferIdentifier() const { return "Unknown buffer"; }
      71             : 
      72             :   /// Open the specified file as a MemoryBuffer, returning a new MemoryBuffer
      73             :   /// if successful, otherwise returning null. If FileSize is specified, this
      74             :   /// means that the client knows that the file exists and that it has the
      75             :   /// specified size.
      76             :   ///
      77             :   /// \param IsVolatile Set to true to indicate that the contents of the file
      78             :   /// can change outside the user's control, e.g. when libclang tries to parse
      79             :   /// while the user is editing/updating the file or if the file is on an NFS.
      80             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
      81             :   getFile(const Twine &Filename, int64_t FileSize = -1,
      82             :           bool RequiresNullTerminator = true, bool IsVolatile = false);
      83             : 
      84             :   /// Read all of the specified file into a MemoryBuffer as a stream
      85             :   /// (i.e. until EOF reached). This is useful for special files that
      86             :   /// look like a regular file but have 0 size (e.g. /proc/cpuinfo on Linux).
      87             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
      88             :   getFileAsStream(const Twine &Filename);
      89             : 
      90             :   /// Given an already-open file descriptor, map some slice of it into a
      91             :   /// MemoryBuffer. The slice is specified by an \p Offset and \p MapSize.
      92             :   /// Since this is in the middle of a file, the buffer is not null terminated.
      93             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
      94             :   getOpenFileSlice(int FD, const Twine &Filename, uint64_t MapSize,
      95             :                    int64_t Offset, bool IsVolatile = false);
      96             : 
      97             :   /// Given an already-open file descriptor, read the file and return a
      98             :   /// MemoryBuffer.
      99             :   ///
     100             :   /// \param IsVolatile Set to true to indicate that the contents of the file
     101             :   /// can change outside the user's control, e.g. when libclang tries to parse
     102             :   /// while the user is editing/updating the file or if the file is on an NFS.
     103             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
     104             :   getOpenFile(int FD, const Twine &Filename, uint64_t FileSize,
     105             :               bool RequiresNullTerminator = true, bool IsVolatile = false);
     106             : 
     107             :   /// Open the specified memory range as a MemoryBuffer. Note that InputData
     108             :   /// must be null terminated if RequiresNullTerminator is true.
     109             :   static std::unique_ptr<MemoryBuffer>
     110             :   getMemBuffer(StringRef InputData, StringRef BufferName = "",
     111             :                bool RequiresNullTerminator = true);
     112             : 
     113             :   static std::unique_ptr<MemoryBuffer>
     114             :   getMemBuffer(MemoryBufferRef Ref, bool RequiresNullTerminator = true);
     115             : 
     116             :   /// Open the specified memory range as a MemoryBuffer, copying the contents
     117             :   /// and taking ownership of it. InputData does not have to be null terminated.
     118             :   static std::unique_ptr<MemoryBuffer>
     119             :   getMemBufferCopy(StringRef InputData, const Twine &BufferName = "");
     120             : 
     121             :   /// Read all of stdin into a file buffer, and return it.
     122             :   static ErrorOr<std::unique_ptr<MemoryBuffer>> getSTDIN();
     123             : 
     124             :   /// Open the specified file as a MemoryBuffer, or open stdin if the Filename
     125             :   /// is "-".
     126             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
     127             :   getFileOrSTDIN(const Twine &Filename, int64_t FileSize = -1,
     128             :                  bool RequiresNullTerminator = true);
     129             : 
     130             :   /// Map a subrange of the specified file as a MemoryBuffer.
     131             :   static ErrorOr<std::unique_ptr<MemoryBuffer>>
     132             :   getFileSlice(const Twine &Filename, uint64_t MapSize, uint64_t Offset,
     133             :                bool IsVolatile = false);
     134             : 
     135             :   //===--------------------------------------------------------------------===//
     136             :   // Provided for performance analysis.
     137             :   //===--------------------------------------------------------------------===//
     138             : 
     139             :   /// The kind of memory backing used to support the MemoryBuffer.
     140             :   enum BufferKind {
     141             :     MemoryBuffer_Malloc,
     142             :     MemoryBuffer_MMap
     143             :   };
     144             : 
     145             :   /// Return information on the memory mechanism used to support the
     146             :   /// MemoryBuffer.
     147             :   virtual BufferKind getBufferKind() const = 0;
     148             : 
     149             :   MemoryBufferRef getMemBufferRef() const;
     150             : };
     151             : 
     152             : /// This class is an extension of MemoryBuffer, which allows copy-on-write
     153             : /// access to the underlying contents.  It only supports creation methods that
     154             : /// are guaranteed to produce a writable buffer.  For example, mapping a file
     155             : /// read-only is not supported.
     156             : class WritableMemoryBuffer : public MemoryBuffer {
     157             : protected:
     158             :   WritableMemoryBuffer() = default;
     159             : 
     160             :   static constexpr sys::fs::mapped_file_region::mapmode Mapmode =
     161             :       sys::fs::mapped_file_region::priv;
     162             : 
     163             : public:
     164             :   using MemoryBuffer::getBuffer;
     165             :   using MemoryBuffer::getBufferEnd;
     166             :   using MemoryBuffer::getBufferStart;
     167             : 
     168             :   // const_cast is well-defined here, because the underlying buffer is
     169             :   // guaranteed to have been initialized with a mutable buffer.
     170             :   char *getBufferStart() {
     171     1545625 :     return const_cast<char *>(MemoryBuffer::getBufferStart());
     172             :   }
     173             :   char *getBufferEnd() {
     174             :     return const_cast<char *>(MemoryBuffer::getBufferEnd());
     175             :   }
     176             :   MutableArrayRef<char> getBuffer() {
     177             :     return {getBufferStart(), getBufferEnd()};
     178             :   }
     179             : 
     180             :   static ErrorOr<std::unique_ptr<WritableMemoryBuffer>>
     181             :   getFile(const Twine &Filename, int64_t FileSize = -1,
     182             :           bool IsVolatile = false);
     183             : 
     184             :   /// Map a subrange of the specified file as a WritableMemoryBuffer.
     185             :   static ErrorOr<std::unique_ptr<WritableMemoryBuffer>>
     186             :   getFileSlice(const Twine &Filename, uint64_t MapSize, uint64_t Offset,
     187             :                bool IsVolatile = false);
     188             : 
     189             :   /// Allocate a new MemoryBuffer of the specified size that is not initialized.
     190             :   /// Note that the caller should initialize the memory allocated by this
     191             :   /// method. The memory is owned by the MemoryBuffer object.
     192             :   static std::unique_ptr<WritableMemoryBuffer>
     193             :   getNewUninitMemBuffer(size_t Size, const Twine &BufferName = "");
     194             : 
     195             :   /// Allocate a new zero-initialized MemoryBuffer of the specified size. Note
     196             :   /// that the caller need not initialize the memory allocated by this method.
     197             :   /// The memory is owned by the MemoryBuffer object.
     198             :   static std::unique_ptr<WritableMemoryBuffer>
     199             :   getNewMemBuffer(size_t Size, const Twine &BufferName = "");
     200             : 
     201             : private:
     202             :   // Hide these base class factory function so one can't write
     203             :   //   WritableMemoryBuffer::getXXX()
     204             :   // and be surprised that he got a read-only Buffer.
     205             :   using MemoryBuffer::getFileAsStream;
     206             :   using MemoryBuffer::getFileOrSTDIN;
     207             :   using MemoryBuffer::getMemBuffer;
     208             :   using MemoryBuffer::getMemBufferCopy;
     209             :   using MemoryBuffer::getOpenFile;
     210             :   using MemoryBuffer::getOpenFileSlice;
     211             :   using MemoryBuffer::getSTDIN;
     212             : };
     213             : 
     214             : /// This class is an extension of MemoryBuffer, which allows write access to
     215             : /// the underlying contents and committing those changes to the original source.
     216             : /// It only supports creation methods that are guaranteed to produce a writable
     217             : /// buffer.  For example, mapping a file read-only is not supported.
     218             : class WriteThroughMemoryBuffer : public MemoryBuffer {
     219             : protected:
     220             :   WriteThroughMemoryBuffer() = default;
     221             : 
     222             :   static constexpr sys::fs::mapped_file_region::mapmode Mapmode =
     223             :       sys::fs::mapped_file_region::readwrite;
     224             : 
     225             : public:
     226             :   using MemoryBuffer::getBuffer;
     227             :   using MemoryBuffer::getBufferEnd;
     228             :   using MemoryBuffer::getBufferStart;
     229             : 
     230             :   // const_cast is well-defined here, because the underlying buffer is
     231             :   // guaranteed to have been initialized with a mutable buffer.
     232             :   char *getBufferStart() {
     233           1 :     return const_cast<char *>(MemoryBuffer::getBufferStart());
     234             :   }
     235             :   char *getBufferEnd() {
     236             :     return const_cast<char *>(MemoryBuffer::getBufferEnd());
     237             :   }
     238             :   MutableArrayRef<char> getBuffer() {
     239             :     return {getBufferStart(), getBufferEnd()};
     240             :   }
     241             : 
     242             :   static ErrorOr<std::unique_ptr<WriteThroughMemoryBuffer>>
     243             :   getFile(const Twine &Filename, int64_t FileSize = -1);
     244             : 
     245             :   /// Map a subrange of the specified file as a ReadWriteMemoryBuffer.
     246             :   static ErrorOr<std::unique_ptr<WriteThroughMemoryBuffer>>
     247             :   getFileSlice(const Twine &Filename, uint64_t MapSize, uint64_t Offset);
     248             : 
     249             : private:
     250             :   // Hide these base class factory function so one can't write
     251             :   //   WritableMemoryBuffer::getXXX()
     252             :   // and be surprised that he got a read-only Buffer.
     253             :   using MemoryBuffer::getFileAsStream;
     254             :   using MemoryBuffer::getFileOrSTDIN;
     255             :   using MemoryBuffer::getMemBuffer;
     256             :   using MemoryBuffer::getMemBufferCopy;
     257             :   using MemoryBuffer::getOpenFile;
     258             :   using MemoryBuffer::getOpenFileSlice;
     259             :   using MemoryBuffer::getSTDIN;
     260             : };
     261             : 
     262             : class MemoryBufferRef {
     263             :   StringRef Buffer;
     264             :   StringRef Identifier;
     265             : 
     266             : public:
     267             :   MemoryBufferRef() = default;
     268             :   MemoryBufferRef(MemoryBuffer& Buffer)
     269       19935 :       : Buffer(Buffer.getBuffer()), Identifier(Buffer.getBufferIdentifier()) {}
     270             :   MemoryBufferRef(StringRef Buffer, StringRef Identifier)
     271       58039 :       : Buffer(Buffer), Identifier(Identifier) {}
     272             : 
     273           0 :   StringRef getBuffer() const { return Buffer; }
     274             : 
     275           0 :   StringRef getBufferIdentifier() const { return Identifier; }
     276             : 
     277      215213 :   const char *getBufferStart() const { return Buffer.begin(); }
     278       37510 :   const char *getBufferEnd() const { return Buffer.end(); }
     279             :   size_t getBufferSize() const { return Buffer.size(); }
     280             : };
     281             : 
     282             : // Create wrappers for C Binding types (see CBindingWrapping.h).
     283             : DEFINE_SIMPLE_CONVERSION_FUNCTIONS(MemoryBuffer, LLVMMemoryBufferRef)
     284             : 
     285             : } // end namespace llvm
     286             : 
     287             : #endif // LLVM_SUPPORT_MEMORYBUFFER_H

Generated by: LCOV version 1.13