| /* |
| * Copyright (c) 2009-2011 Intel Corporation. All rights reserved. |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| #ifndef VIDEO_DECODER_BASE_H_ |
| #define VIDEO_DECODER_BASE_H_ |
| |
| #include <va/va.h> |
| #include <va/va_tpi.h> |
| #include "VideoDecoderDefs.h" |
| #include "VideoDecoderInterface.h" |
| #include <pthread.h> |
| #include <dlfcn.h> |
| |
| extern "C" { |
| #include "vbp_loader.h" |
| } |
| |
| #ifndef Display |
| #ifdef USE_GEN_HW |
| typedef char Display; |
| #else |
| typedef unsigned int Display; |
| #endif |
| #endif |
| |
| // TODO: check what is the best number. Must be at least 2 to support one backward reference frame. |
| // Currently set to 8 to support 7 backward reference frames. This value is used for AVC frame reordering only. |
| // e.g: |
| // POC: 4P, 8P, 10P, 6B and mNextOutputPOC = 5 |
| #define OUTPUT_WINDOW_SIZE 8 |
| |
| /* |
| * ITU-R BT.601, BT.709 transfer matrices from VA 2.0 |
| * Video Color Field definitions Design Spec(Version 0.03). |
| * [R', G', B'] values are in the range [0, 1], Y' is in the range [0,1] |
| * and [Pb, Pr] components are in the range [-0.5, 0.5]. |
| */ |
| static float s601[9] = { |
| 1, -0.000001, 1.402, |
| 1, -0.344136, -0.714136, |
| 1, 1.772, 0 |
| }; |
| |
| static float s709[9] = { |
| 1, 0, 1.5748, |
| 1, -0.187324, -0.468124, |
| 1, 1.8556, 0 |
| }; |
| |
| class VideoDecoderBase : public IVideoDecoder { |
| public: |
| VideoDecoderBase(const char *mimeType, _vbp_parser_type type); |
| virtual ~VideoDecoderBase(); |
| |
| virtual Decode_Status start(VideoConfigBuffer *buffer); |
| virtual Decode_Status reset(VideoConfigBuffer *buffer) ; |
| virtual void stop(void); |
| //virtual Decode_Status decode(VideoDecodeBuffer *buffer); |
| virtual void flush(void); |
| virtual void freeSurfaceBuffers(void); |
| virtual const VideoRenderBuffer* getOutput(bool draining = false, VideoErrorBuffer *output_buf = NULL); |
| virtual Decode_Status signalRenderDone(void * graphichandler, bool isNew = false); |
| virtual const VideoFormatInfo* getFormatInfo(void); |
| virtual bool checkBufferAvail(); |
| virtual void enableErrorReport(bool enabled = false) {mErrReportEnabled = enabled; }; |
| virtual int getOutputQueueLength(void); |
| |
| protected: |
| // each acquireSurfaceBuffer must be followed by a corresponding outputSurfaceBuffer or releaseSurfaceBuffer. |
| // Only one surface buffer can be acquired at any given time |
| virtual Decode_Status acquireSurfaceBuffer(void); |
| // frame is successfully decoded to the acquired surface buffer and surface is ready for output |
| virtual Decode_Status outputSurfaceBuffer(void); |
| // acquired surface buffer is not used |
| virtual Decode_Status releaseSurfaceBuffer(void); |
| // flush all decoded but not rendered buffers |
| virtual void flushSurfaceBuffers(void); |
| virtual Decode_Status endDecodingFrame(bool dropFrame); |
| virtual VideoSurfaceBuffer* findOutputByPoc(bool draining = false); |
| virtual VideoSurfaceBuffer* findOutputByPct(bool draining = false); |
| virtual VideoSurfaceBuffer* findOutputByPts(); |
| virtual Decode_Status setupVA(uint32_t numSurface, VAProfile profile, uint32_t numExtraSurface = 0); |
| virtual Decode_Status terminateVA(void); |
| virtual Decode_Status parseBuffer(uint8_t *buffer, int32_t size, bool config, void** vbpData); |
| |
| static inline uint32_t alignMB(uint32_t a) { |
| return ((a + 15) & (~15)); |
| } |
| |
| virtual Decode_Status getRawDataFromSurface(VideoRenderBuffer *renderBuffer = NULL, uint8_t *pRawData = NULL, uint32_t *pSize = NULL, bool internal = true); |
| |
| #if (defined USE_AVC_SHORT_FORMAT) || (defined USE_SLICE_HEADER_PARSING) |
| Decode_Status updateBuffer(uint8_t *buffer, int32_t size, void** vbpData); |
| Decode_Status queryBuffer(void **vbpData); |
| Decode_Status setParserType(_vbp_parser_type type); |
| virtual Decode_Status getCodecSpecificConfigs(VAProfile profile, VAConfigID *config); |
| #endif |
| virtual Decode_Status checkHardwareCapability(); |
| Decode_Status createSurfaceFromHandle(int32_t index); |
| private: |
| Decode_Status mapSurface(void); |
| void initSurfaceBuffer(bool reset); |
| void drainDecodingErrors(VideoErrorBuffer *outErrBuf, VideoRenderBuffer *currentSurface); |
| void fillDecodingErrors(VideoRenderBuffer *currentSurface); |
| |
| bool mInitialized; |
| pthread_mutex_t mLock; |
| |
| protected: |
| bool mLowDelay; // when true, decoded frame is immediately output for rendering |
| bool mStoreMetaData; // when true, meta data mode is enabled for adaptive playback |
| VideoFormatInfo mVideoFormatInfo; |
| Display *mDisplay; |
| VADisplay mVADisplay; |
| VAContextID mVAContext; |
| VAConfigID mVAConfig; |
| VASurfaceID *mExtraSurfaces; // extra surfaces array |
| int32_t mNumExtraSurfaces; |
| bool mVAStarted; |
| uint64_t mCurrentPTS; // current presentation time stamp (unit is unknown, depend on the framework: GStreamer 100-nanosec, Android: microsecond) |
| // the following three member variables should be set using |
| // acquireSurfaceBuffer/outputSurfaceBuffer/releaseSurfaceBuffer |
| VideoSurfaceBuffer *mAcquiredBuffer; |
| VideoSurfaceBuffer *mLastReference; |
| VideoSurfaceBuffer *mForwardReference; |
| VideoConfigBuffer mConfigBuffer; // only store configure meta data. |
| bool mDecodingFrame; // indicate whether a frame is being decoded |
| bool mSizeChanged; // indicate whether video size is changed. |
| bool mShowFrame; // indicate whether the decoded frame is for display |
| |
| int32_t mOutputWindowSize; // indicate limit of number of outstanding frames for output |
| int32_t mRotationDegrees; |
| pthread_mutex_t mFormatLock; |
| |
| bool mErrReportEnabled; |
| bool mWiDiOn; |
| typedef uint32_t (*OpenFunc)(uint32_t, void **); |
| typedef uint32_t (*CloseFunc)(void *); |
| typedef uint32_t (*ParseFunc)(void *, uint8_t *, uint32_t, uint8_t); |
| typedef uint32_t (*QueryFunc)(void *, void **); |
| typedef uint32_t (*FlushFunc)(void *); |
| typedef uint32_t (*UpdateFunc)(void *, void *, uint32_t, void **); |
| void *mLibHandle; |
| OpenFunc mParserOpen; |
| CloseFunc mParserClose; |
| ParseFunc mParserParse; |
| QueryFunc mParserQuery; |
| FlushFunc mParserFlush; |
| UpdateFunc mParserUpdate; |
| enum { |
| // TODO: move this to vbp_loader.h |
| VBP_INVALID = 0xFF, |
| // TODO: move this to va.h |
| VAProfileSoftwareDecoding = 0xFF, |
| }; |
| |
| enum OUTPUT_METHOD { |
| // output by Picture Coding Type (I, P, B) |
| OUTPUT_BY_PCT, |
| // output by Picture Order Count (for AVC only) |
| OUTPUT_BY_POC, |
| //OUTPUT_BY_POS, |
| //OUTPUT_BY_PTS, |
| }; |
| |
| private: |
| bool mRawOutput; // whether to output NV12 raw data |
| bool mManageReference; // this should stay true for VC1/MP4 decoder, and stay false for AVC decoder. AVC handles reference frame using DPB |
| OUTPUT_METHOD mOutputMethod; |
| |
| int32_t mNumSurfaces; |
| VideoSurfaceBuffer *mSurfaceBuffers; |
| VideoSurfaceBuffer *mOutputHead; // head of output buffer list |
| VideoSurfaceBuffer *mOutputTail; // tail of output buffer list |
| VASurfaceID *mSurfaces; // surfaces array |
| VASurfaceAttribExternalBuffers *mVASurfaceAttrib; |
| uint8_t **mSurfaceUserPtr; // mapped user space pointer |
| int32_t mSurfaceAcquirePos; // position of surface to start acquiring |
| int32_t mNextOutputPOC; // Picture order count of next output |
| _vbp_parser_type mParserType; |
| void *mParserHandle; |
| void *mSignalBufferPre[MAX_GRAPHIC_BUFFER_NUM]; |
| uint32 mSignalBufferSize; |
| bool mUseGEN; |
| uint32_t mMetaDataBuffersNum; |
| protected: |
| void ManageReference(bool enable) {mManageReference = enable;} |
| void setOutputMethod(OUTPUT_METHOD method) {mOutputMethod = method;} |
| void setOutputWindowSize(int32_t size) {mOutputWindowSize = (size < OUTPUT_WINDOW_SIZE) ? size : OUTPUT_WINDOW_SIZE;} |
| void querySurfaceRenderStatus(VideoSurfaceBuffer* surface); |
| void enableLowDelayMode(bool enable) {mLowDelay = enable;} |
| void setRotationDegrees(int32_t rotationDegrees); |
| void setRenderRect(void); |
| void setColorSpaceInfo(int32_t colorMatrix, int32_t videoRange); |
| }; |
| |
| |
| #endif // VIDEO_DECODER_BASE_H_ |