/*
* 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_ENCODER_BASE_H__
#define __VIDEO_ENCODER_BASE_H__
#include <va/va.h>
#include <va/va_tpi.h>
#include "VideoEncoderDef.h"
#include "VideoEncoderInterface.h"
#include "IntelMetadataBuffer.h"
#include <utils/List.h>
#include <utils/threads.h>
#include "VideoEncoderUtils.h"
struct SurfaceMap {
VASurfaceID surface;
VASurfaceID surface_backup;
IntelMetadataBufferType type;
int32_t value;
ValueInfo vinfo;
bool added;
};
struct EncodeTask {
VASurfaceID enc_surface;
VASurfaceID ref_surface;
VASurfaceID rec_surface;
VABufferID coded_buffer;
FrameType type;
int flag;
int64_t timestamp; //corresponding input frame timestamp
void *priv; //input buffer data
bool completed; //if encode task is done complet by HW
};
class VideoEncoderBase : IVideoEncoder {
public:
VideoEncoderBase();
virtual ~VideoEncoderBase();
virtual Encode_Status start(void);
virtual void flush(void);
virtual Encode_Status stop(void);
virtual Encode_Status encode(VideoEncRawBuffer *inBuffer, uint32_t timeout);
/*
* getOutput can be called several time for a frame (such as first time codec data, and second time others)
* encoder will provide encoded data according to the format (whole frame, codec_data, sigle NAL etc)
* If the buffer passed to encoded is not big enough, this API call will return ENCODE_BUFFER_TOO_SMALL
* and caller should provide a big enough buffer and call again
*/
virtual Encode_Status getOutput(VideoEncOutputBuffer *outBuffer, uint32_t timeout);
virtual Encode_Status getParameters(VideoParamConfigSet *videoEncParams);
virtual Encode_Status setParameters(VideoParamConfigSet *videoEncParams);
virtual Encode_Status setConfig(VideoParamConfigSet *videoEncConfig);
virtual Encode_Status getConfig(VideoParamConfigSet *videoEncConfig);
virtual Encode_Status getMaxOutSize(uint32_t *maxSize);
protected:
virtual Encode_Status sendEncodeCommand(EncodeTask* task) = 0;
virtual Encode_Status derivedSetParams(VideoParamConfigSet *videoEncParams) = 0;
virtual Encode_Status derivedGetParams(VideoParamConfigSet *videoEncParams) = 0;
virtual Encode_Status derivedGetConfig(VideoParamConfigSet *videoEncConfig) = 0;
virtual Encode_Status derivedSetConfig(VideoParamConfigSet *videoEncConfig) = 0;
virtual Encode_Status getExtFormatOutput(VideoEncOutputBuffer *outBuffer) = 0;
virtual Encode_Status updateFrameInfo(EncodeTask* task) ;
Encode_Status renderDynamicFrameRate();
Encode_Status renderDynamicBitrate(EncodeTask* task);
Encode_Status renderHrd();
Encode_Status queryProfileLevelConfig(VADisplay dpy, VAProfile profile);
private:
void setDefaultParams(void);
Encode_Status setUpstreamBuffer(VideoParamsUpstreamBuffer *upStreamBuffer);
Encode_Status getNewUsrptrFromSurface(uint32_t width, uint32_t height, uint32_t format,
uint32_t expectedSize, uint32_t *outsize, uint32_t *stride, uint8_t **usrptr);
VASurfaceMap* findSurfaceMapByValue(intptr_t value);
Encode_Status manageSrcSurface(VideoEncRawBuffer *inBuffer, VASurfaceID *sid);
void PrepareFrameInfo(EncodeTask* task);
Encode_Status prepareForOutput(VideoEncOutputBuffer *outBuffer, bool *useLocalBuffer);
Encode_Status cleanupForOutput();
Encode_Status outputAllData(VideoEncOutputBuffer *outBuffer);
Encode_Status queryAutoReferenceConfig(VAProfile profile);
Encode_Status querySupportedSurfaceMemTypes();
Encode_Status copySurfaces(VASurfaceID srcId, VASurfaceID destId);
VASurfaceID CreateSurfaceFromExternalBuf(int32_t value, ValueInfo& vinfo);
protected:
bool mInitialized;
bool mStarted;
VADisplay mVADisplay;
VAContextID mVAContext;
VAConfigID mVAConfig;
VAEntrypoint mVAEntrypoint;
VideoParamsCommon mComParams;
VideoParamsHRD mHrdParam;
VideoParamsStoreMetaDataInBuffers mStoreMetaDataInBuffers;
bool mNewHeader;
bool mRenderMaxSliceSize; //Max Slice Size
bool mRenderQP;
bool mRenderAIR;
bool mRenderCIR;
bool mRenderFrameRate;
bool mRenderBitRate;
bool mRenderHrd;
bool mRenderMaxFrameSize;
bool mRenderMultiTemporal;
bool mForceKFrame;
VABufferID mSeqParamBuf;
VABufferID mRcParamBuf;
VABufferID mFrameRateParamBuf;
VABufferID mPicParamBuf;
VABufferID mSliceParamBuf;
VASurfaceID* mAutoRefSurfaces;
android::List <VASurfaceMap *> mSrcSurfaceMapList; //all mapped surface info list from input buffer
android::List <EncodeTask *> mEncodeTaskList; //all encode tasks list
android::List <VABufferID> mVACodedBufferList; //all available codedbuffer list
VASurfaceID mRefSurface; //reference surface, only used in base
VASurfaceID mRecSurface; //reconstructed surface, only used in base
uint32_t mFrameNum;
uint32_t mCodedBufSize;
bool mAutoReference;
uint32_t mAutoReferenceSurfaceNum;
uint32_t mEncPackedHeaders;
uint32_t mEncMaxRefFrames;
bool mSliceSizeOverflow;
//Current Outputting task
EncodeTask *mCurOutputTask;
//Current outputting CodedBuffer status
VABufferID mOutCodedBuffer;
bool mCodedBufferMapped;
uint8_t *mOutCodedBufferPtr;
VACodedBufferSegment *mCurSegment;
uint32_t mOffsetInSeg;
uint32_t mTotalSize;
uint32_t mTotalSizeCopied;
android::Mutex mCodedBuffer_Lock, mEncodeTask_Lock;
android::Condition mCodedBuffer_Cond, mEncodeTask_Cond;
bool mFrameSkipped;
//supported surface memory types
int mSupportedSurfaceMemType;
//VASurface mapping extra action
int mVASurfaceMappingAction;
// For Temporal Layer Bitrate FrameRate settings
VideoConfigTemperalLayerBitrateFramerate mTemporalLayerBitrateFramerate[3];
#ifdef INTEL_VIDEO_XPROC_SHARING
uint32_t mSessionFlag;
#endif
};
#endif /* __VIDEO_ENCODER_BASE_H__ */