1/*
2 * Copyright 2019 Google LLC
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "src/gpu/GrClientMappedBufferManager.h"
9
10#include <algorithm>
11
12GrClientMappedBufferManager::GrClientMappedBufferManager(uint32_t contextID)
13 : fFinishedBufferInbox(contextID) {}
14
15GrClientMappedBufferManager::~GrClientMappedBufferManager() {
16 this->process();
17 if (!fAbandoned) {
18 // If we're going down before we got the messages we go ahead and unmap all the buffers.
19 // It's up to the client to ensure that they aren't being accessed on another thread while
20 // this is happening (or afterwards on any thread).
21 for (auto& b : fClientHeldBuffers) {
22 b->unmap();
23 }
24 }
25}
26
27void GrClientMappedBufferManager::insert(sk_sp<GrGpuBuffer> b) {
28 SkDEBUGCODE(auto end = fClientHeldBuffers.end());
29 SkASSERT(std::find(fClientHeldBuffers.begin(), end, b) == end);
30 fClientHeldBuffers.emplace_front(std::move(b));
31}
32
33void GrClientMappedBufferManager::process() {
34 SkSTArray<4, BufferFinishedMessage> messages;
35 fFinishedBufferInbox.poll(&messages);
36 if (!fAbandoned) {
37 for (auto& m : messages) {
38 this->remove(m.fBuffer);
39 m.fBuffer->unmap();
40 }
41 }
42}
43
44void GrClientMappedBufferManager::abandon() {
45 fAbandoned = true;
46 fClientHeldBuffers.clear();
47}
48
49void GrClientMappedBufferManager::remove(const sk_sp<GrGpuBuffer>& b) {
50 // There is no convenient remove only the first element that equals a value functionality in
51 // std::forward_list.
52 auto prev = fClientHeldBuffers.before_begin();
53 auto end = fClientHeldBuffers.end();
54 SkASSERT(std::find(fClientHeldBuffers.begin(), end, b) != end);
55 for (auto cur = fClientHeldBuffers.begin(); cur != end; prev = cur++) {
56 if (*cur == b) {
57 fClientHeldBuffers.erase_after(prev);
58 break;
59 }
60 }
61 SkASSERT(std::find(fClientHeldBuffers.begin(), end, b) == end);
62}
63
64//////////////////////////////////////////////////////////////////////////////
65
66DECLARE_SKMESSAGEBUS_MESSAGE(GrClientMappedBufferManager::BufferFinishedMessage)
67
68bool SkShouldPostMessageToBus(const GrClientMappedBufferManager::BufferFinishedMessage& m,
69 uint32_t msgBusUniqueID) {
70 return m.fInboxID == msgBusUniqueID;
71}
72