LCOV - code coverage report
Current view: top level - include/llvm/DebugInfo/MSF - SequencedItemStream.h (source / functions) Hit Total Coverage
Test: llvm-toolchain.info Lines: 21 32 65.6 %
Date: 2017-02-25 14:46:56 Functions: 3 6 50.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //===- SequencedItemStream.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_MSF_SEQUENCEDITEMSTREAM_H
      11             : #define LLVM_DEBUGINFO_MSF_SEQUENCEDITEMSTREAM_H
      12             : 
      13             : #include "llvm/ADT/ArrayRef.h"
      14             : #include "llvm/DebugInfo/MSF/MSFError.h"
      15             : #include "llvm/DebugInfo/MSF/StreamInterface.h"
      16             : #include "llvm/Support/Error.h"
      17             : #include <cstddef>
      18             : #include <cstdint>
      19             : 
      20             : namespace llvm {
      21             : namespace msf {
      22             : 
      23             : template <typename T> struct SequencedItemTraits {
      24             :   static size_t length(const T &Item) = delete;
      25             :   static ArrayRef<uint8_t> bytes(const T &Item) = delete;
      26             : };
      27             : 
      28             : /// SequencedItemStream represents a sequence of objects stored in a
      29             : /// standard container but for which it is useful to view as a stream of
      30             : /// contiguous bytes.  An example of this might be if you have a std::vector
      31             : /// of TPI records, where each record contains a byte sequence that
      32             : /// represents that one record serialized, but where each consecutive item
      33             : /// might not be allocated immediately after the previous item.  Using a
      34             : /// SequencedItemStream, we can adapt the VarStreamArray class to trivially
      35             : /// extract one item at a time, allowing the data to be used anywhere a
      36             : /// VarStreamArray could be used.
      37             : template <typename T, typename Traits = SequencedItemTraits<T>>
      38          10 : class SequencedItemStream : public ReadableStream {
      39             : public:
      40          20 :   SequencedItemStream() = default;
      41             : 
      42           0 :   Error readBytes(uint32_t Offset, uint32_t Size,
      43             :                   ArrayRef<uint8_t> &Buffer) const override {
      44           0 :     auto ExpectedIndex = translateOffsetIndex(Offset);
      45           0 :     if (!ExpectedIndex)
      46           0 :       return ExpectedIndex.takeError();
      47           0 :     const auto &Item = Items[*ExpectedIndex];
      48           0 :     if (Size > Traits::length(Item))
      49           0 :       return make_error<MSFError>(msf_error_code::insufficient_buffer);
      50           0 :     Buffer = Traits::bytes(Item).take_front(Size);
      51           0 :     return Error::success();
      52             :   }
      53             : 
      54         201 :   Error readLongestContiguousChunk(uint32_t Offset,
      55             :                                    ArrayRef<uint8_t> &Buffer) const override {
      56         402 :     auto ExpectedIndex = translateOffsetIndex(Offset);
      57         201 :     if (!ExpectedIndex)
      58           0 :       return ExpectedIndex.takeError();
      59         402 :     Buffer = Traits::bytes(Items[*ExpectedIndex]);
      60         603 :     return Error::success();
      61             :   }
      62             : 
      63         201 :   void setItems(ArrayRef<T> ItemArray) { Items = ItemArray; }
      64             : 
      65          10 :   uint32_t getLength() const override {
      66          30 :     uint32_t Size = 0;
      67         663 :     for (const auto &Item : Items)
      68         603 :       Size += Traits::length(Item);
      69          10 :     return Size;
      70             :   }
      71             : 
      72             : private:
      73         201 :   Expected<uint32_t> translateOffsetIndex(uint32_t Offset) const {
      74         201 :     uint32_t CurrentOffset = 0;
      75         201 :     uint32_t CurrentIndex = 0;
      76        6360 :     for (const auto &Item : Items) {
      77        6159 :       if (CurrentOffset >= Offset)
      78             :         break;
      79        5958 :       CurrentOffset += Traits::length(Item);
      80        5958 :       ++CurrentIndex;
      81             :     }
      82         201 :     if (CurrentOffset != Offset)
      83           0 :       return make_error<MSFError>(msf_error_code::insufficient_buffer);
      84             :     return CurrentIndex;
      85             :   }
      86             : 
      87             :   ArrayRef<T> Items;
      88             : };
      89             : 
      90             : } // end namespace msf
      91             : } // end namespace llvm
      92             : 
      93             : #endif // LLVM_DEBUGINFO_MSF_SEQUENCEDITEMSTREAM_H

Generated by: LCOV version 1.13