xref: /aosp_15_r20/external/skia/src/gpu/ganesh/GrRingBuffer.h (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1 /*
2  * Copyright 2020 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 #ifndef GrRingBuffer_DEFINED
9 #define GrRingBuffer_DEFINED
10 
11 #include "include/core/SkRefCnt.h"
12 #include "include/private/base/SkAssert.h"
13 #include "include/private/base/SkMath.h"
14 #include "src/gpu/ganesh/GrGpuBuffer.h"
15 
16 #include <cstddef>
17 #include <cstdint>
18 #include <vector>
19 
20 class GrGpu;
21 enum class GrGpuBufferType;
22 
23 /**
24  * A wrapper for a GPU buffer that allocates slices in a continuous ring.
25  *
26  * It's assumed that suballocate and startSubmit are always called in the same thread,
27  * and that finishSubmit could be called in a separate thread.
28  */
29 class GrRingBuffer {
30 public:
GrRingBuffer(GrGpu * gpu,size_t size,size_t alignment,GrGpuBufferType intendedType)31     GrRingBuffer(GrGpu* gpu, size_t size, size_t alignment, GrGpuBufferType intendedType)
32         : fGpu(gpu)
33         , fTotalSize(size)
34         , fAlignment(alignment)
35         , fType(intendedType)
36         , fNewAllocation(false)
37         , fHead(0)
38         , fTail(0)
39         , fGenID(0) {
40         // We increment fHead and fTail without bound and let overflow handle any wrapping.
41         // Because of this, size needs to be a power of two.
42         SkASSERT(SkIsPow2(size));
43     }
44 
45     struct Slice {
46         GrGpuBuffer* fBuffer;
47         size_t fOffset;
48     };
49     Slice suballocate(size_t size);
50 
51     // Backends should call startSubmit() at submit time
52     void startSubmit(GrGpu*);
53 
size()54     size_t size() const { return fTotalSize; }
55 
56 private:
57     size_t getAllocationOffset(size_t size);
58     struct SubmitData {
59         GrRingBuffer* fOwner;
60         size_t fLastHead;
61         size_t fGenID;
62     };
63     static void FinishSubmit(void*);
64 
65     GrGpu* fGpu;
66     sk_sp<GrGpuBuffer> fCurrentBuffer;
67     std::vector<sk_sp<GrGpuBuffer>> fPreviousBuffers; // previous buffers we've used in this submit
68     size_t fTotalSize;
69     size_t fAlignment;
70     GrGpuBufferType fType;
71     bool fNewAllocation; // true if there's been a new allocation in this submit
72     size_t fHead;        // where we start allocating
73     size_t fTail;        // where we start deallocating
74     uint64_t fGenID;     // incremented when createBuffer is called
75 };
76 
77 #endif
78