Commit 855ab0e7 authored by Thiabaud Engelbrecht's avatar Thiabaud Engelbrecht Committed by Chromium LUCI CQ

[blink] Clean up RWBuffer.

This a follow-up to https://chromium-review.googlesource.com/c/chromium/src/+/2551847,
which moved RWBuffer from skia to blink.

This CL includes the following:

- Remove `ROBufferStreamAsset` and associated code, since it was unused.
- use `scoped_refptr` instead of `sk_sp`.
- use `BufferMalloc`/`BufferFree` instead of skia versions.
- use `AtomicRefCount` instead of doing it manually.
- Rename tests.

Bug: 1154426
Change-Id: I1faafe98dc1123457974644ee9eb358f57ba9786
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2569102
Commit-Queue: Thiabaud Engelbrecht <thiabaud@google.com>
Reviewed-by: default avatarJeremy Roman <jbroman@chromium.org>
Cr-Commit-Position: refs/heads/master@{#834231}
parent f414566a
...@@ -190,7 +190,7 @@ sk_sp<PaintImageGenerator> DeferredImageDecoder::CreateGenerator() { ...@@ -190,7 +190,7 @@ sk_sp<PaintImageGenerator> DeferredImageDecoder::CreateGenerator() {
DCHECK_GT(decoded_size.width(), 0); DCHECK_GT(decoded_size.width(), 0);
DCHECK_GT(decoded_size.height(), 0); DCHECK_GT(decoded_size.height(), 0);
sk_sp<ROBuffer> ro_buffer(rw_buffer_->MakeROBufferSnapshot()); scoped_refptr<ROBuffer> ro_buffer(rw_buffer_->MakeROBufferSnapshot());
scoped_refptr<SegmentReader> segment_reader = scoped_refptr<SegmentReader> segment_reader =
SegmentReader::CreateFromROBuffer(std::move(ro_buffer)); SegmentReader::CreateFromROBuffer(std::move(ro_buffer));
...@@ -251,7 +251,7 @@ sk_sp<PaintImageGenerator> DeferredImageDecoder::CreateGenerator() { ...@@ -251,7 +251,7 @@ sk_sp<PaintImageGenerator> DeferredImageDecoder::CreateGenerator() {
scoped_refptr<SharedBuffer> DeferredImageDecoder::Data() { scoped_refptr<SharedBuffer> DeferredImageDecoder::Data() {
if (!rw_buffer_) if (!rw_buffer_)
return nullptr; return nullptr;
sk_sp<ROBuffer> ro_buffer(rw_buffer_->MakeROBufferSnapshot()); scoped_refptr<ROBuffer> ro_buffer(rw_buffer_->MakeROBufferSnapshot());
scoped_refptr<SharedBuffer> shared_buffer = SharedBuffer::Create(); scoped_refptr<SharedBuffer> shared_buffer = SharedBuffer::Create();
ROBuffer::Iter it(ro_buffer.get()); ROBuffer::Iter it(ro_buffer.get());
do { do {
......
...@@ -4,10 +4,10 @@ ...@@ -4,10 +4,10 @@
#include "third_party/blink/renderer/platform/graphics/rw_buffer.h" #include "third_party/blink/renderer/platform/graphics/rw_buffer.h"
#include "base/atomic_ref_count.h"
#include "base/check.h" #include "base/check.h"
#include "base/check_op.h" #include "base/check_op.h"
#include "third_party/skia/include/core/SkStream.h" #include "third_party/blink/renderer/platform/wtf/allocator/partitions.h"
#include "third_party/skia/include/private/SkMalloc.h"
#include <algorithm> #include <algorithm>
#include <atomic> #include <atomic>
...@@ -39,7 +39,9 @@ struct RWBuffer::BufferBlock { ...@@ -39,7 +39,9 @@ struct RWBuffer::BufferBlock {
static RWBuffer::BufferBlock* Alloc(size_t length) { static RWBuffer::BufferBlock* Alloc(size_t length) {
size_t capacity = LengthToCapacity(length); size_t capacity = LengthToCapacity(length);
void* buffer = sk_malloc_throw(sizeof(RWBuffer::BufferBlock) + capacity); void* buffer =
WTF::Partitions::BufferMalloc(sizeof(RWBuffer::BufferBlock) + capacity,
"blink::RWBuffer::BufferBlock");
return new (buffer) RWBuffer::BufferBlock(capacity); return new (buffer) RWBuffer::BufferBlock(capacity);
} }
...@@ -71,7 +73,7 @@ struct RWBuffer::BufferBlock { ...@@ -71,7 +73,7 @@ struct RWBuffer::BufferBlock {
}; };
struct RWBuffer::BufferHead { struct RWBuffer::BufferHead {
mutable std::atomic<int32_t> ref_count_; mutable base::AtomicRefCount ref_count_;
RWBuffer::BufferBlock block_; RWBuffer::BufferBlock block_;
explicit BufferHead(size_t capacity) : ref_count_(1), block_(capacity) {} explicit BufferHead(size_t capacity) : ref_count_(1), block_(capacity) {}
...@@ -84,27 +86,27 @@ struct RWBuffer::BufferHead { ...@@ -84,27 +86,27 @@ struct RWBuffer::BufferHead {
static RWBuffer::BufferHead* Alloc(size_t length) { static RWBuffer::BufferHead* Alloc(size_t length) {
size_t capacity = LengthToCapacity(length); size_t capacity = LengthToCapacity(length);
size_t size = sizeof(RWBuffer::BufferHead) + capacity; size_t size = sizeof(RWBuffer::BufferHead) + capacity;
void* buffer = sk_malloc_throw(size); void* buffer =
WTF::Partitions::BufferMalloc(size, "blink::RWBuffer::BufferHead");
return new (buffer) RWBuffer::BufferHead(capacity); return new (buffer) RWBuffer::BufferHead(capacity);
} }
void ref() const { void ref() const {
auto old_ref_count = ref_count_.fetch_add(+1, std::memory_order_relaxed); auto old_ref_count = ref_count_.Increment();
DCHECK_GT(old_ref_count, 0); DCHECK_GT(old_ref_count, 0);
} }
void unref() const { void unref() const {
// A release here acts in place of all releases we "should" have been doing // A release here acts in place of all releases we "should" have been doing
// in ref(). // in ref().
int32_t oldRefCnt = ref_count_.fetch_add(-1, std::memory_order_acq_rel); if (!ref_count_.Decrement()) {
DCHECK(oldRefCnt);
if (1 == oldRefCnt) {
// Like unique(), the acquire is only needed on success. // Like unique(), the acquire is only needed on success.
RWBuffer::BufferBlock* block = block_.next_; RWBuffer::BufferBlock* block = block_.next_;
sk_free(reinterpret_cast<void*>(const_cast<RWBuffer::BufferHead*>(this))); WTF::Partitions::BufferFree(
reinterpret_cast<void*>(const_cast<RWBuffer::BufferHead*>(this)));
while (block) { while (block) {
RWBuffer::BufferBlock* next = block->next_; RWBuffer::BufferBlock* next = block->next_;
sk_free(block); WTF::Partitions::BufferFree(block);
block = next; block = next;
} }
} }
...@@ -113,7 +115,7 @@ struct RWBuffer::BufferHead { ...@@ -113,7 +115,7 @@ struct RWBuffer::BufferHead {
void Validate(size_t minUsed, void Validate(size_t minUsed,
const RWBuffer::BufferBlock* tail = nullptr) const { const RWBuffer::BufferBlock* tail = nullptr) const {
#if DCHECK_IS_ON() #if DCHECK_IS_ON()
DCHECK_GT(ref_count_.load(std::memory_order_relaxed), 0); DCHECK(!ref_count_.IsZero());
size_t totalUsed = 0; size_t totalUsed = 0;
const RWBuffer::BufferBlock* block = &block_; const RWBuffer::BufferBlock* block = &block_;
const RWBuffer::BufferBlock* lastBlock = block; const RWBuffer::BufferBlock* lastBlock = block;
...@@ -159,7 +161,7 @@ ROBuffer::Iter::Iter(const ROBuffer* buffer) { ...@@ -159,7 +161,7 @@ ROBuffer::Iter::Iter(const ROBuffer* buffer) {
Reset(buffer); Reset(buffer);
} }
ROBuffer::Iter::Iter(const sk_sp<ROBuffer>& buffer) { ROBuffer::Iter::Iter(const scoped_refptr<ROBuffer>& buffer) {
Reset(buffer.get()); Reset(buffer.get());
} }
...@@ -239,8 +241,7 @@ void RWBuffer::Append(const void* src, size_t length, size_t reserve) { ...@@ -239,8 +241,7 @@ void RWBuffer::Append(const void* src, size_t length, size_t reserve) {
length -= written; length -= written;
if (length) { if (length) {
RWBuffer::BufferBlock* block = auto* block = RWBuffer::BufferBlock::Alloc(length + reserve);
RWBuffer::BufferBlock::Alloc(length + reserve);
tail_->next_ = block; tail_->next_ = block;
tail_ = block; tail_ = block;
written = tail_->Append(src, length); written = tail_->Append(src, length);
...@@ -249,8 +250,8 @@ void RWBuffer::Append(const void* src, size_t length, size_t reserve) { ...@@ -249,8 +250,8 @@ void RWBuffer::Append(const void* src, size_t length, size_t reserve) {
Validate(); Validate();
} }
sk_sp<ROBuffer> RWBuffer::MakeROBufferSnapshot() const { scoped_refptr<ROBuffer> RWBuffer::MakeROBufferSnapshot() const {
return sk_sp<ROBuffer>(new ROBuffer(head_, total_used_, tail_)); return AdoptRef(new ROBuffer(head_, total_used_, tail_));
} }
bool RWBuffer::HasNoSnapshots() const { bool RWBuffer::HasNoSnapshots() const {
...@@ -260,10 +261,7 @@ bool RWBuffer::HasNoSnapshots() const { ...@@ -260,10 +261,7 @@ bool RWBuffer::HasNoSnapshots() const {
return true; return true;
} }
// For this to be useful, it should only return true when the other threads return head_->ref_count_.IsOne();
// can no longer touch the buffer; this means that the "acquire" ordering is
// required, since the count is decreased with "release" ordering.
return head_->ref_count_.load(std::memory_order_acquire) == 1;
} }
void RWBuffer::Validate() const { void RWBuffer::Validate() const {
...@@ -277,123 +275,4 @@ void RWBuffer::Validate() const { ...@@ -277,123 +275,4 @@ void RWBuffer::Validate() const {
#endif #endif
} }
///////////////////////////////////////////////////////////////////////////////////////////////////
class ROBufferStreamAsset : public SkStreamAsset {
void Validate() const {
DCHECK(global_offset_ <= buffer_->size());
DCHECK(local_offset_ <= iter_.size());
DCHECK(local_offset_ <= global_offset_);
}
#if DCHECK_IS_ON()
class AutoValidate {
public:
explicit AutoValidate(ROBufferStreamAsset* stream) : stream_(stream) {
stream->Validate();
}
~AutoValidate() { stream_->Validate(); }
private:
ROBufferStreamAsset* stream_;
};
#else
class AutoValidate {
public:
explicit AutoValidate(ROBufferStreamAsset*) {}
};
#endif
public:
explicit ROBufferStreamAsset(sk_sp<ROBuffer> buffer)
: buffer_(std::move(buffer)), iter_(buffer_) {
global_offset_ = local_offset_ = 0;
}
size_t getLength() const override { return buffer_->size(); }
bool rewind() override {
AutoValidate av(this);
iter_.Reset(buffer_.get());
global_offset_ = local_offset_ = 0;
return true;
}
size_t read(void* dst, size_t request) override {
AutoValidate av(this);
size_t bytesRead = 0;
for (;;) {
size_t size = iter_.size();
DCHECK(local_offset_ <= size);
size_t avail = std::min(size - local_offset_, request - bytesRead);
if (dst) {
memcpy(dst, static_cast<const char*>(iter_.data()) + local_offset_,
avail);
dst = static_cast<char*>(dst) + avail;
}
bytesRead += avail;
local_offset_ += avail;
DCHECK(bytesRead <= request);
if (bytesRead == request) {
break;
}
// If we get here, we've exhausted the current iter
DCHECK(local_offset_ == size);
local_offset_ = 0;
if (!iter_.Next()) {
break; // ran out of data
}
}
global_offset_ += bytesRead;
DCHECK(global_offset_ <= buffer_->size());
return bytesRead;
}
bool isAtEnd() const override { return buffer_->size() == global_offset_; }
size_t getPosition() const override { return global_offset_; }
bool seek(size_t position) override {
AutoValidate av(this);
if (position < global_offset_) {
rewind();
}
(void)skip(position - global_offset_);
return true;
}
// Since this is overriding a member function we don't control, we can't
// change this type. So, disable the warning here instead.
bool move(long offset) override { // NOLINT
AutoValidate av(this);
offset += global_offset_;
if (offset <= 0) {
rewind();
} else {
(void)seek(SkToSizeT(offset));
}
return true;
}
private:
SkStreamAsset* onDuplicate() const override {
return new ROBufferStreamAsset(buffer_);
}
SkStreamAsset* onFork() const override {
auto clone = duplicate();
clone->seek(getPosition());
return clone.release();
}
sk_sp<ROBuffer> buffer_;
ROBuffer::Iter iter_;
size_t local_offset_;
size_t global_offset_;
};
std::unique_ptr<SkStreamAsset> RWBuffer::MakeStreamSnapshot() const {
return std::make_unique<ROBufferStreamAsset>(MakeROBufferSnapshot());
}
} // namespace blink } // namespace blink
...@@ -6,9 +6,7 @@ ...@@ -6,9 +6,7 @@
#define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_RW_BUFFER_H_ #define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_RW_BUFFER_H_
#include "third_party/blink/renderer/platform/platform_export.h" #include "third_party/blink/renderer/platform/platform_export.h"
#include "third_party/skia/include/core/SkRefCnt.h" #include "third_party/blink/renderer/platform/wtf/thread_safe_ref_counted.h"
class SkStreamAsset;
namespace blink { namespace blink {
...@@ -44,7 +42,7 @@ class PLATFORM_EXPORT RWBuffer { ...@@ -44,7 +42,7 @@ class PLATFORM_EXPORT RWBuffer {
*/ */
void Append(const void* buffer, size_t length, size_t reserve = 0); void Append(const void* buffer, size_t length, size_t reserve = 0);
sk_sp<ROBuffer> MakeROBufferSnapshot() const; scoped_refptr<ROBuffer> MakeROBufferSnapshot() const;
// This should only be called from the same thread that we are creating the // This should only be called from the same thread that we are creating the
// RWBuffer and the snapshots on. // RWBuffer and the snapshots on.
...@@ -52,8 +50,6 @@ class PLATFORM_EXPORT RWBuffer { ...@@ -52,8 +50,6 @@ class PLATFORM_EXPORT RWBuffer {
// its underlying buffer. // its underlying buffer.
bool HasNoSnapshots() const; bool HasNoSnapshots() const;
std::unique_ptr<SkStreamAsset> MakeStreamSnapshot() const;
void Validate() const; void Validate() const;
private: private:
...@@ -67,7 +63,7 @@ class PLATFORM_EXPORT RWBuffer { ...@@ -67,7 +63,7 @@ class PLATFORM_EXPORT RWBuffer {
* the caller must instantiate a local iterator, as the memory is stored in 1 or * the caller must instantiate a local iterator, as the memory is stored in 1 or
* more contiguous blocks. * more contiguous blocks.
*/ */
class PLATFORM_EXPORT ROBuffer : public SkRefCnt { class PLATFORM_EXPORT ROBuffer : public WTF::ThreadSafeRefCounted<ROBuffer> {
public: public:
/** /**
* Return the logical length of the data owned/shared by this buffer. It may * Return the logical length of the data owned/shared by this buffer. It may
...@@ -78,7 +74,7 @@ class PLATFORM_EXPORT ROBuffer : public SkRefCnt { ...@@ -78,7 +74,7 @@ class PLATFORM_EXPORT ROBuffer : public SkRefCnt {
class PLATFORM_EXPORT Iter { class PLATFORM_EXPORT Iter {
public: public:
explicit Iter(const ROBuffer*); explicit Iter(const ROBuffer*);
explicit Iter(const sk_sp<ROBuffer>&); explicit Iter(const scoped_refptr<ROBuffer>&);
void Reset(const ROBuffer*); void Reset(const ROBuffer*);
...@@ -107,10 +103,11 @@ class PLATFORM_EXPORT ROBuffer : public SkRefCnt { ...@@ -107,10 +103,11 @@ class PLATFORM_EXPORT ROBuffer : public SkRefCnt {
}; };
private: private:
friend class WTF::ThreadSafeRefCounted<ROBuffer>;
ROBuffer(const RWBuffer::BufferHead* head, ROBuffer(const RWBuffer::BufferHead* head,
size_t available, size_t available,
const RWBuffer::BufferBlock* tail); const RWBuffer::BufferBlock* tail);
~ROBuffer() override; ~ROBuffer();
const RWBuffer::BufferHead* head_; const RWBuffer::BufferHead* head_;
const size_t available_; const size_t available_;
......
...@@ -22,28 +22,6 @@ void check_abcs(const char buffer[], size_t size) { ...@@ -22,28 +22,6 @@ void check_abcs(const char buffer[], size_t size) {
} }
} }
// stream should contain an integral number of copies of gABC.
void check_alphabet_stream(SkStream* stream) {
ASSERT_TRUE(stream->hasLength());
size_t size = stream->getLength();
ASSERT_EQ(size % 26, 0u);
std::vector<char> storage(size);
char* array = storage.data();
size_t bytesRead = stream->read(array, size);
EXPECT_EQ(bytesRead, size);
check_abcs(array, size);
// try checking backwards
for (size_t offset = size; offset > 0; offset -= 26) {
EXPECT_TRUE(stream->seek(offset - 26));
EXPECT_EQ(stream->getPosition(), offset - 26);
EXPECT_EQ(stream->read(array, 26), 26u);
check_abcs(array, 26);
EXPECT_EQ(stream->getPosition(), offset);
}
}
// reader should contains an integral number of copies of gABC. // reader should contains an integral number of copies of gABC.
void check_alphabet_buffer(const ROBuffer* reader) { void check_alphabet_buffer(const ROBuffer* reader) {
size_t size = reader->size(); size_t size = reader->size();
...@@ -63,40 +41,33 @@ void check_alphabet_buffer(const ROBuffer* reader) { ...@@ -63,40 +41,33 @@ void check_alphabet_buffer(const ROBuffer* reader) {
class ROBufferTestThread : public base::PlatformThread::Delegate { class ROBufferTestThread : public base::PlatformThread::Delegate {
public: public:
ROBufferTestThread(sk_sp<ROBuffer> reader, SkStream* stream, size_t i) ROBufferTestThread(scoped_refptr<ROBuffer> reader, size_t i)
: reader_(reader), stream_(stream), i_(i) {} : reader_(reader), i_(i) {}
ROBufferTestThread() = default; ROBufferTestThread() = default;
ROBufferTestThread(const ROBufferTestThread&) = default; ROBufferTestThread(const ROBufferTestThread&) = default;
void ThreadMain() override { void ThreadMain() override {
EXPECT_EQ((i_ + 1) * 26U, reader_->size()); EXPECT_EQ((i_ + 1) * 26U, reader_->size());
EXPECT_EQ(stream_->getLength(), reader_->size());
check_alphabet_buffer(reader_.get()); check_alphabet_buffer(reader_.get());
check_alphabet_stream(stream_);
EXPECT_TRUE(stream_->rewind());
delete stream_;
} }
sk_sp<ROBuffer> reader_; scoped_refptr<ROBuffer> reader_;
SkStream* stream_;
size_t i_; size_t i_;
}; };
} // namespace } // namespace
TEST(RWBuffer, reporter) { TEST(RWBufferTest, Append) {
// Knowing that the default capacity is 4096, choose N large enough so we // Knowing that the default capacity is 4096, choose N large enough so we
// force it to use multiple buffers internally. // force it to use multiple buffers internally.
static constexpr size_t N = 1000; static constexpr size_t N = 1000;
std::array<sk_sp<ROBuffer>, N> readers; std::array<scoped_refptr<ROBuffer>, N> readers;
std::array<std::unique_ptr<SkStream>, N> streams;
{ {
RWBuffer buffer; RWBuffer buffer;
for (size_t i = 0; i < N; ++i) { for (size_t i = 0; i < N; ++i) {
buffer.Append(gABC, 26); buffer.Append(gABC, 26);
readers[i] = buffer.MakeROBufferSnapshot(); readers[i] = buffer.MakeROBufferSnapshot();
streams[i] = buffer.MakeStreamSnapshot();
} }
EXPECT_EQ(N * 26, buffer.size()); EXPECT_EQ(N * 26, buffer.size());
} }
...@@ -106,11 +77,10 @@ TEST(RWBuffer, reporter) { ...@@ -106,11 +77,10 @@ TEST(RWBuffer, reporter) {
for (size_t i = 0; i < N; ++i) { for (size_t i = 0; i < N; ++i) {
EXPECT_EQ((i + 1) * 26U, readers[i]->size()); EXPECT_EQ((i + 1) * 26U, readers[i]->size());
check_alphabet_buffer(readers[i].get()); check_alphabet_buffer(readers[i].get());
check_alphabet_stream(streams[i].get());
} }
} }
TEST(RWBuffer_threaded, reporter) { TEST(RWBufferTest, Threaded) {
// Knowing that the default capacity is 4096, choose N large enough so we // Knowing that the default capacity is 4096, choose N large enough so we
// force it to use multiple buffers internally. // force it to use multiple buffers internally.
constexpr size_t N = 1000; constexpr size_t N = 1000;
...@@ -120,15 +90,13 @@ TEST(RWBuffer_threaded, reporter) { ...@@ -120,15 +90,13 @@ TEST(RWBuffer_threaded, reporter) {
for (size_t i = 0; i < N; ++i) { for (size_t i = 0; i < N; ++i) {
buffer.Append(gABC, 26); buffer.Append(gABC, 26);
sk_sp<ROBuffer> reader = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> reader = buffer.MakeROBufferSnapshot();
SkStream* stream = buffer.MakeStreamSnapshot().release();
EXPECT_EQ(reader->size(), buffer.size()); EXPECT_EQ(reader->size(), buffer.size());
EXPECT_EQ(stream->getLength(), buffer.size());
// reader's copy constructor will ref the ROBuffer, which will be unreffed // reader's copy constructor will ref the ROBuffer, which will be unreffed
// when the task ends. // when the task ends.
// Ownership of stream is passed to the task, which will delete it. // Ownership of stream is passed to the task, which will delete it.
threads[i] = ROBufferTestThread(reader, stream, i); threads[i] = ROBufferTestThread(reader, i);
ASSERT_TRUE(base::PlatformThread::Create(0, &threads[i], &handlers[i])); ASSERT_TRUE(base::PlatformThread::Create(0, &threads[i], &handlers[i]));
} }
EXPECT_EQ(N * 26, buffer.size()); EXPECT_EQ(N * 26, buffer.size());
...@@ -138,11 +106,11 @@ TEST(RWBuffer_threaded, reporter) { ...@@ -138,11 +106,11 @@ TEST(RWBuffer_threaded, reporter) {
} }
// Tests that it is safe to call ROBuffer::Iter::size() when exhausted. // Tests that it is safe to call ROBuffer::Iter::size() when exhausted.
TEST(RWBuffer_size, r) { TEST(RWBufferTest, Size) {
RWBuffer buffer; RWBuffer buffer;
buffer.Append(gABC, 26); buffer.Append(gABC, 26);
sk_sp<ROBuffer> roBuffer(buffer.MakeROBufferSnapshot()); scoped_refptr<ROBuffer> roBuffer(buffer.MakeROBufferSnapshot());
ROBuffer::Iter iter(roBuffer.get()); ROBuffer::Iter iter(roBuffer.get());
EXPECT_TRUE(iter.data()); EXPECT_TRUE(iter.data());
EXPECT_EQ(iter.size(), 26u); EXPECT_EQ(iter.size(), 26u);
...@@ -154,11 +122,11 @@ TEST(RWBuffer_size, r) { ...@@ -154,11 +122,11 @@ TEST(RWBuffer_size, r) {
// Tests that operations (including the destructor) are safe on an RWBuffer // Tests that operations (including the destructor) are safe on an RWBuffer
// without any data appended. // without any data appended.
TEST(RWBuffer_noAppend, r) { TEST(RWBufferTest, Empty) {
RWBuffer buffer; RWBuffer buffer;
ASSERT_EQ(0u, buffer.size()); ASSERT_EQ(0u, buffer.size());
sk_sp<ROBuffer> roBuffer = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> roBuffer = buffer.MakeROBufferSnapshot();
ASSERT_TRUE(roBuffer); ASSERT_TRUE(roBuffer);
if (roBuffer) { if (roBuffer) {
EXPECT_EQ(roBuffer->size(), 0u); EXPECT_EQ(roBuffer->size(), 0u);
...@@ -167,14 +135,6 @@ TEST(RWBuffer_noAppend, r) { ...@@ -167,14 +135,6 @@ TEST(RWBuffer_noAppend, r) {
EXPECT_TRUE(!iter.data()); EXPECT_TRUE(!iter.data());
EXPECT_TRUE(!iter.Next()); EXPECT_TRUE(!iter.Next());
} }
std::unique_ptr<SkStream> stream(buffer.MakeStreamSnapshot());
EXPECT_TRUE(stream);
if (stream) {
EXPECT_TRUE(stream->hasLength());
EXPECT_EQ(stream->getLength(), 0u);
EXPECT_EQ(stream->skip(10), 0u);
}
} }
// Tests that |HasNoSnapshots| returns the correct value when the buffer is // Tests that |HasNoSnapshots| returns the correct value when the buffer is
...@@ -188,10 +148,10 @@ TEST(RWBufferTest, HasNoSnapshotsEmpty) { ...@@ -188,10 +148,10 @@ TEST(RWBufferTest, HasNoSnapshotsEmpty) {
EXPECT_TRUE(buffer.HasNoSnapshots()); EXPECT_TRUE(buffer.HasNoSnapshots());
{ {
sk_sp<ROBuffer> first = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> first = buffer.MakeROBufferSnapshot();
EXPECT_TRUE(buffer.HasNoSnapshots()); EXPECT_TRUE(buffer.HasNoSnapshots());
sk_sp<ROBuffer> second = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> second = buffer.MakeROBufferSnapshot();
EXPECT_TRUE(buffer.HasNoSnapshots()); EXPECT_TRUE(buffer.HasNoSnapshots());
} }
...@@ -209,10 +169,10 @@ TEST(RWBufferTest, HasNoSnapshots) { ...@@ -209,10 +169,10 @@ TEST(RWBufferTest, HasNoSnapshots) {
EXPECT_TRUE(buffer.HasNoSnapshots()); EXPECT_TRUE(buffer.HasNoSnapshots());
{ {
sk_sp<ROBuffer> first = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> first = buffer.MakeROBufferSnapshot();
EXPECT_FALSE(buffer.HasNoSnapshots()); EXPECT_FALSE(buffer.HasNoSnapshots());
sk_sp<ROBuffer> second = buffer.MakeROBufferSnapshot(); scoped_refptr<ROBuffer> second = buffer.MakeROBufferSnapshot();
EXPECT_FALSE(buffer.HasNoSnapshots()); EXPECT_FALSE(buffer.HasNoSnapshots());
} }
......
...@@ -103,14 +103,14 @@ sk_sp<SkData> DataSegmentReader::GetAsSkData() const { ...@@ -103,14 +103,14 @@ sk_sp<SkData> DataSegmentReader::GetAsSkData() const {
class ROBufferSegmentReader final : public SegmentReader { class ROBufferSegmentReader final : public SegmentReader {
public: public:
explicit ROBufferSegmentReader(sk_sp<ROBuffer>); explicit ROBufferSegmentReader(scoped_refptr<ROBuffer>);
size_t size() const override; size_t size() const override;
size_t GetSomeData(const char*& data, size_t position) const override; size_t GetSomeData(const char*& data, size_t position) const override;
sk_sp<SkData> GetAsSkData() const override; sk_sp<SkData> GetAsSkData() const override;
private: private:
sk_sp<ROBuffer> ro_buffer_; scoped_refptr<ROBuffer> ro_buffer_;
mutable Mutex read_mutex_; mutable Mutex read_mutex_;
// Position of the first char in the current block of iter_. // Position of the first char in the current block of iter_.
mutable size_t position_of_block_ GUARDED_BY(read_mutex_); mutable size_t position_of_block_ GUARDED_BY(read_mutex_);
...@@ -119,7 +119,7 @@ class ROBufferSegmentReader final : public SegmentReader { ...@@ -119,7 +119,7 @@ class ROBufferSegmentReader final : public SegmentReader {
DISALLOW_COPY_AND_ASSIGN(ROBufferSegmentReader); DISALLOW_COPY_AND_ASSIGN(ROBufferSegmentReader);
}; };
ROBufferSegmentReader::ROBufferSegmentReader(sk_sp<ROBuffer> buffer) ROBufferSegmentReader::ROBufferSegmentReader(scoped_refptr<ROBuffer> buffer)
: ro_buffer_(std::move(buffer)), : ro_buffer_(std::move(buffer)),
position_of_block_(0), position_of_block_(0),
iter_(ro_buffer_.get()) {} iter_(ro_buffer_.get()) {}
...@@ -165,7 +165,7 @@ size_t ROBufferSegmentReader::GetSomeData(const char*& data, ...@@ -165,7 +165,7 @@ size_t ROBufferSegmentReader::GetSomeData(const char*& data,
} }
static void UnrefROBuffer(const void* ptr, void* context) { static void UnrefROBuffer(const void* ptr, void* context) {
static_cast<ROBuffer*>(context)->unref(); static_cast<ROBuffer*>(context)->Release();
} }
sk_sp<SkData> ROBufferSegmentReader::GetAsSkData() const { sk_sp<SkData> ROBufferSegmentReader::GetAsSkData() const {
...@@ -179,7 +179,7 @@ sk_sp<SkData> ROBufferSegmentReader::GetAsSkData() const { ...@@ -179,7 +179,7 @@ sk_sp<SkData> ROBufferSegmentReader::GetAsSkData() const {
if (!multiple_blocks) { if (!multiple_blocks) {
// Contiguous data. No need to copy. // Contiguous data. No need to copy.
ro_buffer_->ref(); ro_buffer_->AddRef();
return SkData::MakeWithProc(iter.data(), iter.size(), &UnrefROBuffer, return SkData::MakeWithProc(iter.data(), iter.size(), &UnrefROBuffer,
ro_buffer_.get()); ro_buffer_.get());
} }
...@@ -207,7 +207,7 @@ scoped_refptr<SegmentReader> SegmentReader::CreateFromSkData( ...@@ -207,7 +207,7 @@ scoped_refptr<SegmentReader> SegmentReader::CreateFromSkData(
} }
scoped_refptr<SegmentReader> SegmentReader::CreateFromROBuffer( scoped_refptr<SegmentReader> SegmentReader::CreateFromROBuffer(
sk_sp<ROBuffer> buffer) { scoped_refptr<ROBuffer> buffer) {
return base::AdoptRef(new ROBufferSegmentReader(std::move(buffer))); return base::AdoptRef(new ROBufferSegmentReader(std::move(buffer)));
} }
......
...@@ -41,7 +41,8 @@ class PLATFORM_EXPORT SegmentReader ...@@ -41,7 +41,8 @@ class PLATFORM_EXPORT SegmentReader
// These versions use thread-safe input, so they are always thread-safe. // These versions use thread-safe input, so they are always thread-safe.
static scoped_refptr<SegmentReader> CreateFromSkData(sk_sp<SkData>); static scoped_refptr<SegmentReader> CreateFromSkData(sk_sp<SkData>);
static scoped_refptr<SegmentReader> CreateFromROBuffer(sk_sp<ROBuffer>); static scoped_refptr<SegmentReader> CreateFromROBuffer(
scoped_refptr<ROBuffer>);
SegmentReader() = default; SegmentReader() = default;
virtual ~SegmentReader() = default; virtual ~SegmentReader() = default;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment