// // PartialStream.h // // Library: Zip // Package: Zip // Module: PartialStream // // Definition of the PartialStream class. // // Copyright (c) 2007, Applied Informatics Software Engineering GmbH. // and Contributors. // // SPDX-License-Identifier: BSL-1.0 // #ifndef Zip_PartialStream_INCLUDED #define Zip_PartialStream_INCLUDED #include "Poco/Zip/Zip.h" #include "Poco/BufferedStreamBuf.h" #include "Poco/Buffer.h" #include #include namespace Poco { namespace Zip { class Zip_API PartialStreamBuf: public Poco::BufferedStreamBuf /// A PartialStreamBuf is a class that limits one view on an inputstream to a selected view range { public: PartialStreamBuf(std::istream& in, std::ios::pos_type start, std::ios::pos_type end, const std::string& prefix, const std::string& postfix, bool initStream); /// Creates the PartialStream. /// If initStream is true the status of the stream will be cleared on the first access, and the stream will be repositioned /// to position start PartialStreamBuf(std::ostream& out, std::size_t start, std::size_t end, bool initStream); /// Creates the PartialStream. /// If initStream is true the status of the stream will be cleared on the first access. /// start and end acts as offset values for the written content. A start value greater than zero, /// means that the first bytes are not written but discarded instead, /// an end value not equal to zero means that the last end bytes are not written! /// Examples: /// start = 3; end = 1 /// write("hello", 5) -> "l" ~PartialStreamBuf(); /// Destroys the PartialStream. void close(); /// Flushes a writing streambuf Poco::UInt64 bytesWritten() const; protected: int readFromDevice(char* buffer, std::streamsize length); int writeToDevice(const char* buffer, std::streamsize length); private: enum { STREAM_BUFFER_SIZE = 1024 }; bool _initialized; std::ios::pos_type _start; Poco::UInt64 _numBytes; Poco::UInt64 _bytesWritten; std::istream* _pIstr; std::ostream* _pOstr; std::string _prefix; std::string _postfix; std::size_t _ignoreStart; Poco::Buffer _buffer; Poco::UInt32 _bufferOffset; }; inline Poco::UInt64 PartialStreamBuf::bytesWritten() const { return _bytesWritten; } class Zip_API PartialIOS: public virtual std::ios /// The base class for PartialInputStream and PartialOutputStream. /// /// This class is needed to ensure the correct initialization /// order of the stream buffer and base classes. { public: PartialIOS(std::istream& istr, std::ios::pos_type start, std::ios::pos_type end, const std::string& prefix, const std::string& postfix, bool initStream); /// Creates the basic stream and connects it /// to the given input stream. /// If initStream is true the status of the stream will be cleared on the first access, and the stream will be repositioned /// to position start PartialIOS(std::ostream& ostr, std::size_t start, std::size_t end, bool initStream); /// Creates the basic stream and connects it /// to the given output stream. /// If initStream is true the status of the stream will be cleared on the first access. /// start and end acts as offset values for the written content. A start value greater than zero, /// means that the first bytes are not written but discarded instead, /// an end value not equal to zero means that the last end bytes are not written! /// Examples: /// start = 3; end = 1 /// write("hello", 5) -> "l" ~PartialIOS(); /// Destroys the stream. PartialStreamBuf* rdbuf(); /// Returns a pointer to the underlying streambuf. protected: PartialStreamBuf _buf; }; class Zip_API PartialInputStream: public PartialIOS, public std::istream /// This stream copies all characters read through it /// to one or multiple output streams. { public: PartialInputStream(std::istream& istr, std::ios::pos_type start, std::ios::pos_type end, bool initStream = true, const std::string& prefix = std::string(), const std::string& postfix = std::string()); /// Creates the PartialInputStream and connects it /// to the given input stream. Bytes read are guaranteed to be in the range [start, end-1] /// If initStream is true the status of the stream will be cleared on the first access, and the stream will be repositioned /// to position start ~PartialInputStream(); /// Destroys the PartialInputStream. }; class Zip_API PartialOutputStream: public PartialIOS, public std::ostream /// This stream copies all characters written to it /// to one or multiple output streams. { public: PartialOutputStream(std::ostream& ostr, std::size_t start, std::size_t end, bool initStream = true); /// Creates the PartialOutputStream and connects it /// to the given output stream. Bytes written are guaranteed to be in the range [start, realEnd - end]. /// If initStream is true the status of the stream will be cleared on the first access. /// start and end acts as offset values for the written content. A start value greater than zero, /// means that the first bytes are not written but discarded instead, /// an end value not equal to zero means that the last end bytes are not written! /// Examples: /// start = 3; end = 1 /// write("hello", 5) -> "l" /// /// start = 3; end = 0 /// write("hello", 5) -> "lo" ~PartialOutputStream(); /// Destroys the PartialOutputStream. void close(); /// must be called for the stream to properly terminate it Poco::UInt64 bytesWritten() const; /// Returns the number of bytes actually forwarded to the inner ostream }; inline void PartialOutputStream::close() { flush(); _buf.close(); } inline Poco::UInt64 PartialOutputStream::bytesWritten() const { return _buf.bytesWritten(); } } } // namespace Poco::Zip #endif // Zip_PartialStream_INCLUDED