1 /*
2  * Copyright (C) 2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef HARDWARE_GOOGLE_MEDIA_C2_V1_0_UTILS_TYPES_H
18 #define HARDWARE_GOOGLE_MEDIA_C2_V1_0_UTILS_TYPES_H
19 
20 #include <bufferpool/ClientManager.h>
21 #include <android/hardware/media/bufferpool/1.0/IClientManager.h>
22 #include <android/hardware/media/bufferpool/1.0/types.h>
23 #include <hardware/google/media/c2/1.0/IComponentStore.h>
24 #include <hardware/google/media/c2/1.0/types.h>
25 #include <gui/IGraphicBufferProducer.h>
26 
27 #include <C2Component.h>
28 #include <C2Param.h>
29 #include <C2ParamDef.h>
30 #include <C2Work.h>
31 
32 namespace hardware {
33 namespace google {
34 namespace media {
35 namespace c2 {
36 namespace V1_0 {
37 namespace utils {
38 
39 using ::android::hardware::hidl_bitfield;
40 using ::android::hardware::hidl_handle;
41 using ::android::hardware::hidl_string;
42 using ::android::hardware::hidl_vec;
43 using ::android::status_t;
44 using ::android::sp;
45 using ::android::hardware::media::bufferpool::V1_0::implementation::
46         ConnectionId;
47 using ::android::IGraphicBufferProducer;
48 
49 // Types of metadata for Blocks.
50 struct C2Hidl_Range {
51     uint32_t offset;
52     uint32_t length; // Do not use "size" because the name collides with C2Info::size().
53 };
54 typedef C2GlobalParam<C2Info, C2Hidl_Range, 0> C2Hidl_RangeInfo;
55 
56 struct C2Hidl_Rect {
57     uint32_t left;
58     uint32_t top;
59     uint32_t width;
60     uint32_t height;
61 };
62 typedef C2GlobalParam<C2Info, C2Hidl_Rect, 1> C2Hidl_RectInfo;
63 
64 // C2SettingResult -> SettingResult
65 Status objcpy(
66         SettingResult* d,
67         const C2SettingResult& s);
68 
69 // SettingResult -> std::unique_ptr<C2SettingResult>
70 c2_status_t objcpy(
71         std::unique_ptr<C2SettingResult>* d,
72         const SettingResult& s);
73 
74 // C2ParamDescriptor -> ParamDescriptor
75 Status objcpy(
76         ParamDescriptor* d,
77         const C2ParamDescriptor& s);
78 
79 // ParamDescriptor -> std::shared_ptr<C2ParamDescriptor>
80 c2_status_t objcpy(
81         std::shared_ptr<C2ParamDescriptor>* d,
82         const ParamDescriptor& s);
83 
84 // C2FieldSupportedValuesQuery -> FieldSupportedValuesQuery
85 Status objcpy(
86         FieldSupportedValuesQuery* d,
87         const C2FieldSupportedValuesQuery& s);
88 
89 // FieldSupportedValuesQuery -> C2FieldSupportedValuesQuery
90 c2_status_t objcpy(
91         C2FieldSupportedValuesQuery* d,
92         const FieldSupportedValuesQuery& s);
93 
94 // C2FieldSupportedValuesQuery -> FieldSupportedValuesQueryResult
95 Status objcpy(
96         FieldSupportedValuesQueryResult* d,
97         const C2FieldSupportedValuesQuery& s);
98 
99 // FieldSupportedValuesQuery, FieldSupportedValuesQueryResult -> C2FieldSupportedValuesQuery
100 c2_status_t objcpy(
101         C2FieldSupportedValuesQuery* d,
102         const FieldSupportedValuesQuery& sq,
103         const FieldSupportedValuesQueryResult& sr);
104 
105 // C2Component::Traits -> ComponentTraits
106 Status objcpy(
107         IComponentStore::ComponentTraits* d,
108         const C2Component::Traits& s);
109 
110 // ComponentTraits -> C2Component::Traits, std::unique_ptr<std::vector<std::string>>
111 // Note: The output d is only valid as long as aliasesBuffer remains alive.
112 c2_status_t objcpy(
113         C2Component::Traits* d,
114         std::unique_ptr<std::vector<std::string>>* aliasesBuffer,
115         const IComponentStore::ComponentTraits& s);
116 
117 // C2StructDescriptor -> StructDescriptor
118 Status objcpy(
119         StructDescriptor* d,
120         const C2StructDescriptor& s);
121 
122 // StructDescriptor -> C2StructDescriptor
123 c2_status_t objcpy(
124         std::unique_ptr<C2StructDescriptor>* d,
125         const StructDescriptor& s);
126 
127 // Abstract class to be used in
128 // objcpy(std::list<std::unique_ptr<C2Work>> -> WorkBundle).
129 struct BufferPoolSender {
130     typedef ::android::hardware::media::bufferpool::V1_0::
131             ResultStatus ResultStatus;
132     typedef ::android::hardware::media::bufferpool::V1_0::
133             BufferStatusMessage BufferStatusMessage;
134     typedef ::android::hardware::media::bufferpool::
135             BufferPoolData BufferPoolData;
136 
137     /**
138      * Send bpData and return BufferStatusMessage that can be supplied to
139      * IClientManager::receive() in the receiving process.
140      *
141      * This function will be called from within the function
142      * objcpy(std::list<std::unique_ptr<C2Work>> -> WorkBundle).
143      *
144      * \param[in] bpData BufferPoolData identifying the buffer to send.
145      * \param[out] bpMessage BufferStatusMessage of the transaction. Information
146      *    inside \p bpMessage should be passed to the receiving process by some
147      *    other means so it can call receive() properly.
148      * \return ResultStatus value that determines the success of the operation.
149      *    (See the possible values of ResultStatus in
150      *    hardware/interfaces/media/bufferpool/1.0/types.hal.)
151      */
152     virtual ResultStatus send(
153             const std::shared_ptr<BufferPoolData>& bpData,
154             BufferStatusMessage* bpMessage) = 0;
155 
156     virtual ~BufferPoolSender() = default;
157 };
158 
159 // Default implementation of BufferPoolSender.
160 //
161 // To use DefaultBufferPoolSender, the IClientManager instance of the receiving
162 // process must be set before send() can operate. DefaultBufferPoolSender will
163 // hold a strong reference to the IClientManager instance and use it to call
164 // IClientManager::registerSender() to establish the bufferpool connection when
165 // send() is called.
166 struct DefaultBufferPoolSender : BufferPoolSender {
167     typedef ::android::hardware::media::bufferpool::V1_0::implementation::
168             ClientManager ClientManager;
169     typedef ::android::hardware::media::bufferpool::V1_0::
170             IClientManager IClientManager;
171 
172     // Set the IClientManager of the receiving process to receiverManager.
173     DefaultBufferPoolSender(const sp<IClientManager>& receiverManager = nullptr);
174 
175     // Set the IClientManager of the receiving process to receiverManager.
176     void setReceiver(const sp<IClientManager>& receiverManager);
177 
178     // Implementation of BufferPoolSender::send(). The first time send() is
179     // called, the bufferpool connection will be established with the
180     // previously-set IClientManager of the receiving process.
181     virtual ResultStatus send(
182             const std::shared_ptr<BufferPoolData>& bpData,
183             BufferStatusMessage* bpMessage) override;
184 
185 private:
186     std::mutex mMutex;
187     sp<ClientManager> mSenderManager;
188     sp<IClientManager> mReceiverManager;
189     int64_t mReceiverConnectionId;
190     int64_t mSourceConnectionId;
191 };
192 
193 // std::list<std::unique_ptr<C2Work>> -> WorkBundle
194 // Note: If bufferpool will be used, bpSender must not be null.
195 Status objcpy(
196         WorkBundle* d,
197         const std::list<std::unique_ptr<C2Work>>& s,
198         BufferPoolSender* bpSender = nullptr);
199 
200 // WorkBundle -> std::list<std::unique_ptr<C2Work>>
201 c2_status_t objcpy(
202         std::list<std::unique_ptr<C2Work>>* d,
203         const WorkBundle& s);
204 
205 /**
206  * Parses a params blob and returns C2Param pointers to its params.
207  * \param[out] params target vector of C2Param pointers
208  * \param[in] blob parameter blob to parse
209  * \retval C2_OK if the full blob was parsed
210  * \retval C2_BAD_VALUE otherwise
211  */
212 c2_status_t parseParamsBlob(
213         std::vector<C2Param*> *params,
214         const hidl_vec<uint8_t> &blob);
215 
216 /**
217  * Concatenates a list of C2Params into a params blob.
218  * \param[out] blob target blob
219  * \param[in] params parameters to concatenate
220  * \retval C2_OK if the blob was successfully created
221  * \retval C2_BAD_VALUE if the blob was not successful (this only happens if the parameters were
222  *         not const)
223  */
224 Status createParamsBlob(
225         hidl_vec<uint8_t> *blob,
226         const std::vector<C2Param*> &params);
227 Status createParamsBlob(
228         hidl_vec<uint8_t> *blob,
229         const std::vector<std::unique_ptr<C2Param>> &params);
230 Status createParamsBlob(
231         hidl_vec<uint8_t> *blob,
232         const std::vector<std::shared_ptr<const C2Info>> &params);
233 Status createParamsBlob(
234         hidl_vec<uint8_t> *blob,
235         const std::vector<std::unique_ptr<C2Tuning>> &params);
236 
237 /**
238  * Parses a params blob and create a vector of C2Params whose members are copies
239  * of the params in the blob.
240  * \param[out] params the resulting vector
241  * \param[in] blob parameter blob to parse
242  * \retval C2_OK if the full blob was parsed and params was constructed
243  * \retval C2_BAD_VALUE otherwise
244  */
245 c2_status_t copyParamsFromBlob(
246         std::vector<std::unique_ptr<C2Param>>* params,
247         Params blob);
248 
249 /**
250  * Parses a params blob and applies updates to params
251  * \param[in,out] params params to be updated
252  * \param[in] blob parameter blob containing updates
253  * \retval C2_OK if the full blob was parsed and params was updated
254  * \retval C2_BAD_VALUE otherwise
255  */
256 c2_status_t updateParamsFromBlob(
257         const std::vector<C2Param*>& params,
258         const Params& blob);
259 
260 /**
261  * Converts a BufferPool status value to c2_status_t.
262  * \param BufferPool status
263  * \return Corresponding c2_status_t
264  */
265 c2_status_t toC2Status(::android::hardware::media::bufferpool::V1_0::
266         ResultStatus rs);
267 
268 // BufferQueue-Based Block Operations
269 // ==================================
270 
271 // Create a GraphicBuffer object from a graphic block and attach it to an
272 // IGraphicBufferProducer.
273 status_t attachToBufferQueue(const C2ConstGraphicBlock& block,
274                              const sp<IGraphicBufferProducer>& igbp,
275                              uint32_t generation,
276                              int32_t* bqSlot);
277 
278 // Return false if block does not come from a bufferqueue-based blockpool.
279 // Otherwise, extract bqId and bqSlot and return true.
280 bool getBufferQueueAssignment(const C2ConstGraphicBlock& block,
281                               uint64_t* bqId,
282                               int32_t* bqSlot);
283 
284 // Disassociate the given block with its designated bufferqueue so that
285 // cancelBuffer() will not be called when the block is destroyed. If the block
286 // does not have a designated bufferqueue, the function returns false.
287 // Otherwise, it returns true.
288 //
289 // Note: This function should be called after attachBuffer() or queueBuffer() is
290 // called manually.
291 bool yieldBufferQueueBlock(const C2ConstGraphicBlock& block);
292 
293 // Call yieldBufferQueueBlock() on blocks in the given workList. processInput
294 // determines whether input blocks are yielded. processOutput works similarly on
295 // output blocks. (The default value of processInput is false while the default
296 // value of processOutput is true. This implies that in most cases, only output
297 // buffers contain bufferqueue-based blocks.)
298 //
299 // Note: This function should be called after WorkBundle has been successfully
300 // sent over the Treble boundary to another process.
301 void yieldBufferQueueBlocks(const std::list<std::unique_ptr<C2Work>>& workList,
302                             bool processInput = false,
303                             bool processOutput = true);
304 
305 // Assign the given block to a bufferqueue so that when the block is destroyed,
306 // cancelBuffer() will be called.
307 //
308 // If the block does not come from a bufferqueue-based blockpool, this function
309 // returns false.
310 //
311 // If the block already has a bufferqueue assignment that matches the given one,
312 // the function returns true.
313 //
314 // If the block already has a bufferqueue assignment that does not match the
315 // given one, the block will be reassigned to the given bufferqueue. This
316 // will call attachBuffer() on the given igbp. The function then returns true on
317 // success or false on any failure during the operation.
318 //
319 // Note: This function should be called after detachBuffer() or dequeueBuffer()
320 // is called manually.
321 bool holdBufferQueueBlock(const C2ConstGraphicBlock& block,
322                           const sp<IGraphicBufferProducer>& igbp,
323                           uint64_t bqId,
324                           uint32_t generation);
325 
326 // Call holdBufferQueueBlock() on input or output blocks in the given workList.
327 // Since the bufferqueue assignment for input and output buffers can be
328 // different, this function takes forInput to determine whether the given
329 // bufferqueue is for input buffers or output buffers. (The default value of
330 // forInput is false.)
331 //
332 // In the (rare) case that both input and output buffers are bufferqueue-based,
333 // this function must be called twice, once for the input buffers and once for
334 // the output buffers.
335 //
336 // Note: This function should be called after WorkBundle has been received from
337 // another process.
338 void holdBufferQueueBlocks(const std::list<std::unique_ptr<C2Work>>& workList,
339                            const sp<IGraphicBufferProducer>& igbp,
340                            uint64_t bqId,
341                            uint32_t generation,
342                            bool forInput = false);
343 
344 }  // namespace utils
345 }  // namespace V1_0
346 }  // namespace c2
347 }  // namespace media
348 }  // namespace google
349 }  // namespace hardware
350 
351 #endif  // HARDWARE_GOOGLE_MEDIA_C2_V1_0_UTILS_TYPES_H
352