SoftVPXEncoder.h revision a0a63e13788a77bc502da0c72269d82c4779ac91
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 "SimpleSoftOMXComponent.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
32namespace 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
62struct SoftVPXEncoder : public SimpleSoftOMXComponent {
63    SoftVPXEncoder(const char *name,
64                   const OMX_CALLBACKTYPE *callbacks,
65                   OMX_PTR appData,
66                   OMX_COMPONENTTYPE **component);
67
68protected:
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    // OMX callback when buffers available
82    // Note that both an input and output buffer
83    // is expected to be available to carry out
84    // encoding of the frame
85    virtual void onQueueFilled(OMX_U32 portIndex);
86
87    virtual OMX_ERRORTYPE getExtensionIndex(
88            const char *name, OMX_INDEXTYPE *index);
89
90private:
91    // number of buffers allocated per port
92    static const uint32_t kNumBuffers = 4;
93
94    // OMX port indexes that refer to input and
95    // output ports respectively
96    static const uint32_t kInputPortIndex = 0;
97    static const uint32_t kOutputPortIndex = 1;
98
99    // Byte-alignment required for buffers
100    static const uint32_t kInputBufferAlignment = 1;
101    static const uint32_t kOutputBufferAlignment = 2;
102
103    // Max value supported for DCT partitions
104    static const uint32_t kMaxDCTPartitions = 3;
105
106    // Number of supported input color formats
107    static const uint32_t kNumberOfSupportedColorFormats = 3;
108
109    // vpx specific opaque data structure that
110    // stores encoder state
111    vpx_codec_ctx_t* mCodecContext;
112
113    // vpx specific data structure that
114    // stores encoder configuration
115    vpx_codec_enc_cfg_t* mCodecConfiguration;
116
117    // vpx specific read-only data structure
118    // that specifies algorithm interface (e.g. vp8)
119    vpx_codec_iface_t* mCodecInterface;
120
121    // Width of the input frames
122    int32_t mWidth;
123
124    // Height of the input frames
125    int32_t mHeight;
126
127    // Target bitrate set for the encoder, in bits per second.
128    int32_t mBitrate;
129
130    // Bitrate control mode, either constant or variable
131    vpx_rc_mode mBitrateControlMode;
132
133    // Frame duration is the reciprocal of framerate, denoted
134    // in microseconds
135    uint64_t mFrameDurationUs;
136
137    // vp8 specific configuration parameter
138    // that enables token partitioning of
139    // the stream into substreams
140    int32_t mDCTPartitions;
141
142    // Parameter that denotes whether error resilience
143    // is enabled in encoder
144    OMX_BOOL mErrorResilience;
145
146    // Color format for the input port
147    OMX_COLOR_FORMATTYPE mColorFormat;
148
149    // Encoder profile corresponding to OMX level parameter
150    //
151    // The inconsistency in the naming is caused by
152    // OMX spec referring vpx profiles (g_profile)
153    // as "levels" whereas using the name "profile" for
154    // something else.
155    OMX_VIDEO_VP8LEVELTYPE mLevel;
156
157    // Conversion buffer is needed to convert semi
158    // planar yuv420 to planar format
159    // It is only allocated if input format is
160    // indeed YUV420SemiPlanar.
161    uint8_t* mConversionBuffer;
162
163    bool mInputDataIsMeta;
164    const hw_module_t *mGrallocModule;
165
166    // Initializes input and output OMX ports with sensible
167    // default values.
168    void initPorts();
169
170    // Initializes vpx encoder with available settings.
171    status_t initEncoder();
172
173    // Releases vpx encoder instance, with it's associated
174    // data structures.
175    //
176    // Unless called earlier, this is handled by the
177    // dtor.
178    status_t releaseEncoder();
179
180    // Handles port changes with respect to color formats
181    OMX_ERRORTYPE internalSetFormatParams(
182        const OMX_VIDEO_PARAM_PORTFORMATTYPE* format);
183
184    // Verifies the component role tried to be set to this OMX component is
185    // strictly video_encoder.vp8
186    OMX_ERRORTYPE internalSetRoleParams(
187        const OMX_PARAM_COMPONENTROLETYPE* role);
188
189    // Updates bitrate to reflect port settings.
190    OMX_ERRORTYPE internalSetBitrateParams(
191        const OMX_VIDEO_PARAM_BITRATETYPE* bitrate);
192
193    // Handles port definition changes.
194    OMX_ERRORTYPE internalSetPortParams(
195        const OMX_PARAM_PORTDEFINITIONTYPE* port);
196
197    // Handles vp8 specific parameters.
198    OMX_ERRORTYPE internalSetVp8Params(
199        const OMX_VIDEO_PARAM_VP8TYPE* vp8Params);
200
201    // Updates encoder profile
202    OMX_ERRORTYPE internalSetProfileLevel(
203        const OMX_VIDEO_PARAM_PROFILELEVELTYPE* profileAndLevel);
204
205    DISALLOW_EVIL_CONSTRUCTORS(SoftVPXEncoder);
206};
207
208}  // namespace android
209
210#endif  // SOFT_VPX_ENCODER_H_
211