xref: /aosp_15_r20/frameworks/av/media/codec2/sfplugin/CCodecBuffers.h (revision ec779b8e0859a360c3d303172224686826e6e0e1)
1*ec779b8eSAndroid Build Coastguard Worker /*
2*ec779b8eSAndroid Build Coastguard Worker  * Copyright 2019, The Android Open Source Project
3*ec779b8eSAndroid Build Coastguard Worker  *
4*ec779b8eSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*ec779b8eSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*ec779b8eSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*ec779b8eSAndroid Build Coastguard Worker  *
8*ec779b8eSAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*ec779b8eSAndroid Build Coastguard Worker  *
10*ec779b8eSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*ec779b8eSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*ec779b8eSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*ec779b8eSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*ec779b8eSAndroid Build Coastguard Worker  * limitations under the License.
15*ec779b8eSAndroid Build Coastguard Worker  */
16*ec779b8eSAndroid Build Coastguard Worker 
17*ec779b8eSAndroid Build Coastguard Worker #ifndef CCODEC_BUFFERS_H_
18*ec779b8eSAndroid Build Coastguard Worker 
19*ec779b8eSAndroid Build Coastguard Worker #define CCODEC_BUFFERS_H_
20*ec779b8eSAndroid Build Coastguard Worker 
21*ec779b8eSAndroid Build Coastguard Worker #include <optional>
22*ec779b8eSAndroid Build Coastguard Worker #include <string>
23*ec779b8eSAndroid Build Coastguard Worker #include <vector>
24*ec779b8eSAndroid Build Coastguard Worker 
25*ec779b8eSAndroid Build Coastguard Worker #include <C2Config.h>
26*ec779b8eSAndroid Build Coastguard Worker #include <DataConverter.h>
27*ec779b8eSAndroid Build Coastguard Worker #include <media/stagefright/foundation/AMessage.h>
28*ec779b8eSAndroid Build Coastguard Worker #include <media/MediaCodecBuffer.h>
29*ec779b8eSAndroid Build Coastguard Worker 
30*ec779b8eSAndroid Build Coastguard Worker #include "Codec2Buffer.h"
31*ec779b8eSAndroid Build Coastguard Worker 
32*ec779b8eSAndroid Build Coastguard Worker namespace android {
33*ec779b8eSAndroid Build Coastguard Worker 
34*ec779b8eSAndroid Build Coastguard Worker struct ICrypto;
35*ec779b8eSAndroid Build Coastguard Worker class MemoryDealer;
36*ec779b8eSAndroid Build Coastguard Worker class SkipCutBuffer;
37*ec779b8eSAndroid Build Coastguard Worker class MultiAccessUnitSkipCutBuffer;
38*ec779b8eSAndroid Build Coastguard Worker struct AccessUnitInfo;
39*ec779b8eSAndroid Build Coastguard Worker 
40*ec779b8eSAndroid Build Coastguard Worker constexpr size_t kLinearBufferSize = 1048576;
41*ec779b8eSAndroid Build Coastguard Worker // This can fit an 8K frame.
42*ec779b8eSAndroid Build Coastguard Worker constexpr size_t kMaxLinearBufferSize = 7680 * 4320 * 2;
43*ec779b8eSAndroid Build Coastguard Worker 
44*ec779b8eSAndroid Build Coastguard Worker /**
45*ec779b8eSAndroid Build Coastguard Worker  * Base class for representation of buffers at one port.
46*ec779b8eSAndroid Build Coastguard Worker  */
47*ec779b8eSAndroid Build Coastguard Worker class CCodecBuffers {
48*ec779b8eSAndroid Build Coastguard Worker public:
49*ec779b8eSAndroid Build Coastguard Worker     CCodecBuffers(const char *componentName, const char *name = "Buffers")
mComponentName(componentName)50*ec779b8eSAndroid Build Coastguard Worker         : mComponentName(componentName),
51*ec779b8eSAndroid Build Coastguard Worker           mChannelName(std::string(componentName) + ":" + name),
52*ec779b8eSAndroid Build Coastguard Worker           mName(mChannelName.c_str()) {
53*ec779b8eSAndroid Build Coastguard Worker     }
54*ec779b8eSAndroid Build Coastguard Worker     virtual ~CCodecBuffers() = default;
55*ec779b8eSAndroid Build Coastguard Worker 
56*ec779b8eSAndroid Build Coastguard Worker     /**
57*ec779b8eSAndroid Build Coastguard Worker      * Set format for MediaCodec-facing buffers.
58*ec779b8eSAndroid Build Coastguard Worker      */
59*ec779b8eSAndroid Build Coastguard Worker     void setFormat(const sp<AMessage> &format);
60*ec779b8eSAndroid Build Coastguard Worker 
61*ec779b8eSAndroid Build Coastguard Worker     /**
62*ec779b8eSAndroid Build Coastguard Worker      * Return a copy of current format.
63*ec779b8eSAndroid Build Coastguard Worker      */
64*ec779b8eSAndroid Build Coastguard Worker     sp<AMessage> dupFormat();
65*ec779b8eSAndroid Build Coastguard Worker 
66*ec779b8eSAndroid Build Coastguard Worker     /**
67*ec779b8eSAndroid Build Coastguard Worker      * Returns true if the buffers are operating under array mode.
68*ec779b8eSAndroid Build Coastguard Worker      */
isArrayMode()69*ec779b8eSAndroid Build Coastguard Worker     virtual bool isArrayMode() const { return false; }
70*ec779b8eSAndroid Build Coastguard Worker 
71*ec779b8eSAndroid Build Coastguard Worker     /**
72*ec779b8eSAndroid Build Coastguard Worker      * Fills the vector with MediaCodecBuffer's if in array mode; otherwise,
73*ec779b8eSAndroid Build Coastguard Worker      * no-op.
74*ec779b8eSAndroid Build Coastguard Worker      */
getArray(Vector<sp<MediaCodecBuffer>> *)75*ec779b8eSAndroid Build Coastguard Worker     virtual void getArray(Vector<sp<MediaCodecBuffer>> *) const {}
76*ec779b8eSAndroid Build Coastguard Worker 
77*ec779b8eSAndroid Build Coastguard Worker     /**
78*ec779b8eSAndroid Build Coastguard Worker      * Return number of buffers owned by the client or the component.
79*ec779b8eSAndroid Build Coastguard Worker      */
80*ec779b8eSAndroid Build Coastguard Worker     virtual size_t numActiveSlots() const = 0;
81*ec779b8eSAndroid Build Coastguard Worker 
82*ec779b8eSAndroid Build Coastguard Worker     /**
83*ec779b8eSAndroid Build Coastguard Worker      * Examine image data from the buffer and update the format if necessary.
84*ec779b8eSAndroid Build Coastguard Worker      */
85*ec779b8eSAndroid Build Coastguard Worker     void handleImageData(const sp<Codec2Buffer> &buffer);
86*ec779b8eSAndroid Build Coastguard Worker 
87*ec779b8eSAndroid Build Coastguard Worker     /**
88*ec779b8eSAndroid Build Coastguard Worker      * Get the first pixel format of a metric session.
89*ec779b8eSAndroid Build Coastguard Worker      */
90*ec779b8eSAndroid Build Coastguard Worker     virtual uint32_t getPixelFormatIfApplicable();
91*ec779b8eSAndroid Build Coastguard Worker 
92*ec779b8eSAndroid Build Coastguard Worker     /**
93*ec779b8eSAndroid Build Coastguard Worker      * Reset the pixel format when a new metric session started.
94*ec779b8eSAndroid Build Coastguard Worker      */
95*ec779b8eSAndroid Build Coastguard Worker     virtual bool resetPixelFormatIfApplicable();
96*ec779b8eSAndroid Build Coastguard Worker 
97*ec779b8eSAndroid Build Coastguard Worker protected:
98*ec779b8eSAndroid Build Coastguard Worker     std::string mComponentName; ///< name of component for debugging
99*ec779b8eSAndroid Build Coastguard Worker     std::string mChannelName; ///< name of channel for debugging
100*ec779b8eSAndroid Build Coastguard Worker     const char *mName; ///< C-string version of channel name
101*ec779b8eSAndroid Build Coastguard Worker     // Format to be used for creating MediaCodec-facing buffers.
102*ec779b8eSAndroid Build Coastguard Worker     sp<AMessage> mFormat;
103*ec779b8eSAndroid Build Coastguard Worker 
104*ec779b8eSAndroid Build Coastguard Worker     sp<ABuffer> mLastImageData;
105*ec779b8eSAndroid Build Coastguard Worker     sp<AMessage> mFormatWithImageData;
106*ec779b8eSAndroid Build Coastguard Worker 
107*ec779b8eSAndroid Build Coastguard Worker private:
108*ec779b8eSAndroid Build Coastguard Worker     DISALLOW_EVIL_CONSTRUCTORS(CCodecBuffers);
109*ec779b8eSAndroid Build Coastguard Worker };
110*ec779b8eSAndroid Build Coastguard Worker 
111*ec779b8eSAndroid Build Coastguard Worker class InputBuffers : public CCodecBuffers {
112*ec779b8eSAndroid Build Coastguard Worker public:
113*ec779b8eSAndroid Build Coastguard Worker     InputBuffers(const char *componentName, const char *name = "Input[]")
CCodecBuffers(componentName,name)114*ec779b8eSAndroid Build Coastguard Worker         : CCodecBuffers(componentName, name) { }
115*ec779b8eSAndroid Build Coastguard Worker     virtual ~InputBuffers() = default;
116*ec779b8eSAndroid Build Coastguard Worker 
117*ec779b8eSAndroid Build Coastguard Worker     /**
118*ec779b8eSAndroid Build Coastguard Worker      * Set a block pool to obtain input memory blocks.
119*ec779b8eSAndroid Build Coastguard Worker      */
setPool(const std::shared_ptr<C2BlockPool> & pool)120*ec779b8eSAndroid Build Coastguard Worker     void setPool(const std::shared_ptr<C2BlockPool> &pool) { mPool = pool; }
121*ec779b8eSAndroid Build Coastguard Worker 
122*ec779b8eSAndroid Build Coastguard Worker     /**
123*ec779b8eSAndroid Build Coastguard Worker      * Get a new MediaCodecBuffer for input and its corresponding index.
124*ec779b8eSAndroid Build Coastguard Worker      * Returns false if no new buffer can be obtained at the moment.
125*ec779b8eSAndroid Build Coastguard Worker      */
126*ec779b8eSAndroid Build Coastguard Worker     virtual bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) = 0;
127*ec779b8eSAndroid Build Coastguard Worker 
128*ec779b8eSAndroid Build Coastguard Worker     /**
129*ec779b8eSAndroid Build Coastguard Worker      * Release the buffer obtained from requestNewBuffer() and get the
130*ec779b8eSAndroid Build Coastguard Worker      * associated C2Buffer object back. Returns true if the buffer was on file
131*ec779b8eSAndroid Build Coastguard Worker      * and released successfully.
132*ec779b8eSAndroid Build Coastguard Worker      */
133*ec779b8eSAndroid Build Coastguard Worker     virtual bool releaseBuffer(
134*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
135*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
136*ec779b8eSAndroid Build Coastguard Worker             bool release) = 0;
137*ec779b8eSAndroid Build Coastguard Worker 
138*ec779b8eSAndroid Build Coastguard Worker     /**
139*ec779b8eSAndroid Build Coastguard Worker      * Release the buffer that is no longer used by the codec process. Return
140*ec779b8eSAndroid Build Coastguard Worker      * true if and only if the buffer was on file and released successfully.
141*ec779b8eSAndroid Build Coastguard Worker      */
142*ec779b8eSAndroid Build Coastguard Worker     virtual bool expireComponentBuffer(
143*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) = 0;
144*ec779b8eSAndroid Build Coastguard Worker 
145*ec779b8eSAndroid Build Coastguard Worker     /**
146*ec779b8eSAndroid Build Coastguard Worker      * Flush internal state. After this call, no index or buffer previously
147*ec779b8eSAndroid Build Coastguard Worker      * returned from requestNewBuffer() is valid.
148*ec779b8eSAndroid Build Coastguard Worker      */
149*ec779b8eSAndroid Build Coastguard Worker     virtual void flush() = 0;
150*ec779b8eSAndroid Build Coastguard Worker 
151*ec779b8eSAndroid Build Coastguard Worker     /**
152*ec779b8eSAndroid Build Coastguard Worker      * Return array-backed version of input buffers. The returned object
153*ec779b8eSAndroid Build Coastguard Worker      * shall retain the internal state so that it will honor index and
154*ec779b8eSAndroid Build Coastguard Worker      * buffer from previous calls of requestNewBuffer().
155*ec779b8eSAndroid Build Coastguard Worker      */
156*ec779b8eSAndroid Build Coastguard Worker     virtual std::unique_ptr<InputBuffers> toArrayMode(size_t size) = 0;
157*ec779b8eSAndroid Build Coastguard Worker 
158*ec779b8eSAndroid Build Coastguard Worker     /**
159*ec779b8eSAndroid Build Coastguard Worker      * Release the buffer obtained from requestNewBuffer(), and create a deep
160*ec779b8eSAndroid Build Coastguard Worker      * copy clone of the buffer.
161*ec779b8eSAndroid Build Coastguard Worker      *
162*ec779b8eSAndroid Build Coastguard Worker      * \return  the deep copy clone of the buffer; nullptr if cloning is not
163*ec779b8eSAndroid Build Coastguard Worker      *          possible.
164*ec779b8eSAndroid Build Coastguard Worker      */
165*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> cloneAndReleaseBuffer(const sp<MediaCodecBuffer> &buffer);
166*ec779b8eSAndroid Build Coastguard Worker 
167*ec779b8eSAndroid Build Coastguard Worker protected:
168*ec779b8eSAndroid Build Coastguard Worker     virtual sp<Codec2Buffer> createNewBuffer() = 0;
169*ec779b8eSAndroid Build Coastguard Worker 
170*ec779b8eSAndroid Build Coastguard Worker     // Pool to obtain blocks for input buffers.
171*ec779b8eSAndroid Build Coastguard Worker     std::shared_ptr<C2BlockPool> mPool;
172*ec779b8eSAndroid Build Coastguard Worker 
173*ec779b8eSAndroid Build Coastguard Worker private:
174*ec779b8eSAndroid Build Coastguard Worker     DISALLOW_EVIL_CONSTRUCTORS(InputBuffers);
175*ec779b8eSAndroid Build Coastguard Worker };
176*ec779b8eSAndroid Build Coastguard Worker 
177*ec779b8eSAndroid Build Coastguard Worker class OutputBuffersArray;
178*ec779b8eSAndroid Build Coastguard Worker 
179*ec779b8eSAndroid Build Coastguard Worker class OutputBuffers : public CCodecBuffers {
180*ec779b8eSAndroid Build Coastguard Worker public:
181*ec779b8eSAndroid Build Coastguard Worker     OutputBuffers(const char *componentName, const char *name = "Output");
182*ec779b8eSAndroid Build Coastguard Worker     virtual ~OutputBuffers();
183*ec779b8eSAndroid Build Coastguard Worker 
184*ec779b8eSAndroid Build Coastguard Worker     /**
185*ec779b8eSAndroid Build Coastguard Worker      * Register output C2Buffer from the component and obtain corresponding
186*ec779b8eSAndroid Build Coastguard Worker      * index and MediaCodecBuffer object.
187*ec779b8eSAndroid Build Coastguard Worker      *
188*ec779b8eSAndroid Build Coastguard Worker      * Returns:
189*ec779b8eSAndroid Build Coastguard Worker      *   OK if registration succeeds.
190*ec779b8eSAndroid Build Coastguard Worker      *   NO_MEMORY if all buffers are available but not compatible.
191*ec779b8eSAndroid Build Coastguard Worker      *   WOULD_BLOCK if there are compatible buffers, but they are all in use.
192*ec779b8eSAndroid Build Coastguard Worker      */
193*ec779b8eSAndroid Build Coastguard Worker     virtual status_t registerBuffer(
194*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &buffer,
195*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
196*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> *clientBuffer) = 0;
197*ec779b8eSAndroid Build Coastguard Worker 
198*ec779b8eSAndroid Build Coastguard Worker     /**
199*ec779b8eSAndroid Build Coastguard Worker      * Register codec specific data as a buffer to be consistent with
200*ec779b8eSAndroid Build Coastguard Worker      * MediaCodec behavior.
201*ec779b8eSAndroid Build Coastguard Worker      */
202*ec779b8eSAndroid Build Coastguard Worker     virtual status_t registerCsd(
203*ec779b8eSAndroid Build Coastguard Worker             const C2StreamInitDataInfo::output * /* csd */,
204*ec779b8eSAndroid Build Coastguard Worker             size_t * /* index */,
205*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> * /* clientBuffer */) = 0;
206*ec779b8eSAndroid Build Coastguard Worker 
207*ec779b8eSAndroid Build Coastguard Worker     /**
208*ec779b8eSAndroid Build Coastguard Worker      * Release the buffer obtained from registerBuffer() and get the
209*ec779b8eSAndroid Build Coastguard Worker      * associated C2Buffer object back. Returns true if the buffer was on file
210*ec779b8eSAndroid Build Coastguard Worker      * and released successfully.
211*ec779b8eSAndroid Build Coastguard Worker      */
212*ec779b8eSAndroid Build Coastguard Worker     virtual bool releaseBuffer(
213*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer, std::shared_ptr<C2Buffer> *c2buffer) = 0;
214*ec779b8eSAndroid Build Coastguard Worker 
215*ec779b8eSAndroid Build Coastguard Worker     /**
216*ec779b8eSAndroid Build Coastguard Worker      * Flush internal state. After this call, no index or buffer previously
217*ec779b8eSAndroid Build Coastguard Worker      * returned from registerBuffer() is valid.
218*ec779b8eSAndroid Build Coastguard Worker      */
219*ec779b8eSAndroid Build Coastguard Worker     virtual void flush(const std::list<std::unique_ptr<C2Work>> &flushedWork) = 0;
220*ec779b8eSAndroid Build Coastguard Worker 
221*ec779b8eSAndroid Build Coastguard Worker     /**
222*ec779b8eSAndroid Build Coastguard Worker      * Return array-backed version of output buffers. The returned object
223*ec779b8eSAndroid Build Coastguard Worker      * shall retain the internal state so that it will honor index and
224*ec779b8eSAndroid Build Coastguard Worker      * buffer from previous calls of registerBuffer().
225*ec779b8eSAndroid Build Coastguard Worker      */
226*ec779b8eSAndroid Build Coastguard Worker     virtual std::unique_ptr<OutputBuffersArray> toArrayMode(size_t size) = 0;
227*ec779b8eSAndroid Build Coastguard Worker 
228*ec779b8eSAndroid Build Coastguard Worker     /**
229*ec779b8eSAndroid Build Coastguard Worker      * Initialize SkipCutBuffer object.
230*ec779b8eSAndroid Build Coastguard Worker      */
231*ec779b8eSAndroid Build Coastguard Worker     void initSkipCutBuffer(
232*ec779b8eSAndroid Build Coastguard Worker             int32_t delay, int32_t padding, int32_t sampleRate, int32_t channelCount);
233*ec779b8eSAndroid Build Coastguard Worker 
234*ec779b8eSAndroid Build Coastguard Worker     /**
235*ec779b8eSAndroid Build Coastguard Worker      * Update SkipCutBuffer from format. The @p format must not be null.
236*ec779b8eSAndroid Build Coastguard Worker      */
237*ec779b8eSAndroid Build Coastguard Worker     void updateSkipCutBuffer(const sp<AMessage> &format);
238*ec779b8eSAndroid Build Coastguard Worker 
239*ec779b8eSAndroid Build Coastguard Worker     /**
240*ec779b8eSAndroid Build Coastguard Worker      * Output Stash
241*ec779b8eSAndroid Build Coastguard Worker      * ============
242*ec779b8eSAndroid Build Coastguard Worker      *
243*ec779b8eSAndroid Build Coastguard Worker      * The output stash is a place to hold output buffers temporarily before
244*ec779b8eSAndroid Build Coastguard Worker      * they are registered to output slots. It has 2 main functions:
245*ec779b8eSAndroid Build Coastguard Worker      * 1. Allow reordering of output frames as the codec may produce frames in a
246*ec779b8eSAndroid Build Coastguard Worker      *    different order.
247*ec779b8eSAndroid Build Coastguard Worker      * 2. Act as a "buffer" between the codec and the client because the codec
248*ec779b8eSAndroid Build Coastguard Worker      *    may produce more buffers than available slots. This excess of codec's
249*ec779b8eSAndroid Build Coastguard Worker      *    output buffers should be registered to slots later, after the client
250*ec779b8eSAndroid Build Coastguard Worker      *    has released some slots.
251*ec779b8eSAndroid Build Coastguard Worker      *
252*ec779b8eSAndroid Build Coastguard Worker      * The stash consists of 2 lists of buffers: mPending and mReorderStash.
253*ec779b8eSAndroid Build Coastguard Worker      * mPending is a normal FIFO queue with not size limit, while mReorderStash
254*ec779b8eSAndroid Build Coastguard Worker      * is a sorted list with size limit mDepth.
255*ec779b8eSAndroid Build Coastguard Worker      *
256*ec779b8eSAndroid Build Coastguard Worker      * The normal flow of a non-csd output buffer is as follows:
257*ec779b8eSAndroid Build Coastguard Worker      *
258*ec779b8eSAndroid Build Coastguard Worker      *           |----------------OutputBuffers---------------|
259*ec779b8eSAndroid Build Coastguard Worker      *           |----------Output stash----------|           |
260*ec779b8eSAndroid Build Coastguard Worker      *   Codec --|-> mReorderStash --> mPending --|-> slots --|-> client
261*ec779b8eSAndroid Build Coastguard Worker      *           |                                |           |
262*ec779b8eSAndroid Build Coastguard Worker      *     pushToStash()                    popFromStashAndRegister()
263*ec779b8eSAndroid Build Coastguard Worker      *
264*ec779b8eSAndroid Build Coastguard Worker      * The buffer that comes from the codec first enters mReorderStash. The
265*ec779b8eSAndroid Build Coastguard Worker      * first buffer in mReorderStash gets moved to mPending when mReorderStash
266*ec779b8eSAndroid Build Coastguard Worker      * overflows. Buffers in mPending are registered to slots and given to the
267*ec779b8eSAndroid Build Coastguard Worker      * client as soon as slots are available.
268*ec779b8eSAndroid Build Coastguard Worker      *
269*ec779b8eSAndroid Build Coastguard Worker      * Every output buffer that is not a csd buffer should be put on the stash
270*ec779b8eSAndroid Build Coastguard Worker      * by calling pushToStash(), then later registered to a slot by calling
271*ec779b8eSAndroid Build Coastguard Worker      * popFromStashAndRegister() before notifying the client with
272*ec779b8eSAndroid Build Coastguard Worker      * onOutputBufferAvailable().
273*ec779b8eSAndroid Build Coastguard Worker      *
274*ec779b8eSAndroid Build Coastguard Worker      * Reordering
275*ec779b8eSAndroid Build Coastguard Worker      * ==========
276*ec779b8eSAndroid Build Coastguard Worker      *
277*ec779b8eSAndroid Build Coastguard Worker      * mReorderStash is a sorted list with a specified size limit. The size
278*ec779b8eSAndroid Build Coastguard Worker      * limit can be set by calling setReorderDepth().
279*ec779b8eSAndroid Build Coastguard Worker      *
280*ec779b8eSAndroid Build Coastguard Worker      * Every buffer in mReorderStash has a C2WorkOrdinalStruct, which contains 3
281*ec779b8eSAndroid Build Coastguard Worker      * members, all of which are comparable. Which member of C2WorkOrdinalStruct
282*ec779b8eSAndroid Build Coastguard Worker      * should be used for reordering can be chosen by calling setReorderKey().
283*ec779b8eSAndroid Build Coastguard Worker      */
284*ec779b8eSAndroid Build Coastguard Worker 
285*ec779b8eSAndroid Build Coastguard Worker     /**
286*ec779b8eSAndroid Build Coastguard Worker      * Return the reorder depth---the size of mReorderStash.
287*ec779b8eSAndroid Build Coastguard Worker      */
288*ec779b8eSAndroid Build Coastguard Worker     uint32_t getReorderDepth() const;
289*ec779b8eSAndroid Build Coastguard Worker 
290*ec779b8eSAndroid Build Coastguard Worker     /**
291*ec779b8eSAndroid Build Coastguard Worker      * Set the reorder depth.
292*ec779b8eSAndroid Build Coastguard Worker      */
293*ec779b8eSAndroid Build Coastguard Worker     void setReorderDepth(uint32_t depth);
294*ec779b8eSAndroid Build Coastguard Worker 
295*ec779b8eSAndroid Build Coastguard Worker     /**
296*ec779b8eSAndroid Build Coastguard Worker      * Set the type of "key" to use in comparisons.
297*ec779b8eSAndroid Build Coastguard Worker      */
298*ec779b8eSAndroid Build Coastguard Worker     void setReorderKey(C2Config::ordinal_key_t key);
299*ec779b8eSAndroid Build Coastguard Worker 
300*ec779b8eSAndroid Build Coastguard Worker     /**
301*ec779b8eSAndroid Build Coastguard Worker      * Return whether the output stash has any pending buffers.
302*ec779b8eSAndroid Build Coastguard Worker      */
303*ec779b8eSAndroid Build Coastguard Worker     bool hasPending() const;
304*ec779b8eSAndroid Build Coastguard Worker 
305*ec779b8eSAndroid Build Coastguard Worker     /**
306*ec779b8eSAndroid Build Coastguard Worker      * Flush the stash and reset the depth and the key to their default values.
307*ec779b8eSAndroid Build Coastguard Worker      */
308*ec779b8eSAndroid Build Coastguard Worker     void clearStash();
309*ec779b8eSAndroid Build Coastguard Worker 
310*ec779b8eSAndroid Build Coastguard Worker     /**
311*ec779b8eSAndroid Build Coastguard Worker      * Flush the stash.
312*ec779b8eSAndroid Build Coastguard Worker      */
313*ec779b8eSAndroid Build Coastguard Worker     void flushStash();
314*ec779b8eSAndroid Build Coastguard Worker 
315*ec779b8eSAndroid Build Coastguard Worker     /**
316*ec779b8eSAndroid Build Coastguard Worker      * Push a buffer to the reorder stash.
317*ec779b8eSAndroid Build Coastguard Worker      *
318*ec779b8eSAndroid Build Coastguard Worker      * @param buffer    C2Buffer object from the returned work.
319*ec779b8eSAndroid Build Coastguard Worker      * @param notify    Whether the returned work contains a buffer that should
320*ec779b8eSAndroid Build Coastguard Worker      *                  be reported to the client. This may be false if the
321*ec779b8eSAndroid Build Coastguard Worker      *                  caller wants to process the buffer without notifying the
322*ec779b8eSAndroid Build Coastguard Worker      *                  client.
323*ec779b8eSAndroid Build Coastguard Worker      * @param timestamp Buffer timestamp to report to the client.
324*ec779b8eSAndroid Build Coastguard Worker      * @param flags     Buffer flags to report to the client.
325*ec779b8eSAndroid Build Coastguard Worker      * @param format    Buffer format to report to the client.
326*ec779b8eSAndroid Build Coastguard Worker      * @param ordinal   Ordinal used in reordering. This determines when the
327*ec779b8eSAndroid Build Coastguard Worker      *                  buffer will be popped from the output stash by
328*ec779b8eSAndroid Build Coastguard Worker      *                  `popFromStashAndRegister()`.
329*ec779b8eSAndroid Build Coastguard Worker      */
330*ec779b8eSAndroid Build Coastguard Worker     void pushToStash(
331*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer>& buffer,
332*ec779b8eSAndroid Build Coastguard Worker             bool notify,
333*ec779b8eSAndroid Build Coastguard Worker             int64_t timestamp,
334*ec779b8eSAndroid Build Coastguard Worker             int32_t flags,
335*ec779b8eSAndroid Build Coastguard Worker             const sp<AMessage>& format,
336*ec779b8eSAndroid Build Coastguard Worker             const C2WorkOrdinalStruct& ordinal);
337*ec779b8eSAndroid Build Coastguard Worker 
338*ec779b8eSAndroid Build Coastguard Worker     enum BufferAction : int {
339*ec779b8eSAndroid Build Coastguard Worker         SKIP,
340*ec779b8eSAndroid Build Coastguard Worker         DISCARD,
341*ec779b8eSAndroid Build Coastguard Worker         NOTIFY_CLIENT,
342*ec779b8eSAndroid Build Coastguard Worker         REALLOCATE,
343*ec779b8eSAndroid Build Coastguard Worker         RETRY,
344*ec779b8eSAndroid Build Coastguard Worker     };
345*ec779b8eSAndroid Build Coastguard Worker 
346*ec779b8eSAndroid Build Coastguard Worker     /**
347*ec779b8eSAndroid Build Coastguard Worker      * Try to atomically pop the first buffer from the reorder stash and
348*ec779b8eSAndroid Build Coastguard Worker      * register it to an output slot. The function returns a value that
349*ec779b8eSAndroid Build Coastguard Worker      * indicates a recommended course of action for the caller.
350*ec779b8eSAndroid Build Coastguard Worker      *
351*ec779b8eSAndroid Build Coastguard Worker      * If the stash is empty, the function will return `SKIP`.
352*ec779b8eSAndroid Build Coastguard Worker      *
353*ec779b8eSAndroid Build Coastguard Worker      * If the stash is not empty, the function will peek at the first (oldest)
354*ec779b8eSAndroid Build Coastguard Worker      * entry in mPending process the buffer in the entry as follows:
355*ec779b8eSAndroid Build Coastguard Worker      * - If the buffer should not be sent to the client, the function will
356*ec779b8eSAndroid Build Coastguard Worker      *   return `DISCARD`. The stash entry will be removed.
357*ec779b8eSAndroid Build Coastguard Worker      * - If the buffer should be sent to the client, the function will attempt
358*ec779b8eSAndroid Build Coastguard Worker      *   to register the buffer to a slot. The registration may have 3 outcomes
359*ec779b8eSAndroid Build Coastguard Worker      *   corresponding to the following return values:
360*ec779b8eSAndroid Build Coastguard Worker      *   - `NOTIFY_CLIENT`: The buffer is successfully registered to a slot. The
361*ec779b8eSAndroid Build Coastguard Worker      *     output arguments @p index and @p outBuffer will contain valid values
362*ec779b8eSAndroid Build Coastguard Worker      *     that the caller can use to call onOutputBufferAvailable(). The stash
363*ec779b8eSAndroid Build Coastguard Worker      *     entry will be removed.
364*ec779b8eSAndroid Build Coastguard Worker      *   - `REALLOCATE`: The buffer is not registered because it is not
365*ec779b8eSAndroid Build Coastguard Worker      *     compatible with the current slots (which are available). The caller
366*ec779b8eSAndroid Build Coastguard Worker      *     should reallocate the OutputBuffers with slots that can fit the
367*ec779b8eSAndroid Build Coastguard Worker      *     returned @p c2Buffer. The stash entry will not be removed
368*ec779b8eSAndroid Build Coastguard Worker      *   - `RETRY`: All slots are currently occupied by the client. The caller
369*ec779b8eSAndroid Build Coastguard Worker      *     should try to call this function again after the client has released
370*ec779b8eSAndroid Build Coastguard Worker      *     some slots.
371*ec779b8eSAndroid Build Coastguard Worker      *
372*ec779b8eSAndroid Build Coastguard Worker      * @return What the caller should do afterwards.
373*ec779b8eSAndroid Build Coastguard Worker      *
374*ec779b8eSAndroid Build Coastguard Worker      * @param[out] c2Buffer   Underlying C2Buffer associated to the first buffer
375*ec779b8eSAndroid Build Coastguard Worker      *                        on the stash. This value is guaranteed to be valid
376*ec779b8eSAndroid Build Coastguard Worker      *                        unless the return value is `SKIP`.
377*ec779b8eSAndroid Build Coastguard Worker      * @param[out] index      Slot index. This value is valid only if the return
378*ec779b8eSAndroid Build Coastguard Worker      *                        value is `NOTIFY_CLIENT`.
379*ec779b8eSAndroid Build Coastguard Worker      * @param[out] outBuffer  Registered buffer. This value is valid only if the
380*ec779b8eSAndroid Build Coastguard Worker      *                        return valu is `NOTIFY_CLIENT`.
381*ec779b8eSAndroid Build Coastguard Worker      */
382*ec779b8eSAndroid Build Coastguard Worker     BufferAction popFromStashAndRegister(
383*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer>* c2Buffer,
384*ec779b8eSAndroid Build Coastguard Worker             size_t* index,
385*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer>* outBuffer);
386*ec779b8eSAndroid Build Coastguard Worker 
387*ec779b8eSAndroid Build Coastguard Worker protected:
388*ec779b8eSAndroid Build Coastguard Worker 
389*ec779b8eSAndroid Build Coastguard Worker     sp<MultiAccessUnitSkipCutBuffer> mSkipCutBuffer;
390*ec779b8eSAndroid Build Coastguard Worker 
391*ec779b8eSAndroid Build Coastguard Worker     /**
392*ec779b8eSAndroid Build Coastguard Worker      * Update the SkipCutBuffer object. No-op if it's never initialized.
393*ec779b8eSAndroid Build Coastguard Worker      */
394*ec779b8eSAndroid Build Coastguard Worker     void updateSkipCutBuffer(int32_t sampleRate, int32_t channelCount);
395*ec779b8eSAndroid Build Coastguard Worker 
396*ec779b8eSAndroid Build Coastguard Worker     bool submit(const sp<MediaCodecBuffer> &buffer, int32_t sampleRate,
397*ec779b8eSAndroid Build Coastguard Worker             int32_t channelCount, std::shared_ptr<const C2AccessUnitInfos::output> &infos);
398*ec779b8eSAndroid Build Coastguard Worker 
399*ec779b8eSAndroid Build Coastguard Worker     /**
400*ec779b8eSAndroid Build Coastguard Worker      * Submit buffer to SkipCutBuffer object, if initialized.
401*ec779b8eSAndroid Build Coastguard Worker      */
402*ec779b8eSAndroid Build Coastguard Worker     void submit(const sp<MediaCodecBuffer> &buffer);
403*ec779b8eSAndroid Build Coastguard Worker 
404*ec779b8eSAndroid Build Coastguard Worker     /**
405*ec779b8eSAndroid Build Coastguard Worker      * Apply DataConverter from |src| to |*dst| if needed. If |*dst| is nullptr,
406*ec779b8eSAndroid Build Coastguard Worker      * a new buffer is allocated.
407*ec779b8eSAndroid Build Coastguard Worker      *
408*ec779b8eSAndroid Build Coastguard Worker      * Returns true if conversion was needed and executed; false otherwise.
409*ec779b8eSAndroid Build Coastguard Worker      */
410*ec779b8eSAndroid Build Coastguard Worker     bool convert(const std::shared_ptr<C2Buffer> &src, sp<Codec2Buffer> *dst);
411*ec779b8eSAndroid Build Coastguard Worker 
412*ec779b8eSAndroid Build Coastguard Worker private:
413*ec779b8eSAndroid Build Coastguard Worker     // SkipCutBuffer
414*ec779b8eSAndroid Build Coastguard Worker     int32_t mDelay;
415*ec779b8eSAndroid Build Coastguard Worker     int32_t mPadding;
416*ec779b8eSAndroid Build Coastguard Worker     int32_t mSampleRate;
417*ec779b8eSAndroid Build Coastguard Worker     int32_t mChannelCount;
418*ec779b8eSAndroid Build Coastguard Worker 
419*ec779b8eSAndroid Build Coastguard Worker     void setSkipCutBuffer(int32_t skip, int32_t cut);
420*ec779b8eSAndroid Build Coastguard Worker 
421*ec779b8eSAndroid Build Coastguard Worker     // DataConverter
422*ec779b8eSAndroid Build Coastguard Worker     sp<DataConverter> mDataConverter;
423*ec779b8eSAndroid Build Coastguard Worker     sp<AMessage> mFormatWithConverter;
424*ec779b8eSAndroid Build Coastguard Worker     std::optional<int32_t> mSrcEncoding;
425*ec779b8eSAndroid Build Coastguard Worker     std::optional<int32_t> mDstEncoding;
426*ec779b8eSAndroid Build Coastguard Worker 
427*ec779b8eSAndroid Build Coastguard Worker     // Output stash
428*ec779b8eSAndroid Build Coastguard Worker 
429*ec779b8eSAndroid Build Coastguard Worker     // Struct for an entry in the output stash (mPending and mReorderStash)
430*ec779b8eSAndroid Build Coastguard Worker     struct StashEntry {
StashEntryStashEntry431*ec779b8eSAndroid Build Coastguard Worker         inline StashEntry()
432*ec779b8eSAndroid Build Coastguard Worker             : buffer(nullptr),
433*ec779b8eSAndroid Build Coastguard Worker               notify(false),
434*ec779b8eSAndroid Build Coastguard Worker               timestamp(0),
435*ec779b8eSAndroid Build Coastguard Worker               flags(0),
436*ec779b8eSAndroid Build Coastguard Worker               format(),
437*ec779b8eSAndroid Build Coastguard Worker               ordinal({0, 0, 0}) {}
StashEntryStashEntry438*ec779b8eSAndroid Build Coastguard Worker         inline StashEntry(
439*ec779b8eSAndroid Build Coastguard Worker                 const std::shared_ptr<C2Buffer> &b,
440*ec779b8eSAndroid Build Coastguard Worker                 bool n,
441*ec779b8eSAndroid Build Coastguard Worker                 int64_t t,
442*ec779b8eSAndroid Build Coastguard Worker                 int32_t f,
443*ec779b8eSAndroid Build Coastguard Worker                 const sp<AMessage> &fmt,
444*ec779b8eSAndroid Build Coastguard Worker                 const C2WorkOrdinalStruct &o)
445*ec779b8eSAndroid Build Coastguard Worker             : buffer(b),
446*ec779b8eSAndroid Build Coastguard Worker               notify(n),
447*ec779b8eSAndroid Build Coastguard Worker               timestamp(t),
448*ec779b8eSAndroid Build Coastguard Worker               flags(f),
449*ec779b8eSAndroid Build Coastguard Worker               format(fmt),
450*ec779b8eSAndroid Build Coastguard Worker               ordinal(o) {}
451*ec779b8eSAndroid Build Coastguard Worker         std::shared_ptr<C2Buffer> buffer;
452*ec779b8eSAndroid Build Coastguard Worker         bool notify;
453*ec779b8eSAndroid Build Coastguard Worker         int64_t timestamp;
454*ec779b8eSAndroid Build Coastguard Worker         int32_t flags;
455*ec779b8eSAndroid Build Coastguard Worker         sp<AMessage> format;
456*ec779b8eSAndroid Build Coastguard Worker         C2WorkOrdinalStruct ordinal;
457*ec779b8eSAndroid Build Coastguard Worker     };
458*ec779b8eSAndroid Build Coastguard Worker 
459*ec779b8eSAndroid Build Coastguard Worker     /**
460*ec779b8eSAndroid Build Coastguard Worker      * FIFO queue of stash entries.
461*ec779b8eSAndroid Build Coastguard Worker      */
462*ec779b8eSAndroid Build Coastguard Worker     std::list<StashEntry> mPending;
463*ec779b8eSAndroid Build Coastguard Worker     /**
464*ec779b8eSAndroid Build Coastguard Worker      * Sorted list of stash entries.
465*ec779b8eSAndroid Build Coastguard Worker      */
466*ec779b8eSAndroid Build Coastguard Worker     std::list<StashEntry> mReorderStash;
467*ec779b8eSAndroid Build Coastguard Worker     /**
468*ec779b8eSAndroid Build Coastguard Worker      * Size limit of mReorderStash.
469*ec779b8eSAndroid Build Coastguard Worker      */
470*ec779b8eSAndroid Build Coastguard Worker     uint32_t mDepth{0};
471*ec779b8eSAndroid Build Coastguard Worker     /**
472*ec779b8eSAndroid Build Coastguard Worker      * Choice of key to use in ordering of stash entries in mReorderStash.
473*ec779b8eSAndroid Build Coastguard Worker      */
474*ec779b8eSAndroid Build Coastguard Worker     C2Config::ordinal_key_t mKey{C2Config::ORDINAL};
475*ec779b8eSAndroid Build Coastguard Worker 
476*ec779b8eSAndroid Build Coastguard Worker     /**
477*ec779b8eSAndroid Build Coastguard Worker      * Return false if mPending is empty; otherwise, pop the first entry from
478*ec779b8eSAndroid Build Coastguard Worker      * mPending and return true.
479*ec779b8eSAndroid Build Coastguard Worker      */
480*ec779b8eSAndroid Build Coastguard Worker     bool popPending(StashEntry *entry);
481*ec779b8eSAndroid Build Coastguard Worker 
482*ec779b8eSAndroid Build Coastguard Worker     /**
483*ec779b8eSAndroid Build Coastguard Worker      * Push an entry as the first entry of mPending.
484*ec779b8eSAndroid Build Coastguard Worker      */
485*ec779b8eSAndroid Build Coastguard Worker     void deferPending(const StashEntry &entry);
486*ec779b8eSAndroid Build Coastguard Worker 
487*ec779b8eSAndroid Build Coastguard Worker     /**
488*ec779b8eSAndroid Build Coastguard Worker      * Comparison of C2WorkOrdinalStruct based on mKey.
489*ec779b8eSAndroid Build Coastguard Worker      */
490*ec779b8eSAndroid Build Coastguard Worker     bool less(const C2WorkOrdinalStruct &o1,
491*ec779b8eSAndroid Build Coastguard Worker               const C2WorkOrdinalStruct &o2) const;
492*ec779b8eSAndroid Build Coastguard Worker 
493*ec779b8eSAndroid Build Coastguard Worker     DISALLOW_EVIL_CONSTRUCTORS(OutputBuffers);
494*ec779b8eSAndroid Build Coastguard Worker 
495*ec779b8eSAndroid Build Coastguard Worker     friend OutputBuffersArray;
496*ec779b8eSAndroid Build Coastguard Worker };
497*ec779b8eSAndroid Build Coastguard Worker 
498*ec779b8eSAndroid Build Coastguard Worker /**
499*ec779b8eSAndroid Build Coastguard Worker  * Simple local buffer pool backed by std::vector.
500*ec779b8eSAndroid Build Coastguard Worker  */
501*ec779b8eSAndroid Build Coastguard Worker class LocalBufferPool : public std::enable_shared_from_this<LocalBufferPool> {
502*ec779b8eSAndroid Build Coastguard Worker public:
503*ec779b8eSAndroid Build Coastguard Worker     /**
504*ec779b8eSAndroid Build Coastguard Worker      * Create a new LocalBufferPool object.
505*ec779b8eSAndroid Build Coastguard Worker      *
506*ec779b8eSAndroid Build Coastguard Worker      * \return  a newly created pool object.
507*ec779b8eSAndroid Build Coastguard Worker      */
508*ec779b8eSAndroid Build Coastguard Worker     static std::shared_ptr<LocalBufferPool> Create();
509*ec779b8eSAndroid Build Coastguard Worker 
510*ec779b8eSAndroid Build Coastguard Worker     /**
511*ec779b8eSAndroid Build Coastguard Worker      * Return an ABuffer object whose size is at least |capacity|.
512*ec779b8eSAndroid Build Coastguard Worker      *
513*ec779b8eSAndroid Build Coastguard Worker      * \param   capacity  requested capacity
514*ec779b8eSAndroid Build Coastguard Worker      * \return  nullptr if the pool capacity is reached
515*ec779b8eSAndroid Build Coastguard Worker      *          an ABuffer object otherwise.
516*ec779b8eSAndroid Build Coastguard Worker      */
517*ec779b8eSAndroid Build Coastguard Worker     sp<ABuffer> newBuffer(size_t capacity);
518*ec779b8eSAndroid Build Coastguard Worker 
519*ec779b8eSAndroid Build Coastguard Worker private:
520*ec779b8eSAndroid Build Coastguard Worker     /**
521*ec779b8eSAndroid Build Coastguard Worker      * ABuffer backed by std::vector.
522*ec779b8eSAndroid Build Coastguard Worker      */
523*ec779b8eSAndroid Build Coastguard Worker     class VectorBuffer : public ::android::ABuffer {
524*ec779b8eSAndroid Build Coastguard Worker     public:
525*ec779b8eSAndroid Build Coastguard Worker         /**
526*ec779b8eSAndroid Build Coastguard Worker          * Construct a VectorBuffer by taking the ownership of supplied vector.
527*ec779b8eSAndroid Build Coastguard Worker          *
528*ec779b8eSAndroid Build Coastguard Worker          * \param vec   backing vector of the buffer. this object takes
529*ec779b8eSAndroid Build Coastguard Worker          *              ownership at construction.
530*ec779b8eSAndroid Build Coastguard Worker          * \param pool  a LocalBufferPool object to return the vector at
531*ec779b8eSAndroid Build Coastguard Worker          *              destruction.
532*ec779b8eSAndroid Build Coastguard Worker          */
533*ec779b8eSAndroid Build Coastguard Worker         VectorBuffer(std::vector<uint8_t> &&vec, const std::shared_ptr<LocalBufferPool> &pool);
534*ec779b8eSAndroid Build Coastguard Worker 
535*ec779b8eSAndroid Build Coastguard Worker         ~VectorBuffer() override;
536*ec779b8eSAndroid Build Coastguard Worker 
537*ec779b8eSAndroid Build Coastguard Worker     private:
538*ec779b8eSAndroid Build Coastguard Worker         std::vector<uint8_t> mVec;
539*ec779b8eSAndroid Build Coastguard Worker         std::weak_ptr<LocalBufferPool> mPool;
540*ec779b8eSAndroid Build Coastguard Worker     };
541*ec779b8eSAndroid Build Coastguard Worker 
542*ec779b8eSAndroid Build Coastguard Worker     Mutex mMutex;
543*ec779b8eSAndroid Build Coastguard Worker     size_t mPoolCapacity;
544*ec779b8eSAndroid Build Coastguard Worker     size_t mUsedSize;
545*ec779b8eSAndroid Build Coastguard Worker     std::list<std::vector<uint8_t>> mPool;
546*ec779b8eSAndroid Build Coastguard Worker 
547*ec779b8eSAndroid Build Coastguard Worker     /**
548*ec779b8eSAndroid Build Coastguard Worker      * Private constructor to prevent constructing non-managed LocalBufferPool.
549*ec779b8eSAndroid Build Coastguard Worker      */
LocalBufferPool(size_t poolCapacity)550*ec779b8eSAndroid Build Coastguard Worker     explicit LocalBufferPool(size_t poolCapacity)
551*ec779b8eSAndroid Build Coastguard Worker         : mPoolCapacity(poolCapacity), mUsedSize(0) {
552*ec779b8eSAndroid Build Coastguard Worker     }
553*ec779b8eSAndroid Build Coastguard Worker 
554*ec779b8eSAndroid Build Coastguard Worker     /**
555*ec779b8eSAndroid Build Coastguard Worker      * Take back the ownership of vec from the destructed VectorBuffer and put
556*ec779b8eSAndroid Build Coastguard Worker      * it in front of the pool.
557*ec779b8eSAndroid Build Coastguard Worker      */
558*ec779b8eSAndroid Build Coastguard Worker     void returnVector(std::vector<uint8_t> &&vec);
559*ec779b8eSAndroid Build Coastguard Worker 
560*ec779b8eSAndroid Build Coastguard Worker     DISALLOW_EVIL_CONSTRUCTORS(LocalBufferPool);
561*ec779b8eSAndroid Build Coastguard Worker };
562*ec779b8eSAndroid Build Coastguard Worker 
563*ec779b8eSAndroid Build Coastguard Worker class BuffersArrayImpl;
564*ec779b8eSAndroid Build Coastguard Worker 
565*ec779b8eSAndroid Build Coastguard Worker /**
566*ec779b8eSAndroid Build Coastguard Worker  * Flexible buffer slots implementation.
567*ec779b8eSAndroid Build Coastguard Worker  */
568*ec779b8eSAndroid Build Coastguard Worker class FlexBuffersImpl {
569*ec779b8eSAndroid Build Coastguard Worker public:
FlexBuffersImpl(const char * name)570*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl(const char *name)
571*ec779b8eSAndroid Build Coastguard Worker         : mImplName(std::string(name) + ".Impl"),
572*ec779b8eSAndroid Build Coastguard Worker           mName(mImplName.c_str()) { }
573*ec779b8eSAndroid Build Coastguard Worker 
574*ec779b8eSAndroid Build Coastguard Worker     /**
575*ec779b8eSAndroid Build Coastguard Worker      * Assign an empty slot for a buffer and return the index. If there's no
576*ec779b8eSAndroid Build Coastguard Worker      * empty slot, just add one at the end and return it.
577*ec779b8eSAndroid Build Coastguard Worker      *
578*ec779b8eSAndroid Build Coastguard Worker      * \param buffer[in]  a new buffer to assign a slot.
579*ec779b8eSAndroid Build Coastguard Worker      * \return            index of the assigned slot.
580*ec779b8eSAndroid Build Coastguard Worker      */
581*ec779b8eSAndroid Build Coastguard Worker     size_t assignSlot(const sp<Codec2Buffer> &buffer);
582*ec779b8eSAndroid Build Coastguard Worker 
583*ec779b8eSAndroid Build Coastguard Worker     /**
584*ec779b8eSAndroid Build Coastguard Worker      * Release the slot from the client, and get the C2Buffer object back from
585*ec779b8eSAndroid Build Coastguard Worker      * the previously assigned buffer. Note that the slot is not completely free
586*ec779b8eSAndroid Build Coastguard Worker      * until the returned C2Buffer object is freed.
587*ec779b8eSAndroid Build Coastguard Worker      *
588*ec779b8eSAndroid Build Coastguard Worker      * \param   buffer[in]        the buffer previously assigned a slot.
589*ec779b8eSAndroid Build Coastguard Worker      * \param   c2buffer[in,out]  pointer to C2Buffer to be populated. Ignored
590*ec779b8eSAndroid Build Coastguard Worker      *                            if null.
591*ec779b8eSAndroid Build Coastguard Worker      * \return  true  if the buffer is successfully released from a slot
592*ec779b8eSAndroid Build Coastguard Worker      *          false otherwise
593*ec779b8eSAndroid Build Coastguard Worker      */
594*ec779b8eSAndroid Build Coastguard Worker     bool releaseSlot(
595*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
596*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
597*ec779b8eSAndroid Build Coastguard Worker             bool release);
598*ec779b8eSAndroid Build Coastguard Worker 
599*ec779b8eSAndroid Build Coastguard Worker     /**
600*ec779b8eSAndroid Build Coastguard Worker      * Expire the C2Buffer object in the slot.
601*ec779b8eSAndroid Build Coastguard Worker      *
602*ec779b8eSAndroid Build Coastguard Worker      * \param   c2buffer[in]  C2Buffer object which the component released.
603*ec779b8eSAndroid Build Coastguard Worker      * \return  true  if the buffer is found in one of the slots and
604*ec779b8eSAndroid Build Coastguard Worker      *                successfully released
605*ec779b8eSAndroid Build Coastguard Worker      *          false otherwise
606*ec779b8eSAndroid Build Coastguard Worker      */
607*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(const std::shared_ptr<C2Buffer> &c2buffer);
608*ec779b8eSAndroid Build Coastguard Worker 
609*ec779b8eSAndroid Build Coastguard Worker     /**
610*ec779b8eSAndroid Build Coastguard Worker      * The client abandoned all known buffers, so reclaim the ownership.
611*ec779b8eSAndroid Build Coastguard Worker      */
612*ec779b8eSAndroid Build Coastguard Worker     void flush();
613*ec779b8eSAndroid Build Coastguard Worker 
614*ec779b8eSAndroid Build Coastguard Worker     /**
615*ec779b8eSAndroid Build Coastguard Worker      * Return the number of buffers that are sent to the client or the component.
616*ec779b8eSAndroid Build Coastguard Worker      */
617*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const;
618*ec779b8eSAndroid Build Coastguard Worker 
619*ec779b8eSAndroid Build Coastguard Worker     /**
620*ec779b8eSAndroid Build Coastguard Worker      * Return the number of buffers that are sent to the component but not
621*ec779b8eSAndroid Build Coastguard Worker      * returned back yet.
622*ec779b8eSAndroid Build Coastguard Worker      */
623*ec779b8eSAndroid Build Coastguard Worker     size_t numComponentBuffers() const;
624*ec779b8eSAndroid Build Coastguard Worker 
625*ec779b8eSAndroid Build Coastguard Worker private:
626*ec779b8eSAndroid Build Coastguard Worker     friend class BuffersArrayImpl;
627*ec779b8eSAndroid Build Coastguard Worker 
628*ec779b8eSAndroid Build Coastguard Worker     std::string mImplName; ///< name for debugging
629*ec779b8eSAndroid Build Coastguard Worker     const char *mName; ///< C-string version of name
630*ec779b8eSAndroid Build Coastguard Worker 
631*ec779b8eSAndroid Build Coastguard Worker     struct Entry {
632*ec779b8eSAndroid Build Coastguard Worker         sp<Codec2Buffer> clientBuffer;
633*ec779b8eSAndroid Build Coastguard Worker         std::weak_ptr<C2Buffer> compBuffer;
634*ec779b8eSAndroid Build Coastguard Worker     };
635*ec779b8eSAndroid Build Coastguard Worker     std::vector<Entry> mBuffers;
636*ec779b8eSAndroid Build Coastguard Worker };
637*ec779b8eSAndroid Build Coastguard Worker 
638*ec779b8eSAndroid Build Coastguard Worker /**
639*ec779b8eSAndroid Build Coastguard Worker  * Static buffer slots implementation based on a fixed-size array.
640*ec779b8eSAndroid Build Coastguard Worker  */
641*ec779b8eSAndroid Build Coastguard Worker class BuffersArrayImpl {
642*ec779b8eSAndroid Build Coastguard Worker public:
BuffersArrayImpl()643*ec779b8eSAndroid Build Coastguard Worker     BuffersArrayImpl()
644*ec779b8eSAndroid Build Coastguard Worker         : mImplName("BuffersArrayImpl"),
645*ec779b8eSAndroid Build Coastguard Worker           mName(mImplName.c_str()) { }
646*ec779b8eSAndroid Build Coastguard Worker 
647*ec779b8eSAndroid Build Coastguard Worker     /**
648*ec779b8eSAndroid Build Coastguard Worker      * Initialize buffer array from the original |impl|. The buffers known by
649*ec779b8eSAndroid Build Coastguard Worker      * the client is preserved, and the empty slots are populated so that the
650*ec779b8eSAndroid Build Coastguard Worker      * array size is at least |minSize|.
651*ec779b8eSAndroid Build Coastguard Worker      *
652*ec779b8eSAndroid Build Coastguard Worker      * \param impl[in]      FlexBuffersImpl object used so far.
653*ec779b8eSAndroid Build Coastguard Worker      * \param minSize[in]   minimum size of the buffer array.
654*ec779b8eSAndroid Build Coastguard Worker      * \param allocate[in]  function to allocate a client buffer for an empty slot.
655*ec779b8eSAndroid Build Coastguard Worker      */
656*ec779b8eSAndroid Build Coastguard Worker     void initialize(
657*ec779b8eSAndroid Build Coastguard Worker             const FlexBuffersImpl &impl,
658*ec779b8eSAndroid Build Coastguard Worker             size_t minSize,
659*ec779b8eSAndroid Build Coastguard Worker             std::function<sp<Codec2Buffer>()> allocate);
660*ec779b8eSAndroid Build Coastguard Worker 
661*ec779b8eSAndroid Build Coastguard Worker     /**
662*ec779b8eSAndroid Build Coastguard Worker      * Grab a buffer from the underlying array which matches the criteria.
663*ec779b8eSAndroid Build Coastguard Worker      *
664*ec779b8eSAndroid Build Coastguard Worker      * \param index[out]    index of the slot.
665*ec779b8eSAndroid Build Coastguard Worker      * \param buffer[out]   the matching buffer.
666*ec779b8eSAndroid Build Coastguard Worker      * \param match[in]     a function to test whether the buffer matches the
667*ec779b8eSAndroid Build Coastguard Worker      *                      criteria or not.
668*ec779b8eSAndroid Build Coastguard Worker      * \return OK           if successful,
669*ec779b8eSAndroid Build Coastguard Worker      *         WOULD_BLOCK  if slots are being used,
670*ec779b8eSAndroid Build Coastguard Worker      *         NO_MEMORY    if no slot matches the criteria, even though it's
671*ec779b8eSAndroid Build Coastguard Worker      *                      available
672*ec779b8eSAndroid Build Coastguard Worker      */
673*ec779b8eSAndroid Build Coastguard Worker     status_t grabBuffer(
674*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
675*ec779b8eSAndroid Build Coastguard Worker             sp<Codec2Buffer> *buffer,
676*ec779b8eSAndroid Build Coastguard Worker             std::function<bool(const sp<Codec2Buffer> &)> match =
677*ec779b8eSAndroid Build Coastguard Worker                 [](const sp<Codec2Buffer> &buffer) { return (buffer != nullptr); });
678*ec779b8eSAndroid Build Coastguard Worker 
679*ec779b8eSAndroid Build Coastguard Worker     /**
680*ec779b8eSAndroid Build Coastguard Worker      * Return the buffer from the client, and get the C2Buffer object back from
681*ec779b8eSAndroid Build Coastguard Worker      * the buffer. Note that the slot is not completely free until the returned
682*ec779b8eSAndroid Build Coastguard Worker      * C2Buffer object is freed.
683*ec779b8eSAndroid Build Coastguard Worker      *
684*ec779b8eSAndroid Build Coastguard Worker      * \param   buffer[in]        the buffer previously grabbed.
685*ec779b8eSAndroid Build Coastguard Worker      * \param   c2buffer[in,out]  pointer to C2Buffer to be populated. Ignored
686*ec779b8eSAndroid Build Coastguard Worker      *                            if null.
687*ec779b8eSAndroid Build Coastguard Worker      * \return  true  if the buffer is successfully returned
688*ec779b8eSAndroid Build Coastguard Worker      *          false otherwise
689*ec779b8eSAndroid Build Coastguard Worker      */
690*ec779b8eSAndroid Build Coastguard Worker     bool returnBuffer(
691*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
692*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
693*ec779b8eSAndroid Build Coastguard Worker             bool release);
694*ec779b8eSAndroid Build Coastguard Worker 
695*ec779b8eSAndroid Build Coastguard Worker     /**
696*ec779b8eSAndroid Build Coastguard Worker      * Expire the C2Buffer object in the slot.
697*ec779b8eSAndroid Build Coastguard Worker      *
698*ec779b8eSAndroid Build Coastguard Worker      * \param   c2buffer[in]  C2Buffer object which the component released.
699*ec779b8eSAndroid Build Coastguard Worker      * \return  true  if the buffer is found in one of the slots and
700*ec779b8eSAndroid Build Coastguard Worker      *                successfully released
701*ec779b8eSAndroid Build Coastguard Worker      *          false otherwise
702*ec779b8eSAndroid Build Coastguard Worker      */
703*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(const std::shared_ptr<C2Buffer> &c2buffer);
704*ec779b8eSAndroid Build Coastguard Worker 
705*ec779b8eSAndroid Build Coastguard Worker     /**
706*ec779b8eSAndroid Build Coastguard Worker      * Populate |array| with the underlying buffer array.
707*ec779b8eSAndroid Build Coastguard Worker      *
708*ec779b8eSAndroid Build Coastguard Worker      * \param array[out]  an array to be filled with the underlying buffer array.
709*ec779b8eSAndroid Build Coastguard Worker      */
710*ec779b8eSAndroid Build Coastguard Worker     void getArray(Vector<sp<MediaCodecBuffer>> *array) const;
711*ec779b8eSAndroid Build Coastguard Worker 
712*ec779b8eSAndroid Build Coastguard Worker     /**
713*ec779b8eSAndroid Build Coastguard Worker      * The client abandoned all known buffers, so reclaim the ownership.
714*ec779b8eSAndroid Build Coastguard Worker      */
715*ec779b8eSAndroid Build Coastguard Worker     void flush();
716*ec779b8eSAndroid Build Coastguard Worker 
717*ec779b8eSAndroid Build Coastguard Worker     /**
718*ec779b8eSAndroid Build Coastguard Worker      * Reallocate the array with the given allocation function.
719*ec779b8eSAndroid Build Coastguard Worker      *
720*ec779b8eSAndroid Build Coastguard Worker      * \param alloc[in] the allocation function for client buffers.
721*ec779b8eSAndroid Build Coastguard Worker      */
722*ec779b8eSAndroid Build Coastguard Worker     void realloc(std::function<sp<Codec2Buffer>()> alloc);
723*ec779b8eSAndroid Build Coastguard Worker 
724*ec779b8eSAndroid Build Coastguard Worker     /**
725*ec779b8eSAndroid Build Coastguard Worker      * Grow the array to the new size. It is a programming error to supply
726*ec779b8eSAndroid Build Coastguard Worker      * smaller size as the new size.
727*ec779b8eSAndroid Build Coastguard Worker      *
728*ec779b8eSAndroid Build Coastguard Worker      * \param newSize[in] new size of the array.
729*ec779b8eSAndroid Build Coastguard Worker      * \param alloc[in]   the alllocation function for client buffers to fill
730*ec779b8eSAndroid Build Coastguard Worker      *                    the new empty slots.
731*ec779b8eSAndroid Build Coastguard Worker      */
732*ec779b8eSAndroid Build Coastguard Worker     void grow(size_t newSize, std::function<sp<Codec2Buffer>()> alloc);
733*ec779b8eSAndroid Build Coastguard Worker 
734*ec779b8eSAndroid Build Coastguard Worker     /**
735*ec779b8eSAndroid Build Coastguard Worker      * Return the number of buffers that are sent to the client or the component.
736*ec779b8eSAndroid Build Coastguard Worker      */
737*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const;
738*ec779b8eSAndroid Build Coastguard Worker 
739*ec779b8eSAndroid Build Coastguard Worker     /**
740*ec779b8eSAndroid Build Coastguard Worker      * Return the size of the array.
741*ec779b8eSAndroid Build Coastguard Worker      */
742*ec779b8eSAndroid Build Coastguard Worker     size_t arraySize() const;
743*ec779b8eSAndroid Build Coastguard Worker 
744*ec779b8eSAndroid Build Coastguard Worker private:
745*ec779b8eSAndroid Build Coastguard Worker     std::string mImplName; ///< name for debugging
746*ec779b8eSAndroid Build Coastguard Worker     const char *mName; ///< C-string version of name
747*ec779b8eSAndroid Build Coastguard Worker 
748*ec779b8eSAndroid Build Coastguard Worker     struct Entry {
749*ec779b8eSAndroid Build Coastguard Worker         const sp<Codec2Buffer> clientBuffer;
750*ec779b8eSAndroid Build Coastguard Worker         std::weak_ptr<C2Buffer> compBuffer;
751*ec779b8eSAndroid Build Coastguard Worker         bool ownedByClient;
752*ec779b8eSAndroid Build Coastguard Worker     };
753*ec779b8eSAndroid Build Coastguard Worker     std::vector<Entry> mBuffers;
754*ec779b8eSAndroid Build Coastguard Worker };
755*ec779b8eSAndroid Build Coastguard Worker 
756*ec779b8eSAndroid Build Coastguard Worker class InputBuffersArray : public InputBuffers {
757*ec779b8eSAndroid Build Coastguard Worker public:
758*ec779b8eSAndroid Build Coastguard Worker     InputBuffersArray(const char *componentName, const char *name = "Input[N]")
InputBuffers(componentName,name)759*ec779b8eSAndroid Build Coastguard Worker         : InputBuffers(componentName, name) { }
760*ec779b8eSAndroid Build Coastguard Worker     ~InputBuffersArray() override = default;
761*ec779b8eSAndroid Build Coastguard Worker 
762*ec779b8eSAndroid Build Coastguard Worker     /**
763*ec779b8eSAndroid Build Coastguard Worker      * Initialize this object from the non-array state. We keep existing slots
764*ec779b8eSAndroid Build Coastguard Worker      * at the same index, and for empty slots we allocate client buffers with
765*ec779b8eSAndroid Build Coastguard Worker      * the given allocate function. If the number of slots is less than minSize,
766*ec779b8eSAndroid Build Coastguard Worker      * we fill the array to the minimum size.
767*ec779b8eSAndroid Build Coastguard Worker      *
768*ec779b8eSAndroid Build Coastguard Worker      * \param impl[in]      existing non-array state
769*ec779b8eSAndroid Build Coastguard Worker      * \param minSize[in]   minimum size of the array
770*ec779b8eSAndroid Build Coastguard Worker      * \param allocate[in]  allocate function to fill empty slots
771*ec779b8eSAndroid Build Coastguard Worker      */
772*ec779b8eSAndroid Build Coastguard Worker     void initialize(
773*ec779b8eSAndroid Build Coastguard Worker             const FlexBuffersImpl &impl,
774*ec779b8eSAndroid Build Coastguard Worker             size_t minSize,
775*ec779b8eSAndroid Build Coastguard Worker             std::function<sp<Codec2Buffer>()> allocate);
776*ec779b8eSAndroid Build Coastguard Worker 
isArrayMode()777*ec779b8eSAndroid Build Coastguard Worker     bool isArrayMode() const final { return true; }
778*ec779b8eSAndroid Build Coastguard Worker 
toArrayMode(size_t)779*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t) final {
780*ec779b8eSAndroid Build Coastguard Worker         return nullptr;
781*ec779b8eSAndroid Build Coastguard Worker     }
782*ec779b8eSAndroid Build Coastguard Worker 
783*ec779b8eSAndroid Build Coastguard Worker     void getArray(Vector<sp<MediaCodecBuffer>> *array) const final;
784*ec779b8eSAndroid Build Coastguard Worker 
785*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) override;
786*ec779b8eSAndroid Build Coastguard Worker 
787*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
788*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
789*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
790*ec779b8eSAndroid Build Coastguard Worker             bool release) override;
791*ec779b8eSAndroid Build Coastguard Worker 
792*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(
793*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) override;
794*ec779b8eSAndroid Build Coastguard Worker 
795*ec779b8eSAndroid Build Coastguard Worker     void flush() override;
796*ec779b8eSAndroid Build Coastguard Worker 
797*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
798*ec779b8eSAndroid Build Coastguard Worker 
799*ec779b8eSAndroid Build Coastguard Worker protected:
800*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override;
801*ec779b8eSAndroid Build Coastguard Worker 
802*ec779b8eSAndroid Build Coastguard Worker private:
803*ec779b8eSAndroid Build Coastguard Worker     BuffersArrayImpl mImpl;
804*ec779b8eSAndroid Build Coastguard Worker     std::function<sp<Codec2Buffer>()> mAllocate;
805*ec779b8eSAndroid Build Coastguard Worker };
806*ec779b8eSAndroid Build Coastguard Worker 
807*ec779b8eSAndroid Build Coastguard Worker class SlotInputBuffers : public InputBuffers {
808*ec779b8eSAndroid Build Coastguard Worker public:
809*ec779b8eSAndroid Build Coastguard Worker     SlotInputBuffers(const char *componentName, const char *name = "Slot-Input")
InputBuffers(componentName,name)810*ec779b8eSAndroid Build Coastguard Worker         : InputBuffers(componentName, name),
811*ec779b8eSAndroid Build Coastguard Worker           mImpl(mName) { }
812*ec779b8eSAndroid Build Coastguard Worker     ~SlotInputBuffers() override = default;
813*ec779b8eSAndroid Build Coastguard Worker 
814*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) final;
815*ec779b8eSAndroid Build Coastguard Worker 
816*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
817*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
818*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
819*ec779b8eSAndroid Build Coastguard Worker             bool release) final;
820*ec779b8eSAndroid Build Coastguard Worker 
821*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(
822*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) final;
823*ec779b8eSAndroid Build Coastguard Worker 
824*ec779b8eSAndroid Build Coastguard Worker     void flush() final;
825*ec779b8eSAndroid Build Coastguard Worker 
826*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t size) final;
827*ec779b8eSAndroid Build Coastguard Worker 
828*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
829*ec779b8eSAndroid Build Coastguard Worker 
830*ec779b8eSAndroid Build Coastguard Worker protected:
831*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() final;
832*ec779b8eSAndroid Build Coastguard Worker 
833*ec779b8eSAndroid Build Coastguard Worker private:
834*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl mImpl;
835*ec779b8eSAndroid Build Coastguard Worker };
836*ec779b8eSAndroid Build Coastguard Worker 
837*ec779b8eSAndroid Build Coastguard Worker class LinearInputBuffers : public InputBuffers {
838*ec779b8eSAndroid Build Coastguard Worker public:
839*ec779b8eSAndroid Build Coastguard Worker     LinearInputBuffers(const char *componentName, const char *name = "1D-Input")
InputBuffers(componentName,name)840*ec779b8eSAndroid Build Coastguard Worker         : InputBuffers(componentName, name),
841*ec779b8eSAndroid Build Coastguard Worker           mImpl(mName) { }
842*ec779b8eSAndroid Build Coastguard Worker     ~LinearInputBuffers() override = default;
843*ec779b8eSAndroid Build Coastguard Worker 
844*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) override;
845*ec779b8eSAndroid Build Coastguard Worker 
846*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
847*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
848*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
849*ec779b8eSAndroid Build Coastguard Worker             bool release) override;
850*ec779b8eSAndroid Build Coastguard Worker 
851*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(
852*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) override;
853*ec779b8eSAndroid Build Coastguard Worker 
854*ec779b8eSAndroid Build Coastguard Worker     void flush() override;
855*ec779b8eSAndroid Build Coastguard Worker 
856*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t size) override;
857*ec779b8eSAndroid Build Coastguard Worker 
858*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
859*ec779b8eSAndroid Build Coastguard Worker 
860*ec779b8eSAndroid Build Coastguard Worker protected:
861*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override;
862*ec779b8eSAndroid Build Coastguard Worker 
863*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl mImpl;
864*ec779b8eSAndroid Build Coastguard Worker 
865*ec779b8eSAndroid Build Coastguard Worker private:
866*ec779b8eSAndroid Build Coastguard Worker     static sp<Codec2Buffer> Alloc(
867*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2BlockPool> &pool, const sp<AMessage> &format);
868*ec779b8eSAndroid Build Coastguard Worker };
869*ec779b8eSAndroid Build Coastguard Worker 
870*ec779b8eSAndroid Build Coastguard Worker class EncryptedLinearInputBuffers : public LinearInputBuffers {
871*ec779b8eSAndroid Build Coastguard Worker public:
872*ec779b8eSAndroid Build Coastguard Worker     EncryptedLinearInputBuffers(
873*ec779b8eSAndroid Build Coastguard Worker             bool secure,
874*ec779b8eSAndroid Build Coastguard Worker             const sp<MemoryDealer> &dealer,
875*ec779b8eSAndroid Build Coastguard Worker             const sp<ICrypto> &crypto,
876*ec779b8eSAndroid Build Coastguard Worker             int32_t heapSeqNum,
877*ec779b8eSAndroid Build Coastguard Worker             size_t capacity,
878*ec779b8eSAndroid Build Coastguard Worker             size_t numInputSlots,
879*ec779b8eSAndroid Build Coastguard Worker             const char *componentName, const char *name = "EncryptedInput");
880*ec779b8eSAndroid Build Coastguard Worker 
881*ec779b8eSAndroid Build Coastguard Worker     ~EncryptedLinearInputBuffers() override = default;
882*ec779b8eSAndroid Build Coastguard Worker 
883*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t size) override;
884*ec779b8eSAndroid Build Coastguard Worker 
885*ec779b8eSAndroid Build Coastguard Worker protected:
886*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override;
887*ec779b8eSAndroid Build Coastguard Worker 
888*ec779b8eSAndroid Build Coastguard Worker private:
889*ec779b8eSAndroid Build Coastguard Worker     struct Entry {
890*ec779b8eSAndroid Build Coastguard Worker         std::weak_ptr<C2LinearBlock> block;
891*ec779b8eSAndroid Build Coastguard Worker         sp<IMemory> memory;
892*ec779b8eSAndroid Build Coastguard Worker         int32_t heapSeqNum;
893*ec779b8eSAndroid Build Coastguard Worker     };
894*ec779b8eSAndroid Build Coastguard Worker 
895*ec779b8eSAndroid Build Coastguard Worker     static sp<Codec2Buffer> Alloc(
896*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2BlockPool> &pool,
897*ec779b8eSAndroid Build Coastguard Worker             const sp<AMessage> &format,
898*ec779b8eSAndroid Build Coastguard Worker             C2MemoryUsage usage,
899*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<std::vector<Entry>> &memoryVector);
900*ec779b8eSAndroid Build Coastguard Worker 
901*ec779b8eSAndroid Build Coastguard Worker     C2MemoryUsage mUsage;
902*ec779b8eSAndroid Build Coastguard Worker     sp<MemoryDealer> mDealer;
903*ec779b8eSAndroid Build Coastguard Worker     sp<ICrypto> mCrypto;
904*ec779b8eSAndroid Build Coastguard Worker     std::shared_ptr<std::vector<Entry>> mMemoryVector;
905*ec779b8eSAndroid Build Coastguard Worker };
906*ec779b8eSAndroid Build Coastguard Worker 
907*ec779b8eSAndroid Build Coastguard Worker class GraphicMetadataInputBuffers : public InputBuffers {
908*ec779b8eSAndroid Build Coastguard Worker public:
909*ec779b8eSAndroid Build Coastguard Worker     GraphicMetadataInputBuffers(const char *componentName, const char *name = "2D-MetaInput");
910*ec779b8eSAndroid Build Coastguard Worker     ~GraphicMetadataInputBuffers() override = default;
911*ec779b8eSAndroid Build Coastguard Worker 
912*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) override;
913*ec779b8eSAndroid Build Coastguard Worker 
914*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
915*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
916*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
917*ec779b8eSAndroid Build Coastguard Worker             bool release) override;
918*ec779b8eSAndroid Build Coastguard Worker 
919*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(
920*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) override;
921*ec779b8eSAndroid Build Coastguard Worker 
922*ec779b8eSAndroid Build Coastguard Worker     void flush() override;
923*ec779b8eSAndroid Build Coastguard Worker 
924*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t size) final;
925*ec779b8eSAndroid Build Coastguard Worker 
926*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
927*ec779b8eSAndroid Build Coastguard Worker 
928*ec779b8eSAndroid Build Coastguard Worker protected:
929*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override;
930*ec779b8eSAndroid Build Coastguard Worker 
931*ec779b8eSAndroid Build Coastguard Worker private:
932*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl mImpl;
933*ec779b8eSAndroid Build Coastguard Worker     std::shared_ptr<C2AllocatorStore> mStore;
934*ec779b8eSAndroid Build Coastguard Worker };
935*ec779b8eSAndroid Build Coastguard Worker 
936*ec779b8eSAndroid Build Coastguard Worker class GraphicInputBuffers : public InputBuffers {
937*ec779b8eSAndroid Build Coastguard Worker public:
938*ec779b8eSAndroid Build Coastguard Worker     GraphicInputBuffers(const char *componentName, const char *name = "2D-BB-Input");
939*ec779b8eSAndroid Build Coastguard Worker     ~GraphicInputBuffers() override = default;
940*ec779b8eSAndroid Build Coastguard Worker 
941*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *index, sp<MediaCodecBuffer> *buffer) override;
942*ec779b8eSAndroid Build Coastguard Worker 
943*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
944*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
945*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer,
946*ec779b8eSAndroid Build Coastguard Worker             bool release) override;
947*ec779b8eSAndroid Build Coastguard Worker 
948*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(
949*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &c2buffer) override;
950*ec779b8eSAndroid Build Coastguard Worker 
951*ec779b8eSAndroid Build Coastguard Worker     void flush() override;
952*ec779b8eSAndroid Build Coastguard Worker 
953*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(
954*ec779b8eSAndroid Build Coastguard Worker             size_t size) final;
955*ec779b8eSAndroid Build Coastguard Worker 
956*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
957*ec779b8eSAndroid Build Coastguard Worker 
958*ec779b8eSAndroid Build Coastguard Worker     uint32_t getPixelFormatIfApplicable() override;
959*ec779b8eSAndroid Build Coastguard Worker 
960*ec779b8eSAndroid Build Coastguard Worker     bool resetPixelFormatIfApplicable() override;
961*ec779b8eSAndroid Build Coastguard Worker 
962*ec779b8eSAndroid Build Coastguard Worker protected:
963*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override;
964*ec779b8eSAndroid Build Coastguard Worker 
965*ec779b8eSAndroid Build Coastguard Worker private:
966*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl mImpl;
967*ec779b8eSAndroid Build Coastguard Worker     std::shared_ptr<LocalBufferPool> mLocalBufferPool;
968*ec779b8eSAndroid Build Coastguard Worker     uint32_t mPixelFormat;
969*ec779b8eSAndroid Build Coastguard Worker };
970*ec779b8eSAndroid Build Coastguard Worker 
971*ec779b8eSAndroid Build Coastguard Worker class DummyInputBuffers : public InputBuffers {
972*ec779b8eSAndroid Build Coastguard Worker public:
973*ec779b8eSAndroid Build Coastguard Worker     DummyInputBuffers(const char *componentName, const char *name = "2D-Input")
InputBuffers(componentName,name)974*ec779b8eSAndroid Build Coastguard Worker         : InputBuffers(componentName, name) { }
975*ec779b8eSAndroid Build Coastguard Worker     ~DummyInputBuffers() override = default;
976*ec779b8eSAndroid Build Coastguard Worker 
requestNewBuffer(size_t *,sp<MediaCodecBuffer> *)977*ec779b8eSAndroid Build Coastguard Worker     bool requestNewBuffer(size_t *, sp<MediaCodecBuffer> *) override {
978*ec779b8eSAndroid Build Coastguard Worker         return false;
979*ec779b8eSAndroid Build Coastguard Worker     }
980*ec779b8eSAndroid Build Coastguard Worker 
releaseBuffer(const sp<MediaCodecBuffer> &,std::shared_ptr<C2Buffer> *,bool)981*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
982*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &, std::shared_ptr<C2Buffer> *, bool) override {
983*ec779b8eSAndroid Build Coastguard Worker         return false;
984*ec779b8eSAndroid Build Coastguard Worker     }
985*ec779b8eSAndroid Build Coastguard Worker 
expireComponentBuffer(const std::shared_ptr<C2Buffer> &)986*ec779b8eSAndroid Build Coastguard Worker     bool expireComponentBuffer(const std::shared_ptr<C2Buffer> &) override {
987*ec779b8eSAndroid Build Coastguard Worker         return false;
988*ec779b8eSAndroid Build Coastguard Worker     }
flush()989*ec779b8eSAndroid Build Coastguard Worker     void flush() override {
990*ec779b8eSAndroid Build Coastguard Worker     }
991*ec779b8eSAndroid Build Coastguard Worker 
toArrayMode(size_t)992*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<InputBuffers> toArrayMode(size_t) final {
993*ec779b8eSAndroid Build Coastguard Worker         return nullptr;
994*ec779b8eSAndroid Build Coastguard Worker     }
995*ec779b8eSAndroid Build Coastguard Worker 
isArrayMode()996*ec779b8eSAndroid Build Coastguard Worker     bool isArrayMode() const final { return true; }
997*ec779b8eSAndroid Build Coastguard Worker 
getArray(Vector<sp<MediaCodecBuffer>> * array)998*ec779b8eSAndroid Build Coastguard Worker     void getArray(Vector<sp<MediaCodecBuffer>> *array) const final {
999*ec779b8eSAndroid Build Coastguard Worker         array->clear();
1000*ec779b8eSAndroid Build Coastguard Worker     }
1001*ec779b8eSAndroid Build Coastguard Worker 
numActiveSlots()1002*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final {
1003*ec779b8eSAndroid Build Coastguard Worker         return 0u;
1004*ec779b8eSAndroid Build Coastguard Worker     }
1005*ec779b8eSAndroid Build Coastguard Worker 
1006*ec779b8eSAndroid Build Coastguard Worker protected:
createNewBuffer()1007*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> createNewBuffer() override {
1008*ec779b8eSAndroid Build Coastguard Worker         return nullptr;
1009*ec779b8eSAndroid Build Coastguard Worker     }
1010*ec779b8eSAndroid Build Coastguard Worker };
1011*ec779b8eSAndroid Build Coastguard Worker 
1012*ec779b8eSAndroid Build Coastguard Worker class OutputBuffersArray : public OutputBuffers {
1013*ec779b8eSAndroid Build Coastguard Worker public:
1014*ec779b8eSAndroid Build Coastguard Worker     OutputBuffersArray(const char *componentName, const char *name = "Output[N]")
OutputBuffers(componentName,name)1015*ec779b8eSAndroid Build Coastguard Worker         : OutputBuffers(componentName, name) { }
1016*ec779b8eSAndroid Build Coastguard Worker     ~OutputBuffersArray() override = default;
1017*ec779b8eSAndroid Build Coastguard Worker 
1018*ec779b8eSAndroid Build Coastguard Worker     /**
1019*ec779b8eSAndroid Build Coastguard Worker      * Initialize this object from the non-array state. We keep existing slots
1020*ec779b8eSAndroid Build Coastguard Worker      * at the same index, and for empty slots we allocate client buffers with
1021*ec779b8eSAndroid Build Coastguard Worker      * the given allocate function. If the number of slots is less than minSize,
1022*ec779b8eSAndroid Build Coastguard Worker      * we fill the array to the minimum size.
1023*ec779b8eSAndroid Build Coastguard Worker      *
1024*ec779b8eSAndroid Build Coastguard Worker      * \param impl[in]      existing non-array state
1025*ec779b8eSAndroid Build Coastguard Worker      * \param minSize[in]   minimum size of the array
1026*ec779b8eSAndroid Build Coastguard Worker      * \param allocate[in]  allocate function to fill empty slots
1027*ec779b8eSAndroid Build Coastguard Worker      */
1028*ec779b8eSAndroid Build Coastguard Worker     void initialize(
1029*ec779b8eSAndroid Build Coastguard Worker             const FlexBuffersImpl &impl,
1030*ec779b8eSAndroid Build Coastguard Worker             size_t minSize,
1031*ec779b8eSAndroid Build Coastguard Worker             std::function<sp<Codec2Buffer>()> allocate);
1032*ec779b8eSAndroid Build Coastguard Worker 
isArrayMode()1033*ec779b8eSAndroid Build Coastguard Worker     bool isArrayMode() const final { return true; }
1034*ec779b8eSAndroid Build Coastguard Worker 
toArrayMode(size_t)1035*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<OutputBuffersArray> toArrayMode(size_t) final {
1036*ec779b8eSAndroid Build Coastguard Worker         return nullptr;
1037*ec779b8eSAndroid Build Coastguard Worker     }
1038*ec779b8eSAndroid Build Coastguard Worker 
1039*ec779b8eSAndroid Build Coastguard Worker     status_t registerBuffer(
1040*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &buffer,
1041*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
1042*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> *clientBuffer) final;
1043*ec779b8eSAndroid Build Coastguard Worker 
1044*ec779b8eSAndroid Build Coastguard Worker     status_t registerCsd(
1045*ec779b8eSAndroid Build Coastguard Worker             const C2StreamInitDataInfo::output *csd,
1046*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
1047*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> *clientBuffer) final;
1048*ec779b8eSAndroid Build Coastguard Worker 
1049*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
1050*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer, std::shared_ptr<C2Buffer> *c2buffer) override;
1051*ec779b8eSAndroid Build Coastguard Worker 
1052*ec779b8eSAndroid Build Coastguard Worker     void flush(const std::list<std::unique_ptr<C2Work>> &flushedWork) override;
1053*ec779b8eSAndroid Build Coastguard Worker 
1054*ec779b8eSAndroid Build Coastguard Worker     void getArray(Vector<sp<MediaCodecBuffer>> *array) const final;
1055*ec779b8eSAndroid Build Coastguard Worker 
1056*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
1057*ec779b8eSAndroid Build Coastguard Worker 
1058*ec779b8eSAndroid Build Coastguard Worker     /**
1059*ec779b8eSAndroid Build Coastguard Worker      * Reallocate the array, filled with buffers with the same size as given
1060*ec779b8eSAndroid Build Coastguard Worker      * buffer.
1061*ec779b8eSAndroid Build Coastguard Worker      *
1062*ec779b8eSAndroid Build Coastguard Worker      * \param c2buffer[in] the reference buffer
1063*ec779b8eSAndroid Build Coastguard Worker      */
1064*ec779b8eSAndroid Build Coastguard Worker     void realloc(const std::shared_ptr<C2Buffer> &c2buffer);
1065*ec779b8eSAndroid Build Coastguard Worker 
1066*ec779b8eSAndroid Build Coastguard Worker     /**
1067*ec779b8eSAndroid Build Coastguard Worker      * Grow the array to the new size. It is a programming error to supply
1068*ec779b8eSAndroid Build Coastguard Worker      * smaller size as the new size.
1069*ec779b8eSAndroid Build Coastguard Worker      *
1070*ec779b8eSAndroid Build Coastguard Worker      * \param newSize[in] new size of the array.
1071*ec779b8eSAndroid Build Coastguard Worker      */
1072*ec779b8eSAndroid Build Coastguard Worker     void grow(size_t newSize);
1073*ec779b8eSAndroid Build Coastguard Worker 
1074*ec779b8eSAndroid Build Coastguard Worker     /**
1075*ec779b8eSAndroid Build Coastguard Worker      * Transfer the SkipCutBuffer and the output stash from another
1076*ec779b8eSAndroid Build Coastguard Worker      * OutputBuffers.
1077*ec779b8eSAndroid Build Coastguard Worker      */
1078*ec779b8eSAndroid Build Coastguard Worker     void transferFrom(OutputBuffers* source);
1079*ec779b8eSAndroid Build Coastguard Worker 
1080*ec779b8eSAndroid Build Coastguard Worker private:
1081*ec779b8eSAndroid Build Coastguard Worker     BuffersArrayImpl mImpl;
1082*ec779b8eSAndroid Build Coastguard Worker     std::function<sp<Codec2Buffer>()> mAlloc;
1083*ec779b8eSAndroid Build Coastguard Worker };
1084*ec779b8eSAndroid Build Coastguard Worker 
1085*ec779b8eSAndroid Build Coastguard Worker class FlexOutputBuffers : public OutputBuffers {
1086*ec779b8eSAndroid Build Coastguard Worker public:
1087*ec779b8eSAndroid Build Coastguard Worker     FlexOutputBuffers(const char *componentName, const char *name = "Output[]")
OutputBuffers(componentName,name)1088*ec779b8eSAndroid Build Coastguard Worker         : OutputBuffers(componentName, name),
1089*ec779b8eSAndroid Build Coastguard Worker           mImpl(mName),
1090*ec779b8eSAndroid Build Coastguard Worker           mPixelFormat(0) { }
1091*ec779b8eSAndroid Build Coastguard Worker 
1092*ec779b8eSAndroid Build Coastguard Worker     status_t registerBuffer(
1093*ec779b8eSAndroid Build Coastguard Worker             const std::shared_ptr<C2Buffer> &buffer,
1094*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
1095*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> *clientBuffer) override;
1096*ec779b8eSAndroid Build Coastguard Worker 
1097*ec779b8eSAndroid Build Coastguard Worker     status_t registerCsd(
1098*ec779b8eSAndroid Build Coastguard Worker             const C2StreamInitDataInfo::output *csd,
1099*ec779b8eSAndroid Build Coastguard Worker             size_t *index,
1100*ec779b8eSAndroid Build Coastguard Worker             sp<MediaCodecBuffer> *clientBuffer) final;
1101*ec779b8eSAndroid Build Coastguard Worker 
1102*ec779b8eSAndroid Build Coastguard Worker     bool releaseBuffer(
1103*ec779b8eSAndroid Build Coastguard Worker             const sp<MediaCodecBuffer> &buffer,
1104*ec779b8eSAndroid Build Coastguard Worker             std::shared_ptr<C2Buffer> *c2buffer) override;
1105*ec779b8eSAndroid Build Coastguard Worker 
1106*ec779b8eSAndroid Build Coastguard Worker     void flush(
1107*ec779b8eSAndroid Build Coastguard Worker             const std::list<std::unique_ptr<C2Work>> &flushedWork) override;
1108*ec779b8eSAndroid Build Coastguard Worker 
1109*ec779b8eSAndroid Build Coastguard Worker     std::unique_ptr<OutputBuffersArray> toArrayMode(size_t size) override;
1110*ec779b8eSAndroid Build Coastguard Worker 
1111*ec779b8eSAndroid Build Coastguard Worker     size_t numActiveSlots() const final;
1112*ec779b8eSAndroid Build Coastguard Worker 
1113*ec779b8eSAndroid Build Coastguard Worker     /**
1114*ec779b8eSAndroid Build Coastguard Worker      * Return an appropriate Codec2Buffer object for the type of buffers.
1115*ec779b8eSAndroid Build Coastguard Worker      *
1116*ec779b8eSAndroid Build Coastguard Worker      * \param buffer  C2Buffer object to wrap.
1117*ec779b8eSAndroid Build Coastguard Worker      *
1118*ec779b8eSAndroid Build Coastguard Worker      * \return  appropriate Codec2Buffer object to wrap |buffer|.
1119*ec779b8eSAndroid Build Coastguard Worker      */
1120*ec779b8eSAndroid Build Coastguard Worker     virtual sp<Codec2Buffer> wrap(const std::shared_ptr<C2Buffer> &buffer) = 0;
1121*ec779b8eSAndroid Build Coastguard Worker 
1122*ec779b8eSAndroid Build Coastguard Worker     /**
1123*ec779b8eSAndroid Build Coastguard Worker      * Return a function that allocates an appropriate Codec2Buffer object for
1124*ec779b8eSAndroid Build Coastguard Worker      * the type of buffers, to be used as an empty array buffer. The function
1125*ec779b8eSAndroid Build Coastguard Worker      * must not refer to this pointer, since it may be used after this object
1126*ec779b8eSAndroid Build Coastguard Worker      * destructs.
1127*ec779b8eSAndroid Build Coastguard Worker      *
1128*ec779b8eSAndroid Build Coastguard Worker      * \return  a function that allocates appropriate Codec2Buffer object,
1129*ec779b8eSAndroid Build Coastguard Worker      *          which can copy() from C2Buffers.
1130*ec779b8eSAndroid Build Coastguard Worker      */
1131*ec779b8eSAndroid Build Coastguard Worker     virtual std::function<sp<Codec2Buffer>()> getAlloc() = 0;
1132*ec779b8eSAndroid Build Coastguard Worker 
1133*ec779b8eSAndroid Build Coastguard Worker     uint32_t getPixelFormatIfApplicable() override;
1134*ec779b8eSAndroid Build Coastguard Worker 
1135*ec779b8eSAndroid Build Coastguard Worker     bool resetPixelFormatIfApplicable() override;
1136*ec779b8eSAndroid Build Coastguard Worker private:
1137*ec779b8eSAndroid Build Coastguard Worker     FlexBuffersImpl mImpl;
1138*ec779b8eSAndroid Build Coastguard Worker 
1139*ec779b8eSAndroid Build Coastguard Worker     uint32_t mPixelFormat;
1140*ec779b8eSAndroid Build Coastguard Worker 
1141*ec779b8eSAndroid Build Coastguard Worker     /**
1142*ec779b8eSAndroid Build Coastguard Worker      * extract pixel format from C2Buffer when register.
1143*ec779b8eSAndroid Build Coastguard Worker      *
1144*ec779b8eSAndroid Build Coastguard Worker      * \param buffer   The C2Buffer used to extract pixel format.
1145*ec779b8eSAndroid Build Coastguard Worker      */
1146*ec779b8eSAndroid Build Coastguard Worker     bool extractPixelFormatFromC2Buffer(const std::shared_ptr<C2Buffer> &buffer);
1147*ec779b8eSAndroid Build Coastguard Worker };
1148*ec779b8eSAndroid Build Coastguard Worker 
1149*ec779b8eSAndroid Build Coastguard Worker class LinearOutputBuffers : public FlexOutputBuffers {
1150*ec779b8eSAndroid Build Coastguard Worker public:
1151*ec779b8eSAndroid Build Coastguard Worker     LinearOutputBuffers(const char *componentName, const char *name = "1D-Output")
FlexOutputBuffers(componentName,name)1152*ec779b8eSAndroid Build Coastguard Worker         : FlexOutputBuffers(componentName, name) { }
1153*ec779b8eSAndroid Build Coastguard Worker 
1154*ec779b8eSAndroid Build Coastguard Worker     void flush(
1155*ec779b8eSAndroid Build Coastguard Worker             const std::list<std::unique_ptr<C2Work>> &flushedWork) override;
1156*ec779b8eSAndroid Build Coastguard Worker 
1157*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> wrap(const std::shared_ptr<C2Buffer> &buffer) override;
1158*ec779b8eSAndroid Build Coastguard Worker 
1159*ec779b8eSAndroid Build Coastguard Worker     std::function<sp<Codec2Buffer>()> getAlloc() override;
1160*ec779b8eSAndroid Build Coastguard Worker };
1161*ec779b8eSAndroid Build Coastguard Worker 
1162*ec779b8eSAndroid Build Coastguard Worker class GraphicOutputBuffers : public FlexOutputBuffers {
1163*ec779b8eSAndroid Build Coastguard Worker public:
1164*ec779b8eSAndroid Build Coastguard Worker     GraphicOutputBuffers(const char *componentName, const char *name = "2D-Output")
FlexOutputBuffers(componentName,name)1165*ec779b8eSAndroid Build Coastguard Worker         : FlexOutputBuffers(componentName, name) { }
1166*ec779b8eSAndroid Build Coastguard Worker 
1167*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> wrap(const std::shared_ptr<C2Buffer> &buffer) override;
1168*ec779b8eSAndroid Build Coastguard Worker 
1169*ec779b8eSAndroid Build Coastguard Worker     std::function<sp<Codec2Buffer>()> getAlloc() override;
1170*ec779b8eSAndroid Build Coastguard Worker };
1171*ec779b8eSAndroid Build Coastguard Worker 
1172*ec779b8eSAndroid Build Coastguard Worker class RawGraphicOutputBuffers : public FlexOutputBuffers {
1173*ec779b8eSAndroid Build Coastguard Worker public:
1174*ec779b8eSAndroid Build Coastguard Worker     RawGraphicOutputBuffers(const char *componentName, const char *name = "2D-BB-Output");
1175*ec779b8eSAndroid Build Coastguard Worker     ~RawGraphicOutputBuffers() override = default;
1176*ec779b8eSAndroid Build Coastguard Worker 
1177*ec779b8eSAndroid Build Coastguard Worker     sp<Codec2Buffer> wrap(const std::shared_ptr<C2Buffer> &buffer) override;
1178*ec779b8eSAndroid Build Coastguard Worker 
1179*ec779b8eSAndroid Build Coastguard Worker     std::function<sp<Codec2Buffer>()> getAlloc() override;
1180*ec779b8eSAndroid Build Coastguard Worker 
1181*ec779b8eSAndroid Build Coastguard Worker private:
1182*ec779b8eSAndroid Build Coastguard Worker     std::shared_ptr<LocalBufferPool> mLocalBufferPool;
1183*ec779b8eSAndroid Build Coastguard Worker };
1184*ec779b8eSAndroid Build Coastguard Worker 
1185*ec779b8eSAndroid Build Coastguard Worker }  // namespace android
1186*ec779b8eSAndroid Build Coastguard Worker 
1187*ec779b8eSAndroid Build Coastguard Worker #endif  // CCODEC_BUFFERS_H_
1188