1 /* 2 * Copyright (C) 2013 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 SOFT_VPX_ENCODER_H_ 18 19 #define SOFT_VPX_ENCODER_H_ 20 21 #include "SoftVideoEncoderOMXComponent.h" 22 23 #include <OMX_VideoExt.h> 24 #include <OMX_IndexExt.h> 25 26 #include <hardware/gralloc.h> 27 28 #include "vpx/vpx_encoder.h" 29 #include "vpx/vpx_codec.h" 30 #include "vpx/vp8cx.h" 31 32 namespace android { 33 34 // Exposes a vpx encoder as an OMX Component 35 // 36 // Boilerplate for callback bindings are taken care 37 // by the base class SimpleSoftOMXComponent and its 38 // parent SoftOMXComponent. 39 // 40 // Only following encoder settings are available 41 // - target bitrate 42 // - rate control (constant / variable) 43 // - frame rate 44 // - error resilience 45 // - token partitioning 46 // - reconstruction & loop filters (g_profile) 47 // 48 // Only following color formats are recognized 49 // - YUV420Planar 50 // - YUV420SemiPlanar 51 // - AndroidOpaque 52 // 53 // Following settings are not configurable by the client 54 // - encoding deadline is realtime 55 // - multithreaded encoding utilizes a number of threads equal 56 // to online cpu's available 57 // - the algorithm interface for encoder is vp8 58 // - fractional bits of frame rate is discarded 59 // - OMX timestamps are in microseconds, therefore 60 // encoder timebase is fixed to 1/1000000 61 62 struct SoftVPXEncoder : public SoftVideoEncoderOMXComponent { 63 SoftVPXEncoder(const char *name, 64 const OMX_CALLBACKTYPE *callbacks, 65 OMX_PTR appData, 66 OMX_COMPONENTTYPE **component); 67 68 protected: 69 virtual ~SoftVPXEncoder(); 70 71 // Returns current values for requested OMX 72 // parameters 73 virtual OMX_ERRORTYPE internalGetParameter( 74 OMX_INDEXTYPE index, OMX_PTR param); 75 76 // Validates, extracts and stores relevant OMX 77 // parameters 78 virtual OMX_ERRORTYPE internalSetParameter( 79 OMX_INDEXTYPE index, const OMX_PTR param); 80 81 virtual OMX_ERRORTYPE setConfig( 82 OMX_INDEXTYPE index, const OMX_PTR params); 83 84 // OMX callback when buffers available 85 // Note that both an input and output buffer 86 // is expected to be available to carry out 87 // encoding of the frame 88 virtual void onQueueFilled(OMX_U32 portIndex); 89 90 private: 91 enum TemporalReferences { 92 // For 1 layer case: reference all (last, golden, and alt ref), but only 93 // update last. 94 kTemporalUpdateLastRefAll = 12, 95 // First base layer frame for 3 temporal layers, which updates last and 96 // golden with alt ref dependency. 97 kTemporalUpdateLastAndGoldenRefAltRef = 11, 98 // First enhancement layer with alt ref dependency. 99 kTemporalUpdateGoldenRefAltRef = 10, 100 // First enhancement layer with alt ref dependency. 101 kTemporalUpdateGoldenWithoutDependencyRefAltRef = 9, 102 // Base layer with alt ref dependency. 103 kTemporalUpdateLastRefAltRef = 8, 104 // Highest enhacement layer without dependency on golden with alt ref 105 // dependency. 106 kTemporalUpdateNoneNoRefGoldenRefAltRef = 7, 107 // Second layer and last frame in cycle, for 2 layers. 108 kTemporalUpdateNoneNoRefAltref = 6, 109 // Highest enhancement layer. 110 kTemporalUpdateNone = 5, 111 // Second enhancement layer. 112 kTemporalUpdateAltref = 4, 113 // Second enhancement layer without dependency on previous frames in 114 // the second enhancement layer. 115 kTemporalUpdateAltrefWithoutDependency = 3, 116 // First enhancement layer. 117 kTemporalUpdateGolden = 2, 118 // First enhancement layer without dependency on previous frames in 119 // the first enhancement layer. 120 kTemporalUpdateGoldenWithoutDependency = 1, 121 // Base layer. 122 kTemporalUpdateLast = 0, 123 }; 124 enum { 125 kMaxTemporalPattern = 8 126 }; 127 128 // number of buffers allocated per port 129 static const uint32_t kNumBuffers = 4; 130 131 // OMX port indexes that refer to input and 132 // output ports respectively 133 static const uint32_t kInputPortIndex = 0; 134 static const uint32_t kOutputPortIndex = 1; 135 136 // Byte-alignment required for buffers 137 static const uint32_t kInputBufferAlignment = 1; 138 static const uint32_t kOutputBufferAlignment = 2; 139 140 // Max value supported for DCT partitions 141 static const uint32_t kMaxDCTPartitions = 3; 142 143 // Number of supported input color formats 144 static const uint32_t kNumberOfSupportedColorFormats = 3; 145 146 // vpx specific opaque data structure that 147 // stores encoder state 148 vpx_codec_ctx_t* mCodecContext; 149 150 // vpx specific data structure that 151 // stores encoder configuration 152 vpx_codec_enc_cfg_t* mCodecConfiguration; 153 154 // vpx specific read-only data structure 155 // that specifies algorithm interface (e.g. vp8) 156 vpx_codec_iface_t* mCodecInterface; 157 158 // If a request for a change it bitrate has been received. 159 bool mBitrateUpdated; 160 161 // Bitrate control mode, either constant or variable 162 vpx_rc_mode mBitrateControlMode; 163 164 // vp8 specific configuration parameter 165 // that enables token partitioning of 166 // the stream into substreams 167 int32_t mDCTPartitions; 168 169 // Parameter that denotes whether error resilience 170 // is enabled in encoder 171 OMX_BOOL mErrorResilience; 172 173 // Encoder profile corresponding to OMX level parameter 174 // 175 // The inconsistency in the naming is caused by 176 // OMX spec referring vpx profiles (g_profile) 177 // as "levels" whereas using the name "profile" for 178 // something else. 179 OMX_VIDEO_VP8LEVELTYPE mLevel; 180 181 // Key frame interval in frames 182 uint32_t mKeyFrameInterval; 183 184 // Minimum (best quality) quantizer 185 uint32_t mMinQuantizer; 186 187 // Maximum (worst quality) quantizer 188 uint32_t mMaxQuantizer; 189 190 // Number of coding temporal layers to be used. 191 size_t mTemporalLayers; 192 193 // Temporal layer bitrare ratio in percentage 194 uint32_t mTemporalLayerBitrateRatio[OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS]; 195 196 // Temporal pattern type 197 OMX_VIDEO_ANDROID_VPXTEMPORALLAYERPATTERNTYPE mTemporalPatternType; 198 199 // Temporal pattern length 200 size_t mTemporalPatternLength; 201 202 // Temporal pattern current index 203 size_t mTemporalPatternIdx; 204 205 // Frame type temporal pattern 206 TemporalReferences mTemporalPattern[kMaxTemporalPattern]; 207 208 // Last input buffer timestamp 209 OMX_TICKS mLastTimestamp; 210 211 // Conversion buffer is needed to convert semi 212 // planar yuv420 to planar format 213 // It is only allocated if input format is 214 // indeed YUV420SemiPlanar. 215 uint8_t* mConversionBuffer; 216 217 bool mKeyFrameRequested; 218 219 // Initializes vpx encoder with available settings. 220 status_t initEncoder(); 221 222 // Releases vpx encoder instance, with it's associated 223 // data structures. 224 // 225 // Unless called earlier, this is handled by the 226 // dtor. 227 status_t releaseEncoder(); 228 229 // Get current encode flags 230 vpx_enc_frame_flags_t getEncodeFlags(); 231 232 // Updates bitrate to reflect port settings. 233 OMX_ERRORTYPE internalSetBitrateParams( 234 const OMX_VIDEO_PARAM_BITRATETYPE* bitrate); 235 236 // Handles vp8 specific parameters. 237 OMX_ERRORTYPE internalSetVp8Params( 238 const OMX_VIDEO_PARAM_VP8TYPE* vp8Params); 239 240 // Handles Android vp8 specific parameters. 241 OMX_ERRORTYPE internalSetAndroidVp8Params( 242 const OMX_VIDEO_PARAM_ANDROID_VP8ENCODERTYPE* vp8AndroidParams); 243 244 DISALLOW_EVIL_CONSTRUCTORS(SoftVPXEncoder); 245 }; 246 247 } // namespace android 248 249 #endif // SOFT_VPX_ENCODER_H_ 250