1 // Copyright 2016 The PDFium Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6 7 #ifndef CORE_FPDFAPI_PARSER_CPDF_STREAM_H_ 8 #define CORE_FPDFAPI_PARSER_CPDF_STREAM_H_ 9 10 #include <stdint.h> 11 12 #include <memory> 13 #include <set> 14 15 #include "core/fpdfapi/parser/cpdf_object.h" 16 #include "core/fxcrt/data_vector.h" 17 #include "core/fxcrt/fx_string_wrappers.h" 18 #include "core/fxcrt/retain_ptr.h" 19 #include "third_party/abseil-cpp/absl/types/variant.h" 20 21 class IFX_SeekableReadStream; 22 23 class CPDF_Stream final : public CPDF_Object { 24 public: 25 static constexpr int kFileBufSize = 512; 26 27 CONSTRUCT_VIA_MAKE_RETAIN; 28 29 // CPDF_Object: 30 Type GetType() const override; 31 RetainPtr<CPDF_Object> Clone() const override; 32 WideString GetUnicodeText() const override; 33 CPDF_Stream* AsMutableStream() override; 34 bool WriteTo(IFX_ArchiveStream* archive, 35 const CPDF_Encryptor* encryptor) const override; 36 37 size_t GetRawSize() const; 38 // Can only be called when stream is memory-based. 39 // This is meant to be used by CPDF_StreamAcc only. 40 // Other callers should use CPDF_StreamAcc to access data in all cases. 41 pdfium::span<const uint8_t> GetInMemoryRawData() const; 42 43 // Copies span or stream into internally-owned buffer. 44 void SetData(pdfium::span<const uint8_t> pData); 45 void SetDataFromStringstream(fxcrt::ostringstream* stream); 46 47 void TakeData(DataVector<uint8_t> data); 48 49 // Set data and remove "Filter" and "DecodeParms" fields from stream 50 // dictionary. Copies span or stream into internally-owned buffer. 51 void SetDataAndRemoveFilter(pdfium::span<const uint8_t> pData); 52 void SetDataFromStringstreamAndRemoveFilter(fxcrt::ostringstream* stream); 53 54 void InitStreamWithEmptyData(RetainPtr<CPDF_Dictionary> pDict); 55 void InitStreamFromFile(RetainPtr<IFX_SeekableReadStream> pFile, 56 RetainPtr<CPDF_Dictionary> pDict); 57 58 // Can only be called when a stream is not memory-based. 59 DataVector<uint8_t> ReadAllRawData() const; 60 IsUninitialized()61 bool IsUninitialized() const { 62 return absl::holds_alternative<absl::monostate>(data_); 63 } IsFileBased()64 bool IsFileBased() const { 65 return absl::holds_alternative<RetainPtr<IFX_SeekableReadStream>>(data_); 66 } IsMemoryBased()67 bool IsMemoryBased() const { 68 return absl::holds_alternative<DataVector<uint8_t>>(data_); 69 } 70 bool HasFilter() const; 71 72 private: 73 friend class CPDF_Dictionary; 74 75 // Uninitialized. 76 CPDF_Stream(); 77 78 // Initializes with empty data. 79 explicit CPDF_Stream(RetainPtr<CPDF_Dictionary> pDict); 80 81 CPDF_Stream(DataVector<uint8_t> pData, RetainPtr<CPDF_Dictionary> pDict); 82 ~CPDF_Stream() override; 83 84 const CPDF_Dictionary* GetDictInternal() const override; 85 RetainPtr<CPDF_Object> CloneNonCyclic( 86 bool bDirect, 87 std::set<const CPDF_Object*>* pVisited) const override; 88 89 void SetLengthInDict(int length); 90 91 absl::variant<absl::monostate, 92 RetainPtr<IFX_SeekableReadStream>, 93 DataVector<uint8_t>> 94 data_; 95 RetainPtr<CPDF_Dictionary> dict_; 96 }; 97 ToStream(CPDF_Object * obj)98inline CPDF_Stream* ToStream(CPDF_Object* obj) { 99 return obj ? obj->AsMutableStream() : nullptr; 100 } 101 ToStream(const CPDF_Object * obj)102inline const CPDF_Stream* ToStream(const CPDF_Object* obj) { 103 return obj ? obj->AsStream() : nullptr; 104 } 105 ToStream(RetainPtr<CPDF_Object> obj)106inline RetainPtr<CPDF_Stream> ToStream(RetainPtr<CPDF_Object> obj) { 107 return RetainPtr<CPDF_Stream>(ToStream(obj.Get())); 108 } 109 ToStream(RetainPtr<const CPDF_Object> obj)110inline RetainPtr<const CPDF_Stream> ToStream(RetainPtr<const CPDF_Object> obj) { 111 return RetainPtr<const CPDF_Stream>(ToStream(obj.Get())); 112 } 113 114 #endif // CORE_FPDFAPI_PARSER_CPDF_STREAM_H_ 115