1 /* 2 * Copyright 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 CODEC2_HIDL_V1_0_UTILS_TYPES_H 18 #define CODEC2_HIDL_V1_0_UTILS_TYPES_H 19 20 #include <bufferpool/ClientManager.h> 21 #include <android/hardware/media/bufferpool/2.0/IClientManager.h> 22 #include <android/hardware/media/bufferpool/2.0/types.h> 23 #include <android/hardware/media/c2/1.0/IComponentStore.h> 24 #include <android/hardware/media/c2/1.0/types.h> 25 #include <android/hidl/safe_union/1.0/types.h> 26 27 #include <C2Component.h> 28 #include <C2Param.h> 29 #include <C2ParamDef.h> 30 #include <C2Work.h> 31 #include <util/C2Debug-base.h> 32 33 #include <chrono> 34 35 using namespace std::chrono_literals; 36 37 namespace android { 38 namespace hardware { 39 namespace media { 40 namespace c2 { 41 namespace V1_0 { 42 namespace utils { 43 44 using ::android::hardware::hidl_bitfield; 45 using ::android::hardware::hidl_handle; 46 using ::android::hardware::hidl_string; 47 using ::android::hardware::hidl_vec; 48 using ::android::status_t; 49 using ::android::sp; 50 using ::android::hardware::media::bufferpool::V2_0::implementation:: 51 ConnectionId; 52 53 // Types of metadata for Blocks. 54 struct C2Hidl_Range { 55 uint32_t offset; 56 uint32_t length; // Do not use "size" because the name collides with C2Info::size(). 57 }; 58 typedef C2GlobalParam<C2Info, C2Hidl_Range, 0> C2Hidl_RangeInfo; 59 60 struct C2Hidl_Rect { 61 uint32_t left; 62 uint32_t top; 63 uint32_t width; 64 uint32_t height; 65 }; 66 typedef C2GlobalParam<C2Info, C2Hidl_Rect, 1> C2Hidl_RectInfo; 67 68 // Make asString() and operator<< work with Status as well as c2_status_t. 69 C2_DECLARE_AS_STRING_AND_DEFINE_STREAM_OUT(Status); 70 71 /** 72 * All objcpy() functions will return a boolean value indicating whether the 73 * conversion succeeds or not. 74 */ 75 76 // C2SettingResult -> SettingResult 77 bool objcpy( 78 SettingResult* d, 79 const C2SettingResult& s); 80 81 // SettingResult -> std::unique_ptr<C2SettingResult> 82 bool objcpy( 83 std::unique_ptr<C2SettingResult>* d, 84 const SettingResult& s); 85 86 // C2ParamDescriptor -> ParamDescriptor 87 bool objcpy( 88 ParamDescriptor* d, 89 const C2ParamDescriptor& s); 90 91 // ParamDescriptor -> std::shared_ptr<C2ParamDescriptor> 92 bool objcpy( 93 std::shared_ptr<C2ParamDescriptor>* d, 94 const ParamDescriptor& s); 95 96 // C2FieldSupportedValuesQuery -> FieldSupportedValuesQuery 97 bool objcpy( 98 FieldSupportedValuesQuery* d, 99 const C2FieldSupportedValuesQuery& s); 100 101 // FieldSupportedValuesQuery -> C2FieldSupportedValuesQuery 102 bool objcpy( 103 C2FieldSupportedValuesQuery* d, 104 const FieldSupportedValuesQuery& s); 105 106 // C2FieldSupportedValuesQuery -> FieldSupportedValuesQueryResult 107 bool objcpy( 108 FieldSupportedValuesQueryResult* d, 109 const C2FieldSupportedValuesQuery& s); 110 111 // FieldSupportedValuesQuery, FieldSupportedValuesQueryResult -> C2FieldSupportedValuesQuery 112 bool objcpy( 113 C2FieldSupportedValuesQuery* d, 114 const FieldSupportedValuesQuery& sq, 115 const FieldSupportedValuesQueryResult& sr); 116 117 // C2Component::Traits -> ComponentTraits 118 bool objcpy( 119 IComponentStore::ComponentTraits* d, 120 const C2Component::Traits& s); 121 122 // ComponentTraits -> C2Component::Traits 123 bool objcpy( 124 C2Component::Traits* d, 125 const IComponentStore::ComponentTraits& s); 126 127 // C2StructDescriptor -> StructDescriptor 128 bool objcpy( 129 StructDescriptor* d, 130 const C2StructDescriptor& s); 131 132 // StructDescriptor -> C2StructDescriptor 133 bool objcpy( 134 std::unique_ptr<C2StructDescriptor>* d, 135 const StructDescriptor& s); 136 137 // Abstract class to be used in 138 // objcpy(std::list<std::unique_ptr<C2Work>> -> WorkBundle). 139 struct BufferPoolSender { 140 typedef ::android::hardware::media::bufferpool::V2_0:: 141 ResultStatus ResultStatus; 142 typedef ::android::hardware::media::bufferpool::V2_0:: 143 BufferStatusMessage BufferStatusMessage; 144 typedef ::android::hardware::media::bufferpool:: 145 BufferPoolData BufferPoolData; 146 147 /** 148 * Send bpData and return BufferStatusMessage that can be supplied to 149 * IClientManager::receive() in the receiving process. 150 * 151 * This function will be called from within the function 152 * objcpy(std::list<std::unique_ptr<C2Work>> -> WorkBundle). 153 * 154 * \param[in] bpData BufferPoolData identifying the buffer to send. 155 * \param[out] bpMessage BufferStatusMessage of the transaction. Information 156 * inside \p bpMessage should be passed to the receiving process by some 157 * other means so it can call receive() properly. 158 * \return ResultStatus value that determines the success of the operation. 159 * (See the possible values of ResultStatus in 160 * hardware/interfaces/media/bufferpool/2.0/types.hal.) 161 */ 162 virtual ResultStatus send( 163 const std::shared_ptr<BufferPoolData>& bpData, 164 BufferStatusMessage* bpMessage) = 0; 165 166 virtual ~BufferPoolSender() = default; 167 }; 168 169 // Default implementation of BufferPoolSender. 170 // 171 // To use DefaultBufferPoolSender, the IClientManager instance of the receiving 172 // process must be set before send() can operate. DefaultBufferPoolSender will 173 // hold a strong reference to the IClientManager instance and use it to call 174 // IClientManager::registerSender() to establish the bufferpool connection when 175 // send() is called. 176 struct DefaultBufferPoolSender : BufferPoolSender { 177 typedef ::android::hardware::media::bufferpool::V2_0::implementation:: 178 ClientManager ClientManager; 179 typedef ::android::hardware::media::bufferpool::V2_0:: 180 IClientManager IClientManager; 181 182 // Set the IClientManager instance of the receiving process and the refresh 183 // interval for the connection. The default interval is 4.5 seconds, which 184 // is slightly shorter than the amount of time the bufferpool will keep an 185 // inactive connection for. 186 DefaultBufferPoolSender( 187 const sp<IClientManager>& receiverManager = nullptr, 188 std::chrono::steady_clock::duration refreshInterval = 4500ms); 189 190 // Set the IClientManager instance of the receiving process and the refresh 191 // interval for the connection. The default interval is 4.5 seconds, which 192 // is slightly shorter than the amount of time the bufferpool will keep an 193 // inactive connection for. 194 void setReceiver( 195 const sp<IClientManager>& receiverManager, 196 std::chrono::steady_clock::duration refreshInterval = 4500ms); 197 198 // Implementation of BufferPoolSender::send(). send() will establish a 199 // bufferpool connection if needed, then send the bufferpool data over to 200 // the receiving process. 201 virtual ResultStatus send( 202 const std::shared_ptr<BufferPoolData>& bpData, 203 BufferStatusMessage* bpMessage) override; 204 205 private: 206 std::mutex mMutex; 207 sp<ClientManager> mSenderManager; 208 sp<IClientManager> mReceiverManager; 209 int64_t mReceiverConnectionId; 210 int64_t mSourceConnectionId; 211 std::chrono::steady_clock::time_point mLastSent; 212 std::chrono::steady_clock::duration mRefreshInterval; 213 }; 214 215 // std::list<std::unique_ptr<C2Work>> -> WorkBundle 216 // Note: If bufferpool will be used, bpSender must not be null. 217 bool objcpy( 218 WorkBundle* d, 219 const std::list<std::unique_ptr<C2Work>>& s, 220 BufferPoolSender* bpSender = nullptr); 221 222 // WorkBundle -> std::list<std::unique_ptr<C2Work>> 223 bool objcpy( 224 std::list<std::unique_ptr<C2Work>>* d, 225 const WorkBundle& s); 226 227 /** 228 * Parses a params blob and returns C2Param pointers to its params. The pointers 229 * point to locations inside the underlying buffer of \p blob. If \p blob is 230 * destroyed, the pointers become invalid. 231 * 232 * \param[out] params target vector of C2Param pointers 233 * \param[in] blob parameter blob to parse 234 * \retval true if the full blob was parsed 235 * \retval false otherwise 236 */ 237 bool parseParamsBlob( 238 std::vector<C2Param*> *params, 239 const hidl_vec<uint8_t> &blob); 240 241 /** 242 * Concatenates a list of C2Params into a params blob. 243 * 244 * \param[out] blob target blob 245 * \param[in] params parameters to concatenate 246 * \retval true if the blob was successfully created 247 * \retval false if the blob was not successful (this only happens if the 248 * parameters were not const) 249 */ 250 bool createParamsBlob( 251 hidl_vec<uint8_t> *blob, 252 const std::vector<C2Param*> ¶ms); 253 bool createParamsBlob( 254 hidl_vec<uint8_t> *blob, 255 const std::vector<std::unique_ptr<C2Param>> ¶ms); 256 bool createParamsBlob( 257 hidl_vec<uint8_t> *blob, 258 const std::vector<std::shared_ptr<const C2Info>> ¶ms); 259 bool createParamsBlob( 260 hidl_vec<uint8_t> *blob, 261 const std::vector<std::unique_ptr<C2Tuning>> ¶ms); 262 263 /** 264 * Parses a params blob and create a vector of C2Params whose members are copies 265 * of the params in the blob. 266 * 267 * \param[out] params the resulting vector 268 * \param[in] blob parameter blob to parse 269 * \retval true if the full blob was parsed and params was constructed 270 * \retval false otherwise 271 */ 272 bool copyParamsFromBlob( 273 std::vector<std::unique_ptr<C2Param>>* params, 274 Params blob); 275 bool copyParamsFromBlob( 276 std::vector<std::unique_ptr<C2Tuning>>* params, 277 Params blob); 278 279 /** 280 * Parses a params blob and applies updates to params. 281 * 282 * \param[in,out] params params to be updated 283 * \param[in] blob parameter blob containing updates 284 * \retval true if the full blob was parsed and params was updated 285 * \retval false otherwise 286 */ 287 bool updateParamsFromBlob( 288 const std::vector<C2Param*>& params, 289 const Params& blob); 290 291 /** 292 * Converts a BufferPool status value to c2_status_t. 293 * \param BufferPool status 294 * \return Corresponding c2_status_t 295 */ 296 c2_status_t toC2Status(::android::hardware::media::bufferpool::V2_0:: 297 ResultStatus rs); 298 299 // BufferQueue-Based Block Operations 300 // ================================== 301 302 // Call before transferring block to other processes. 303 // 304 // The given block is ready to transfer to other processes. This will guarantee 305 // the given block data is not mutated by bufferqueue migration. 306 bool beginTransferBufferQueueBlock(const C2ConstGraphicBlock& block); 307 308 // Call beginTransferBufferQueueBlock() on blocks in the given workList. 309 // processInput determines whether input blocks are yielded. processOutput 310 // works similarly on output blocks. (The default value of processInput is 311 // false while the default value of processOutput is true. This implies that in 312 // most cases, only output buffers contain bufferqueue-based blocks.) 313 void beginTransferBufferQueueBlocks( 314 const std::list<std::unique_ptr<C2Work>>& workList, 315 bool processInput = false, 316 bool processOutput = true); 317 318 // Call after transferring block is finished and make sure that 319 // beginTransferBufferQueueBlock() is called before. 320 // 321 // The transfer of given block is finished. If transfer is successful the given 322 // block is not owned by process anymore. Since transfer is finished the given 323 // block data is OK to mutate by bufferqueue migration after this call. 324 bool endTransferBufferQueueBlock(const C2ConstGraphicBlock& block, 325 bool transfer); 326 327 // Call endTransferBufferQueueBlock() on blocks in the given workList. 328 // processInput determines whether input blocks are yielded. processOutput 329 // works similarly on output blocks. (The default value of processInput is 330 // false while the default value of processOutput is true. This implies that in 331 // most cases, only output buffers contain bufferqueue-based blocks.) 332 void endTransferBufferQueueBlocks( 333 const std::list<std::unique_ptr<C2Work>>& workList, 334 bool transfer, 335 bool processInput = false, 336 bool processOutput = true); 337 338 // The given block is ready to be rendered. the given block is not owned by 339 // process anymore. If migration is in progress, this returns false in order 340 // not to render. 341 bool displayBufferQueueBlock(const C2ConstGraphicBlock& block); 342 343 } // namespace utils 344 } // namespace V1_0 345 } // namespace c2 346 } // namespace media 347 } // namespace hardware 348 } // namespace android 349 350 #endif // CODEC2_HIDL_V1_0_UTILS_TYPES_H 351