shithub: openh264

ref: cf92e8d6208af51fb55ed61554b135585ed33c1b
dir: /codec/encoder/core/inc/md.h/

View raw version
/*!
 * \copy
 *     Copyright (c)  2009-2013, Cisco Systems
 *     All rights reserved.
 *
 *     Redistribution and use in source and binary forms, with or without
 *     modification, are permitted provided that the following conditions
 *     are met:
 *
 *        * Redistributions of source code must retain the above copyright
 *          notice, this list of conditions and the following disclaimer.
 *
 *        * Redistributions in binary form must reproduce the above copyright
 *          notice, this list of conditions and the following disclaimer in
 *          the documentation and/or other materials provided with the
 *          distribution.
 *
 *     THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 *     "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 *     LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
 *     FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
 *     COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
 *     INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
 *     BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 *     LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
 *     CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 *     LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
 *     ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 *     POSSIBILITY OF SUCH DAMAGE.
 *
 *
 * \file	md.h
 *
 * \brief	mode decision 
 *
 * \date	2009.5.14 Created
 *
 *************************************************************************************
 */
#ifndef WELS_MACROBLOCK_MODE_DECISION_H__
#define WELS_MACROBLOCK_MODE_DECISION_H__

#include "svc_motion_estimate.h"
#include "svc_enc_macroblock.h"
#include "encode_mb_aux.h"
#include "wels_func_ptr_def.h"

