fifo_buffer.h 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136
  1. /*
  2. * Copyright 2019 The WebRTC Project Authors. All rights reserved.
  3. *
  4. * Use of this source code is governed by a BSD-style license
  5. * that can be found in the LICENSE file in the root of the source
  6. * tree. An additional intellectual property rights grant can be found
  7. * in the file PATENTS. All contributing project authors may
  8. * be found in the AUTHORS file in the root of the source tree.
  9. */
  10. #ifndef RTC_BASE_MEMORY_FIFO_BUFFER_H_
  11. #define RTC_BASE_MEMORY_FIFO_BUFFER_H_
  12. #include <memory>
  13. #include "rtc_base/stream.h"
  14. #include "rtc_base/synchronization/mutex.h"
  15. namespace rtc {
  16. // FifoBuffer allows for efficient, thread-safe buffering of data between
  17. // writer and reader.
  18. class FifoBuffer final : public StreamInterface {
  19. public:
  20. // Creates a FIFO buffer with the specified capacity.
  21. explicit FifoBuffer(size_t length);
  22. // Creates a FIFO buffer with the specified capacity and owner
  23. FifoBuffer(size_t length, Thread* owner);
  24. ~FifoBuffer() override;
  25. // Gets the amount of data currently readable from the buffer.
  26. bool GetBuffered(size_t* data_len) const;
  27. // Resizes the buffer to the specified capacity. Fails if data_length_ > size
  28. bool SetCapacity(size_t length);
  29. // Read into |buffer| with an offset from the current read position, offset
  30. // is specified in number of bytes.
  31. // This method doesn't adjust read position nor the number of available
  32. // bytes, user has to call ConsumeReadData() to do this.
  33. StreamResult ReadOffset(void* buffer,
  34. size_t bytes,
  35. size_t offset,
  36. size_t* bytes_read);
  37. // Write |buffer| with an offset from the current write position, offset is
  38. // specified in number of bytes.
  39. // This method doesn't adjust the number of buffered bytes, user has to call
  40. // ConsumeWriteBuffer() to do this.
  41. StreamResult WriteOffset(const void* buffer,
  42. size_t bytes,
  43. size_t offset,
  44. size_t* bytes_written);
  45. // StreamInterface methods
  46. StreamState GetState() const override;
  47. StreamResult Read(void* buffer,
  48. size_t bytes,
  49. size_t* bytes_read,
  50. int* error) override;
  51. StreamResult Write(const void* buffer,
  52. size_t bytes,
  53. size_t* bytes_written,
  54. int* error) override;
  55. void Close() override;
  56. // Seek to a byte offset from the beginning of the stream. Returns false if
  57. // the stream does not support seeking, or cannot seek to the specified
  58. // position.
  59. bool SetPosition(size_t position);
  60. // Get the byte offset of the current position from the start of the stream.
  61. // Returns false if the position is not known.
  62. bool GetPosition(size_t* position) const;
  63. // Seek to the start of the stream.
  64. bool Rewind() { return SetPosition(0); }
  65. // GetReadData returns a pointer to a buffer which is owned by the stream.
  66. // The buffer contains data_len bytes. null is returned if no data is
  67. // available, or if the method fails. If the caller processes the data, it
  68. // must call ConsumeReadData with the number of processed bytes. GetReadData
  69. // does not require a matching call to ConsumeReadData if the data is not
  70. // processed. Read and ConsumeReadData invalidate the buffer returned by
  71. // GetReadData.
  72. const void* GetReadData(size_t* data_len);
  73. void ConsumeReadData(size_t used);
  74. // GetWriteBuffer returns a pointer to a buffer which is owned by the stream.
  75. // The buffer has a capacity of buf_len bytes. null is returned if there is
  76. // no buffer available, or if the method fails. The call may write data to
  77. // the buffer, and then call ConsumeWriteBuffer with the number of bytes
  78. // written. GetWriteBuffer does not require a matching call to
  79. // ConsumeWriteData if no data is written. Write and
  80. // ConsumeWriteData invalidate the buffer returned by GetWriteBuffer.
  81. void* GetWriteBuffer(size_t* buf_len);
  82. void ConsumeWriteBuffer(size_t used);
  83. // Return the number of Write()-able bytes remaining before end-of-stream.
  84. // Returns false if not known.
  85. bool GetWriteRemaining(size_t* size) const;
  86. private:
  87. // Helper method that implements ReadOffset. Caller must acquire a lock
  88. // when calling this method.
  89. StreamResult ReadOffsetLocked(void* buffer,
  90. size_t bytes,
  91. size_t offset,
  92. size_t* bytes_read)
  93. RTC_EXCLUSIVE_LOCKS_REQUIRED(mutex_);
  94. // Helper method that implements WriteOffset. Caller must acquire a lock
  95. // when calling this method.
  96. StreamResult WriteOffsetLocked(const void* buffer,
  97. size_t bytes,
  98. size_t offset,
  99. size_t* bytes_written)
  100. RTC_EXCLUSIVE_LOCKS_REQUIRED(mutex_);
  101. // keeps the opened/closed state of the stream
  102. StreamState state_ RTC_GUARDED_BY(mutex_);
  103. // the allocated buffer
  104. std::unique_ptr<char[]> buffer_ RTC_GUARDED_BY(mutex_);
  105. // size of the allocated buffer
  106. size_t buffer_length_ RTC_GUARDED_BY(mutex_);
  107. // amount of readable data in the buffer
  108. size_t data_length_ RTC_GUARDED_BY(mutex_);
  109. // offset to the readable data
  110. size_t read_position_ RTC_GUARDED_BY(mutex_);
  111. // stream callbacks are dispatched on this thread
  112. Thread* owner_;
  113. // object lock
  114. mutable webrtc::Mutex mutex_;
  115. RTC_DISALLOW_COPY_AND_ASSIGN(FifoBuffer);
  116. };
  117. } // namespace rtc
  118. #endif // RTC_BASE_MEMORY_FIFO_BUFFER_H_