LCOV - code coverage report
Current view: top level - include/llvm/Support - BinaryByteStream.h (source / functions) Hit Total Coverage
Test: llvm-toolchain.info Lines: 50 59 84.7 %
Date: 2017-09-14 15:23:50 Functions: 17 29 58.6 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //===- BinaryByteStream.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             : // A BinaryStream which stores data in a single continguous memory buffer.
       9             : //===----------------------------------------------------------------------===//
      10             : 
      11             : #ifndef LLVM_SUPPORT_BINARYBYTESTREAM_H
      12             : #define LLVM_SUPPORT_BINARYBYTESTREAM_H
      13             : 
      14             : #include "llvm/ADT/ArrayRef.h"
      15             : #include "llvm/ADT/StringRef.h"
      16             : #include "llvm/Support/BinaryStream.h"
      17             : #include "llvm/Support/BinaryStreamError.h"
      18             : #include "llvm/Support/Error.h"
      19             : #include "llvm/Support/FileOutputBuffer.h"
      20             : #include "llvm/Support/MemoryBuffer.h"
      21             : #include <algorithm>
      22             : #include <cstdint>
      23             : #include <cstring>
      24             : #include <memory>
      25             : 
      26             : namespace llvm {
      27             : 
      28             : /// \brief An implementation of BinaryStream which holds its entire data set
      29             : /// in a single contiguous buffer.  BinaryByteStream guarantees that no read
      30             : /// operation will ever incur a copy.  Note that BinaryByteStream does not
      31             : /// own the underlying buffer.
      32       16491 : class BinaryByteStream : public BinaryStream {
      33             : public:
      34         844 :   BinaryByteStream() = default;
      35             :   BinaryByteStream(ArrayRef<uint8_t> Data, llvm::support::endianness Endian)
      36       15482 :       : Endian(Endian), Data(Data) {}
      37             :   BinaryByteStream(StringRef Data, llvm::support::endianness Endian)
      38         452 :       : Endian(Endian), Data(Data.bytes_begin(), Data.bytes_end()) {}
      39             : 
      40       80472 :   llvm::support::endianness getEndian() const override { return Endian; }
      41             : 
      42      114195 :   Error readBytes(uint32_t Offset, uint32_t Size,
      43             :                   ArrayRef<uint8_t> &Buffer) override {
      44      342582 :     if (auto EC = checkOffset(Offset, Size))
      45           6 :       return EC;
      46      228384 :     Buffer = Data.slice(Offset, Size);
      47      342576 :     return Error::success();
      48             :   }
      49             : 
      50       12579 :   Error readLongestContiguousChunk(uint32_t Offset,
      51             :                                    ArrayRef<uint8_t> &Buffer) override {
      52       37737 :     if (auto EC = checkOffset(Offset, 1))
      53           0 :       return EC;
      54       25158 :     Buffer = Data.slice(Offset);
      55       37737 :     return Error::success();
      56             :   }
      57             : 
      58      386199 :   uint32_t getLength() override { return Data.size(); }
      59             : 
      60             :   ArrayRef<uint8_t> data() const { return Data; }
      61             : 
      62             :   StringRef str() const {
      63             :     const char *CharData = reinterpret_cast<const char *>(Data.data());
      64             :     return StringRef(CharData, Data.size());
      65             :   }
      66             : 
      67             : protected:
      68             :   llvm::support::endianness Endian;
      69             :   ArrayRef<uint8_t> Data;
      70             : };
      71             : 
      72             : /// \brief An implementation of BinaryStream whose data is backed by an llvm
      73             : /// MemoryBuffer object.  MemoryBufferByteStream owns the MemoryBuffer in
      74             : /// question.  As with BinaryByteStream, reading from a MemoryBufferByteStream
      75             : /// will never cause a copy.
      76         288 : class MemoryBufferByteStream : public BinaryByteStream {
      77             : public:
      78             :   MemoryBufferByteStream(std::unique_ptr<MemoryBuffer> Buffer,
      79             :                          llvm::support::endianness Endian)
      80          98 :       : BinaryByteStream(Buffer->getBuffer(), Endian),
      81         490 :         MemBuffer(std::move(Buffer)) {}
      82             : 
      83             :   std::unique_ptr<MemoryBuffer> MemBuffer;
      84             : };
      85             : 
      86             : /// \brief An implementation of BinaryStream which holds its entire data set
      87             : /// in a single contiguous buffer.  As with BinaryByteStream, the mutable
      88             : /// version also guarantees that no read operation will ever incur a copy,
      89             : /// and similarly it does not own the underlying buffer.
      90       17943 : class MutableBinaryByteStream : public WritableBinaryStream {
      91             : public:
      92         252 :   MutableBinaryByteStream() = default;
      93             :   MutableBinaryByteStream(MutableArrayRef<uint8_t> Data,
      94             :                           llvm::support::endianness Endian)
      95       17568 :       : Data(Data), ImmutableStream(Data, Endian) {}
      96             : 
      97       31276 :   llvm::support::endianness getEndian() const override {
      98       63052 :     return ImmutableStream.getEndian();
      99             :   }
     100             : 
     101          57 :   Error readBytes(uint32_t Offset, uint32_t Size,
     102             :                   ArrayRef<uint8_t> &Buffer) override {
     103          57 :     return ImmutableStream.readBytes(Offset, Size, Buffer);
     104             :   }
     105             : 
     106          58 :   Error readLongestContiguousChunk(uint32_t Offset,
     107             :                                    ArrayRef<uint8_t> &Buffer) override {
     108          58 :     return ImmutableStream.readLongestContiguousChunk(Offset, Buffer);
     109             :   }
     110             : 
     111      242766 :   uint32_t getLength() override { return ImmutableStream.getLength(); }
     112             : 
     113       57502 :   Error writeBytes(uint32_t Offset, ArrayRef<uint8_t> Buffer) override {
     114       57502 :     if (Buffer.empty())
     115         177 :       return Error::success();
     116             : 
     117      172326 :     if (auto EC = checkOffset(Offset, Buffer.size()))
     118           6 :       return EC;
     119             : 
     120      114880 :     uint8_t *DataPtr = const_cast<uint8_t *>(Data.data());
     121       57440 :     ::memcpy(DataPtr + Offset, Buffer.data(), Buffer.size());
     122      172320 :     return Error::success();
     123             :   }
     124             : 
     125           0 :   Error commit() override { return Error::success(); }
     126             : 
     127             :   MutableArrayRef<uint8_t> data() const { return Data; }
     128             : 
     129             : private:
     130             :   MutableArrayRef<uint8_t> Data;
     131             :   BinaryByteStream ImmutableStream;
     132             : };
     133             : 
     134             : /// \brief An implementation of WritableBinaryStream backed by an llvm
     135             : /// FileOutputBuffer.
     136         180 : class FileBufferByteStream : public WritableBinaryStream {
     137             : private:
     138         120 :   class StreamImpl : public MutableBinaryByteStream {
     139             :   public:
     140          60 :     StreamImpl(std::unique_ptr<FileOutputBuffer> Buffer,
     141             :                llvm::support::endianness Endian)
     142          60 :         : MutableBinaryByteStream(
     143             :               MutableArrayRef<uint8_t>(Buffer->getBufferStart(),
     144             :                                        Buffer->getBufferEnd()),
     145             :               Endian),
     146         420 :           FileBuffer(std::move(Buffer)) {}
     147             : 
     148          60 :     Error commit() override {
     149         120 :       if (FileBuffer->commit())
     150             :         return make_error<BinaryStreamError>(
     151           0 :             stream_error_code::filesystem_error);
     152         180 :       return Error::success();
     153             :     }
     154             : 
     155             :   private:
     156             :     std::unique_ptr<FileOutputBuffer> FileBuffer;
     157             :   };
     158             : 
     159             : public:
     160          60 :   FileBufferByteStream(std::unique_ptr<FileOutputBuffer> Buffer,
     161             :                        llvm::support::endianness Endian)
     162         180 :       : Impl(std::move(Buffer), Endian) {}
     163             : 
     164           0 :   llvm::support::endianness getEndian() const override {
     165           0 :     return Impl.getEndian();
     166             :   }
     167             : 
     168           0 :   Error readBytes(uint32_t Offset, uint32_t Size,
     169             :                   ArrayRef<uint8_t> &Buffer) override {
     170           0 :     return Impl.readBytes(Offset, Size, Buffer);
     171             :   }
     172             : 
     173           0 :   Error readLongestContiguousChunk(uint32_t Offset,
     174             :                                    ArrayRef<uint8_t> &Buffer) override {
     175           0 :     return Impl.readLongestContiguousChunk(Offset, Buffer);
     176             :   }
     177             : 
     178        1154 :   uint32_t getLength() override { return Impl.getLength(); }
     179             : 
     180        6946 :   Error writeBytes(uint32_t Offset, ArrayRef<uint8_t> Data) override {
     181        6946 :     return Impl.writeBytes(Offset, Data);
     182             :   }
     183             : 
     184          60 :   Error commit() override { return Impl.commit(); }
     185             : 
     186             : private:
     187             :   StreamImpl Impl;
     188             : };
     189             : 
     190             : } // end namespace llvm
     191             : 
     192             : #endif // LLVM_SUPPORT_BYTESTREAM_H

Generated by: LCOV version 1.13