namespace WelsSVCEnc {
#define ME_REFINE_BUF_STRIDE       32
#define ME_REFINE_BUF_WIDTH_BLK4   8
#define ME_REFINE_BUF_WIDTH_BLK8   16
#define ME_REFINE_BUF_STRIDE_BLK4  160
#define ME_REFINE_BUF_STRIDE_BLK8  320
	
#define REFINE_ME_NO_BEST_HALF_PIXEL 0 //( 0,  0)
#define REFINE_ME_HALF_PIXEL_LEFT    3 //(-2,  0)
#define REFINE_ME_HALF_PIXEL_RIGHT   4 //( 2,  0)
#define REFINE_ME_HALF_PIXEL_TOP     1 //( 0, -2)
#define REFINE_ME_HALF_PIXEL_BOTTOM  2 //( 0,  2)
	
#define ME_NO_BEST_QUAR_PIXEL 1 //( 0,  0) or best half pixel
#define ME_QUAR_PIXEL_LEFT    2 //(-1,  0)
#define ME_QUAR_PIXEL_RIGHT   3 //( 1,  0)
#define ME_QUAR_PIXEL_TOP     4 //( 0, -1)
#define ME_QUAR_PIXEL_BOTTOM  5 //( 0,  1)

#define NO_BEST_FRAC_PIX   1 // REFINE_ME_NO_BEST_HALF_PIXEL + ME_NO_BEST_QUAR_PIXEL

extern const int32_t g_kiQpCostTable[52];
extern const int8_t g_kiMapModeI16x16[7];
//extern const int8_t g_kiMapModeI4x4[14];
extern const int8_t g_kiMapModeIntraChroma[7];	

/////////////////////////////

// if we want keep total sizeof(SWelsMD) <= 256, we maybe need to seperate three member of SWelsME.
typedef struct TagWelsMD
{
    int32_t			iLambda;
	uint16_t		*pMvdCost;

	int32_t			iCostLuma;
    int32_t			iCostChroma;//satd+lambda(best_pred_mode) //i_sad_chroma;
	int32_t			iSadPredMb; 

    uint8_t			uiRef; //uiRefIndex appointed by Encoder, used for MC
    bool_t			bMdUsingSad;
    uint16_t		uiReserved;

	int32_t			iCostSkipMb;
    int32_t			iSadPredSkip;
    
	//NO B frame in our Wels, we can ignore list1

	struct 
	{		
		SWelsME			sMe16x16;		//adjust each SWelsME for 8 D-word!
		SWelsME			sMe8x8[4];
		SWelsME			sMe16x8[2];
		SWelsME			sMe8x16[2];				
//		SMVUnitXY		i_mvbs[MB_BLOCK8x8_NUM];	//scaled MVB
	} sMe;    

}SWelsMD;

typedef struct TagMeRefinePointer
{
	uint8_t* pHalfPixH;
	uint8_t* pHalfPixV;
	uint8_t* pHalfPixHV;

	uint8_t* pQuarPixBest;
	uint8_t* pQuarPixTmp; 

} SMeRefinePointer;

static void md_intra_init(sWelsEncCtx* pEncCtx, SWelsMD* pWelsMd, SMB* pCurMb);
static void md_inter_init(sWelsEncCtx* pEncCtx, SWelsMD* pWelsMd, SMB* pCurMb);

void FillNeighborCacheIntra(SMbCache* pMbCache, SMB* pCurMb, int32_t iMbWidth/*, bool_t constrained_intra_pred_flag*/);
void FillNeighborCacheInterWithoutBGD(SMbCache* pMbCache, SMB* pCurMb, int32_t iMbWidth, int8_t *pVaaBgMbFlag); //BGD spatial func
void FillNeighborCacheInterWithBGD(SMbCache* pMbCache, SMB* pCurMb, int32_t iMbWidth, int8_t *pVaaBgMbFlag);
void InitFillNeighborCacheInterFunc( SWelsFuncPtrList *pFuncList, const int32_t kiFlag );

void MvdCostInit( uint16_t* pMvdCostInter, const int32_t kiMvdSz );

void PredictSad( int8_t* pRefIndexCache, int32_t* pSadCostCache, int32_t uiRef, int32_t * pSadPred );


void PredictSadSkip( int8_t* pRefIndexCache, bool_t* pMbSkipCache, int32_t* pSadCostCache, int32_t uiRef, int32_t * iSadPredSkip );

//  for pfGetVarianceFromIntraVaa function ptr adaptive by CPU features, 6/7/2010
void InitIntraAnalysisVaaInfo( SWelsFuncPtrList *pFuncList, const uint32_t kuiCpuFlag );
BOOL_T MdIntraAnalysisVaaInfo( sWelsEncCtx* pEncCtx, uint8_t* pEncMb );

uint8_t MdInterAnalysisVaaInfo_c( int32_t *pSad8x8 );


void InitMeRefinePointer(SMeRefinePointer* pMeRefine, SMbCache* pMbCache, int32_t iStride);
void MeRefineFracPixel(sWelsEncCtx* pEncCtx, uint8_t* pMemPredInterMb, SWelsME* pMe,
						  SMeRefinePointer* pMeRefine, int32_t iWidth, int32_t iHeight);
								 
void InitBlkStrideWithRef(int32_t* pBlkStride, const int32_t kiStrideRef);

void UpdateMbMv_c( SMVUnitXY *pMvBuffer, const SMVUnitXY ksMv );

#if defined(__cplusplus)
extern "C" {
#endif//__cplusplus

#if defined(X86_ASM)

//  for pfGetVarianceFromIntraVaa SIMD optimization, 6/7/2010
int32_t AnalysisVaaInfoIntra_sse2 (	uint8_t *pDataY, const int32_t kiLineSize );
int32_t AnalysisVaaInfoIntra_ssse3(	uint8_t *pDataY, const int32_t kiLineSize );
uint8_t MdInterAnalysisVaaInfo_sse2( int32_t *pSad8x8 );
uint8_t MdInterAnalysisVaaInfo_sse41( int32_t *pSad8x8 );
void UpdateMbMv_sse2( SMVUnitXY *pMvBuffer, const SMVUnitXY ksMv );

#endif//X86_ASM

#if defined(__cplusplus)
}
#endif//__cplusplus

}
#endif//WELS_MACROBLOCK_MODE_DECISION_H__