Home | History | Annotate | Download | only in src
      1 /*
      2  * Copyright (c) 2011 Intel Corporation. All Rights Reserved.
      3  * Copyright (c) Imagination Technologies Limited, UK
      4  *
      5  * Permission is hereby granted, free of charge, to any person obtaining a
      6  * copy of this software and associated documentation files (the
      7  * "Software"), to deal in the Software without restriction, including
      8  * without limitation the rights to use, copy, modify, merge, publish,
      9  * distribute, sub license, and/or sell copies of the Software, and to
     10  * permit persons to whom the Software is furnished to do so, subject to
     11  * the following conditions:
     12  *
     13  * The above copyright notice and this permission notice (including the
     14  * next paragraph) shall be included in all copies or substantial portions
     15  * of the Software.
     16  *
     17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
     18  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
     19  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
     20  * IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
     21  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
     22  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
     23  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
     24  *
     25  * Authors:
     26  *    Elaine Wang <elaine.wang (at) intel.com>
     27  *    Zeng Li <zeng.li (at) intel.com>
     28  *    Edward Lin <edward.lin (at) intel.com>
     29  *
     30  */
     31 
     32 #include <errno.h>
     33 #include <stdlib.h>
     34 #include <unistd.h>
     35 #include <stdint.h>
     36 #include <string.h>
     37 #include <limits.h>
     38 
     39 #include "hwdefs/coreflags.h"
     40 #include "hwdefs/topaz_vlc_regs.h"
     41 #include "hwdefs/topaz_db_regs.h"
     42 
     43 #include "va/va_enc_h264.h"
     44 
     45 #include "psb_def.h"
     46 #include "psb_drv_debug.h"
     47 #include "psb_surface.h"
     48 #include "tng_cmdbuf.h"
     49 #include "tng_hostcode.h"
     50 #include "tng_hostheader.h"
     51 #include "tng_picmgmt.h"
     52 #include "tng_slotorder.h"
     53 #include "tng_hostair.h"
     54 #include "tng_H264ES.h"
     55 #ifdef _TOPAZHP_PDUMP_
     56 #include "tng_trace.h"
     57 #endif
     58 
     59 #define TOPAZ_H264_MAX_BITRATE 135000000
     60 
     61 #define INIT_CONTEXT_H264ES     context_ENC_p ctx = (context_ENC_p) obj_context->format_data
     62 #define SURFACE(id)    ((object_surface_p) object_heap_lookup( &ctx->obj_context->driver_data->surface_heap, id ))
     63 #define BUFFER(id)  ((object_buffer_p) object_heap_lookup( &ctx->obj_context->driver_data->buffer_heap, id ))
     64 
     65 static VAStatus tng__H264ES_init_profile(
     66     object_context_p obj_context,
     67     object_config_p obj_config)
     68 {
     69     VAStatus vaStatus = VA_STATUS_SUCCESS;
     70     context_ENC_p ctx;
     71     ctx = (context_ENC_p) obj_context->format_data;
     72     switch (obj_config->profile) {
     73         case VAProfileH264Baseline:
     74         case VAProfileH264ConstrainedBaseline:
     75             ctx->ui8ProfileIdc = H264ES_PROFILE_BASELINE;
     76             break;
     77         case VAProfileH264Main:
     78             ctx->ui8ProfileIdc = H264ES_PROFILE_MAIN;
     79             break;
     80         case VAProfileH264High:
     81             ctx->ui8ProfileIdc = H264ES_PROFILE_HIGH;
     82             break;
     83         case VAProfileH264StereoHigh:
     84             ctx->ui8ProfileIdc = H264ES_PROFILE_HIGH;
     85             ctx->bEnableMVC = 1;
     86             ctx->ui16MVCViewIdx = 0;
     87             break;
     88         default:
     89             ctx->ui8ProfileIdc = H264ES_PROFILE_BASELINE;
     90             vaStatus = VA_STATUS_ERROR_UNSUPPORTED_PROFILE;
     91             break;
     92     }
     93     drv_debug_msg(VIDEO_DEBUG_GENERAL,
     94         "%s: obj_config->profile = %dctx->eStandard = %d, ctx->bEnableMVC = %d\n",
     95         __FUNCTION__, obj_config->profile, ctx->eStandard, ctx->bEnableMVC);
     96     return vaStatus;
     97 }
     98 
     99 static VAStatus tng__H264ES_get_codec_type(
    100     object_context_p obj_context,
    101     object_config_p __maybe_unused obj_config)
    102 {
    103     VAStatus vaStatus = VA_STATUS_SUCCESS;
    104     context_ENC_p ctx = (context_ENC_p) obj_context->format_data;
    105     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    106 
    107     ctx->eCodec = IMG_CODEC_NUM;
    108 
    109     if (ctx->bEnableMVC) {
    110         switch (psRCParams->eRCMode) {
    111             case IMG_RCMODE_NONE:
    112                 ctx->eCodec = IMG_CODEC_H264MVC_NO_RC;
    113                 break;
    114             case IMG_RCMODE_CBR:
    115                 ctx->eCodec = IMG_CODEC_H264MVC_CBR;
    116                 break;
    117             case IMG_RCMODE_VBR:
    118                 ctx->eCodec = IMG_CODEC_H264MVC_VBR;
    119                 break;
    120             default:
    121                 drv_debug_msg(VIDEO_DEBUG_ERROR, "RC mode MVC\n");
    122                 break;
    123         }
    124     } else {
    125         switch (psRCParams->eRCMode) {
    126             case IMG_RCMODE_NONE:
    127                 ctx->eCodec = IMG_CODEC_H264_NO_RC;
    128                 break;
    129             case IMG_RCMODE_CBR:
    130                 ctx->eCodec = IMG_CODEC_H264_CBR;
    131                 break;
    132             case IMG_RCMODE_VBR:
    133                 ctx->eCodec = IMG_CODEC_H264_VBR;
    134                 break;
    135             case IMG_RCMODE_VCM:
    136                 ctx->eCodec = IMG_CODEC_H264_VCM;
    137                 break;
    138             default:
    139                 drv_debug_msg(VIDEO_DEBUG_ERROR, "RC mode\n");
    140                 break;
    141         }
    142     }
    143     return vaStatus;
    144 }
    145 
    146 static VAStatus tng__H264ES_init_format_mode(
    147     object_context_p obj_context,
    148     object_config_p __maybe_unused obj_config)
    149 {
    150     VAStatus vaStatus = VA_STATUS_SUCCESS;
    151     context_ENC_p ctx = (context_ENC_p) obj_context->format_data;
    152 
    153     ctx->bIsInterlaced = IMG_FALSE;
    154     ctx->bIsInterleaved = IMG_FALSE;
    155     ctx->ui16PictureHeight = ctx->ui16FrameHeight;
    156     ctx->eCodec = IMG_CODEC_H264_NO_RC;
    157     return vaStatus;
    158 }
    159 
    160 static void tng__H264ES_init_context(object_context_p obj_context,
    161     object_config_p __maybe_unused obj_config)
    162 {
    163     context_ENC_p ctx = (context_ENC_p) obj_context->format_data;
    164     //This parameter need not be exposed
    165     ctx->ui8InterIntraIndex = 3;
    166     ctx->ui8CodedSkippedIndex = 3;
    167     ctx->bEnableHostQP = IMG_FALSE;
    168     ctx->uMaxChunks = 0xA0;
    169     ctx->uChunksPerMb = 0x40;
    170     ctx->uPriorityChunks = (0xA0 - 0x60);
    171     ctx->ui32FCode = 4;
    172     ctx->iFineYSearchSize = 2;
    173 
    174     //This parameter need not be exposed
    175     //host to control the encoding process
    176     ctx->bEnableInpCtrl = IMG_FALSE;
    177     ctx->bEnableHostBias = IMG_FALSE;
    178     //By default false Newly Added
    179     ctx->bEnableCumulativeBiases = IMG_FALSE;
    180 
    181     //Weighted Prediction is not supported in TopazHP Version 3.0
    182     ctx->bWeightedPrediction = IMG_FALSE;
    183     ctx->ui8VPWeightedImplicitBiPred = 0;
    184     ctx->bInsertHRDParams = IMG_FALSE;
    185     ctx->bArbitrarySO = IMG_FALSE;
    186     ctx->ui32BasicUnit = 0;
    187     ctx->idr_force_flag = 0;
    188     ctx->bVPAdaptiveRoundingDisable = IMG_FALSE;
    189 }
    190 
    191 static VAStatus tng__H264ES_process_misc_framerate_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    192 {
    193     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
    194     VAEncMiscParameterFrameRate *psMiscFrameRateParam;
    195     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    196 
    197     ASSERT(obj_buffer->type == VAEncMiscParameterTypeFrameRate);
    198     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterFrameRate));
    199 
    200     psMiscFrameRateParam = (VAEncMiscParameterFrameRate *)(pBuffer->data);
    201 
    202     if (psMiscFrameRateParam == NULL)
    203         return VA_STATUS_ERROR_INVALID_BUFFER;
    204 
    205     if (psMiscFrameRateParam->framerate < 1 || psMiscFrameRateParam->framerate > 65535)
    206         return VA_STATUS_ERROR_INVALID_PARAMETER;
    207 
    208 
    209     if (psRCParams->ui32FrameRate == 0)
    210         psRCParams->ui32FrameRate = psMiscFrameRateParam->framerate;
    211     else {
    212         if(psMiscFrameRateParam->framerate != psRCParams->ui32FrameRate){
    213 	    if (psMiscFrameRateParam->framerate > psRCParams->ui32FrameRate)
    214 		psRCParams->ui32BitsPerSecond /= (float)psMiscFrameRateParam->framerate / psRCParams->ui32FrameRate;
    215 	    else
    216 		psRCParams->ui32BitsPerSecond *= (float)psRCParams->ui32FrameRate / psMiscFrameRateParam->framerate;
    217             psRCParams->ui32FrameRate = psMiscFrameRateParam->framerate;
    218             ctx->rc_update_flag |= RC_MASK_frame_rate;
    219         }
    220     }
    221 
    222     return VA_STATUS_SUCCESS;
    223 }
    224 
    225 static VAStatus tng__H264ES_process_misc_ratecontrol_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    226 {
    227     IMG_INT32 ui32BitsPerFrame;
    228     VAEncMiscParameterRateControl *psMiscRcParams;
    229     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    230     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
    231     unsigned int max_bps;
    232 
    233     ASSERT(obj_buffer->type == VAEncMiscParameterTypeRateControl);
    234     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterRateControl));
    235     psMiscRcParams = (VAEncMiscParameterRateControl *)pBuffer->data;
    236 
    237 #ifdef _TOPAZHP_PDUMP_
    238     tng_H264ES_trace_misc_rc_params(psMiscRcParams);
    239 #endif
    240 
    241     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    242         "%s psRCParams->ui32BitsPerSecond = %d, psMiscRcParams->bits_per_second = %d \n",
    243         __FUNCTION__, psRCParams->ui32BitsPerSecond, psMiscRcParams->bits_per_second);
    244 
    245     if (psMiscRcParams->bits_per_second > TOPAZ_H264_MAX_BITRATE) {
    246         drv_debug_msg(VIDEO_DEBUG_GENERAL,
    247             "%s: bits_per_second(%d) exceeds the maximum bitrate, set it with %d\n",
    248             __FUNCTION__, psMiscRcParams->bits_per_second, TOPAZ_H264_MAX_BITRATE);
    249         psMiscRcParams->bits_per_second = TOPAZ_H264_MAX_BITRATE;
    250     }
    251 
    252     if ((psRCParams->ui32BitsPerSecond != psMiscRcParams->bits_per_second) &&
    253         psMiscRcParams->bits_per_second != 0) {
    254         psRCParams->ui32BitsPerSecond = psMiscRcParams->bits_per_second;
    255 	ctx->rc_update_flag |= RC_MASK_bits_per_second;
    256     }
    257 
    258     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    259         "%s: rate control changed from %d to %d\n", __FUNCTION__,
    260         psRCParams->ui32BitsPerSecond, psMiscRcParams->bits_per_second);
    261 
    262     if (psMiscRcParams->rc_flags.value != 0) {
    263        if (psMiscRcParams->rc_flags.bits.disable_bit_stuffing)
    264            ctx->sRCParams.bDisableBitStuffing = IMG_TRUE;
    265        drv_debug_msg(VIDEO_DEBUG_GENERAL, "bDisableBitStuffing is %d\n",
    266            ctx->sRCParams.bDisableBitStuffing);
    267     }
    268 
    269     if (psMiscRcParams->window_size > 2000) {
    270 	drv_debug_msg(VIDEO_DEBUG_ERROR, "window_size is too much!\n");
    271 	return VA_STATUS_ERROR_INVALID_PARAMETER;
    272     }
    273 
    274     if (psMiscRcParams->window_size != 0)
    275         ctx->uiCbrBufferTenths = psMiscRcParams->window_size / 100;
    276 
    277     if (psRCParams->ui32FrameRate == 0)
    278         psRCParams->ui32FrameRate = 30;
    279 
    280     /* According to Table A-1 Level limits, if resolution is bigger than 625SD,
    281        min compression ratio is 4, otherwise min compression ratio is 2 */
    282     if (psRCParams->ui32BitsPerSecond == 0) {
    283 	max_bps =  (ctx->obj_context->picture_width * ctx->obj_context->picture_height * 3 / 2 ) * 8 * psRCParams->ui32FrameRate;
    284 	if (ctx->ui16SourceWidth > 720)
    285 	    max_bps /= 4;
    286 	else
    287 	    max_bps /= 2;
    288 	psRCParams->ui32BitsPerSecond = max_bps;
    289     }
    290 
    291     if (ctx->uiCbrBufferTenths) {
    292         psRCParams->ui32BufferSize = (IMG_UINT32)(psRCParams->ui32BitsPerSecond * ctx->uiCbrBufferTenths / 10.0);
    293     } else {
    294         if (psRCParams->ui32BitsPerSecond < 256000)
    295             psRCParams->ui32BufferSize = ((9 * psRCParams->ui32BitsPerSecond) >> 1);
    296         else
    297             psRCParams->ui32BufferSize = ((5 * psRCParams->ui32BitsPerSecond) >> 1);
    298     }
    299 
    300     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    301         "%s ctx->uiCbrBufferTenths = %d, psRCParams->ui32BufferSize = %d\n",
    302         __FUNCTION__, ctx->uiCbrBufferTenths, psRCParams->ui32BufferSize);
    303     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    304         "%s psRCParams->ui32BitsPerSecond = %d, psMiscRcParams->bits_per_second = %d\n",
    305         __FUNCTION__, psRCParams->ui32BitsPerSecond, psMiscRcParams->bits_per_second);
    306 
    307     //psRCParams->ui32BUSize = psMiscRcParams->basic_unit_size;
    308     psRCParams->i32InitialDelay = (13 * psRCParams->ui32BufferSize) >> 4;
    309     psRCParams->i32InitialLevel = (3 * psRCParams->ui32BufferSize) >> 4;
    310 
    311     ui32BitsPerFrame = psRCParams->ui32BitsPerSecond / psRCParams->ui32FrameRate;
    312     /* in order to minimise mismatches between firmware and external world InitialLevel should be a multiple of ui32BitsPerFrame */
    313     psRCParams->i32InitialLevel = ((psRCParams->i32InitialLevel + ui32BitsPerFrame / 2) / ui32BitsPerFrame) * ui32BitsPerFrame;
    314     psRCParams->i32InitialLevel = tng__max(psRCParams->i32InitialLevel, ui32BitsPerFrame);
    315     psRCParams->i32InitialDelay = psRCParams->ui32BufferSize - psRCParams->i32InitialLevel;
    316 
    317     //free(psMiscRcParams);
    318     if (psMiscRcParams->initial_qp > 51 ||
    319 	psMiscRcParams->min_qp > 51 ||
    320 	psMiscRcParams->max_qp > 51) {
    321         drv_debug_msg(VIDEO_DEBUG_ERROR,
    322             "%s: Initial_qp(%d) min_qp(%d) max_qp(%d) invalid.\nQP shouldn't be larger than 51 for H264\n",
    323             __FUNCTION__, psMiscRcParams->initial_qp, psMiscRcParams->min_qp, psMiscRcParams->max_qp);
    324         return VA_STATUS_ERROR_INVALID_PARAMETER;
    325     }
    326 
    327     if ((psRCParams->ui32InitialQp != psMiscRcParams->initial_qp) &&
    328 	(psMiscRcParams->initial_qp != 0)) {
    329 	drv_debug_msg(VIDEO_DEBUG_GENERAL,
    330 	    "%s: initial_qp updated from %d to %d\n",
    331 	    __FUNCTION__, psRCParams->ui32InitialQp, psMiscRcParams->initial_qp);
    332 	ctx->rc_update_flag |= RC_MASK_initial_qp;
    333 	psRCParams->ui32InitialQp = psMiscRcParams->initial_qp;
    334     }
    335 
    336     if ((psRCParams->iMinQP != psMiscRcParams->min_qp) &&
    337 	(psMiscRcParams->min_qp != 0)) {
    338 	drv_debug_msg(VIDEO_DEBUG_GENERAL,
    339 	    "%s: min_qp updated from %d to %d\n",
    340 	    __FUNCTION__, psRCParams->iMinQP, psMiscRcParams->min_qp);
    341 	ctx->rc_update_flag |= RC_MASK_min_qp;
    342 	psRCParams->iMinQP = psMiscRcParams->min_qp;
    343     }
    344 
    345     if ((ctx->max_qp != psMiscRcParams->max_qp) &&
    346 	(psMiscRcParams->max_qp != 0)) {
    347 	drv_debug_msg(VIDEO_DEBUG_GENERAL,
    348 	    "%s: max_qp updated from %d to %d\n",
    349 	    __FUNCTION__, ctx->max_qp, psMiscRcParams->max_qp);
    350 	ctx->rc_update_flag |= RC_MASK_max_qp;
    351 	ctx->max_qp = psMiscRcParams->max_qp;
    352     }
    353 
    354     return VA_STATUS_SUCCESS;
    355 }
    356 
    357 static VAStatus tng__H264ES_process_misc_hrd_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    358 {
    359     VAStatus vaStatus = VA_STATUS_SUCCESS;
    360     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
    361     VAEncMiscParameterHRD *psMiscHrdParams = NULL;
    362     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    363     ASSERT(obj_buffer->type == VAEncMiscParameterTypeHRD);
    364     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterHRD));
    365     psMiscHrdParams = (VAEncMiscParameterHRD *)pBuffer->data;
    366 
    367     if (psMiscHrdParams->buffer_size == 0
    368 	|| psMiscHrdParams->initial_buffer_fullness == 0) {
    369 	drv_debug_msg(VIDEO_DEBUG_ERROR, "Find zero value for buffer_size "
    370 		"and initial_buffer_fullness.\n");
    371 	vaStatus = VA_STATUS_ERROR_INVALID_PARAMETER;
    372 	return vaStatus;
    373     }
    374 
    375     if (ctx->initial_buffer_fullness > ctx->buffer_size) {
    376 	drv_debug_msg(VIDEO_DEBUG_ERROR, "initial_buffer_fullnessi(%d) shouldn't be"
    377 		" larger that buffer_size(%d)!\n",
    378 		psMiscHrdParams->initial_buffer_fullness,
    379 		psMiscHrdParams->buffer_size);
    380 	vaStatus = VA_STATUS_ERROR_INVALID_PARAMETER;
    381 	return vaStatus;
    382     }
    383 
    384     if (!psRCParams->bRCEnable) {
    385 	drv_debug_msg(VIDEO_DEBUG_ERROR, "Only when rate control is enabled,"
    386 		" VAEncMiscParameterTypeHRD will take effect.\n");
    387 	vaStatus = VA_STATUS_ERROR_ATTR_NOT_SUPPORTED;
    388 	return vaStatus;
    389     }
    390 
    391     ctx->buffer_size = psMiscHrdParams->buffer_size;
    392     ctx->initial_buffer_fullness = psMiscHrdParams->initial_buffer_fullness;
    393     ctx->bInsertHRDParams = IMG_TRUE;
    394     drv_debug_msg(VIDEO_DEBUG_GENERAL, "hrd param buffer_size set to %d "
    395 	"initial buffer fullness set to %d\n",
    396 	ctx->buffer_size, ctx->initial_buffer_fullness);
    397 
    398     return VA_STATUS_SUCCESS;
    399 }
    400 
    401 //APP_SetVideoParams
    402 static VAStatus tng__H264ES_process_misc_air_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    403 {
    404     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
    405     VAEncMiscParameterAIR *psMiscAirParams = NULL;
    406     ADAPTIVE_INTRA_REFRESH_INFO_TYPE *psAIRInfo = &(ctx->sAirInfo);
    407     IMG_UINT32 ui32MbNum;
    408     ASSERT(obj_buffer->type == VAEncMiscParameterTypeAIR);
    409     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterAIR));
    410 
    411     psMiscAirParams = (VAEncMiscParameterAIR*)pBuffer->data;
    412     ui32MbNum = (ctx->ui16PictureHeight * ctx->ui16Width) >> 8;
    413 
    414     drv_debug_msg(VIDEO_DEBUG_GENERAL, "%s: enable_AIR = %d, mb_num = %d, thresh_hold = %d, air_auto = %d\n", __FUNCTION__,
    415         ctx->bEnableAIR, psMiscAirParams->air_num_mbs, psMiscAirParams->air_threshold, psMiscAirParams->air_auto);
    416 
    417     ctx->bEnableAIR = 1;
    418     ctx->bEnableInpCtrl = 1;
    419     ctx->bEnableHostBias = 1;
    420     ctx->ui8EnableSelStatsFlags |= ESF_FIRST_STAGE_STATS;
    421     ctx->ui8EnableSelStatsFlags |= ESF_MP_BEST_MB_DECISION_STATS;
    422 
    423     /*FIXME
    424     if (psMiscAirParams->air_threshold == -1 && psMiscAirParams->air_num_mbs == 0) {
    425         drv_debug_msg(VIDEO_DEBUG_ERROR,
    426             "%s: ERROR: Cannot have both -AIRMBperFrame set to zero"
    427             "AND and -AIRSADThreshold set to -1 (APP_SetVideoParams)\n",
    428             __FUNCTION__);
    429         return VA_STATUS_ERROR_INVALID_PARAMETER;
    430     }*/
    431 
    432     if (psMiscAirParams->air_num_mbs > 65535) {
    433         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: ERROR: air_num_mbs = %d should not bigger than 65536\n",
    434             __FUNCTION__, psMiscAirParams->air_num_mbs);
    435         return VA_STATUS_ERROR_INVALID_PARAMETER;
    436     }
    437 
    438     if (psMiscAirParams->air_num_mbs > ui32MbNum)
    439         psMiscAirParams->air_num_mbs = ui32MbNum;
    440 
    441     if (psMiscAirParams->air_threshold > 65535) {
    442         drv_debug_msg(VIDEO_DEBUG_ERROR,
    443             "%s: ERROR: air_threshold = %d should not bigger than 65536\n",
    444             __FUNCTION__, psMiscAirParams->air_threshold);
    445         return VA_STATUS_ERROR_INVALID_PARAMETER;
    446     }
    447 
    448     if (psMiscAirParams->air_auto) {
    449 	psAIRInfo->i32NumAIRSPerFrame = -1;
    450 	psAIRInfo->i32SAD_Threshold = -1;
    451 	psAIRInfo->i16AIRSkipCnt = -1;
    452     } else {
    453 	psAIRInfo->i32NumAIRSPerFrame = psMiscAirParams->air_num_mbs;
    454 	psAIRInfo->i32SAD_Threshold = psMiscAirParams->air_threshold;
    455 	psAIRInfo->i16AIRSkipCnt = -1;
    456     }
    457 
    458     psAIRInfo->ui16AIRScanPos = 0;
    459 
    460     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    461         "%s: air slice size changed to num_air_mbs %d "
    462         "air_threshold %d, air_auto %d\n", __FUNCTION__,
    463         psMiscAirParams->air_num_mbs, psMiscAirParams->air_threshold,
    464         psMiscAirParams->air_auto);
    465 
    466     if (psAIRInfo->pi8AIR_Table != NULL)
    467         free(psAIRInfo->pi8AIR_Table);
    468     tng_air_buf_create(ctx);
    469 
    470     return VA_STATUS_SUCCESS;
    471 }
    472 
    473 static VAStatus tng__H264ES_process_misc_cir_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    474 {
    475     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *)obj_buffer->buffer_data;
    476     VAEncMiscParameterCIR *psMiscCirParams = NULL;
    477 
    478     ASSERT(obj_buffer->type == VAEncMiscParameterTypeCIR);
    479     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterCIR));
    480 
    481     psMiscCirParams = (VAEncMiscParameterCIR*)pBuffer->data;
    482 
    483     if (psMiscCirParams->cir_num_mbs > 0) {
    484 	drv_debug_msg(VIDEO_DEBUG_GENERAL,
    485 	    "CIR enabled with MB count %d\n", ctx->ui16IntraRefresh);
    486 	ctx->ui16IntraRefresh = psMiscCirParams->cir_num_mbs;
    487 	ctx->bEnableCIR = 1;
    488 	ctx->bEnableInpCtrl = 1;
    489 	ctx->bEnableHostBias = 1;
    490     } else {
    491         drv_debug_msg(VIDEO_DEBUG_ERROR,
    492             "%s: ERROR: invalid cir num mbs(%d), should bigger than 0\n",
    493             __FUNCTION__, ctx->ui16IntraRefresh);
    494         return VA_STATUS_ERROR_INVALID_PARAMETER;
    495     }
    496 
    497     return VA_STATUS_SUCCESS;
    498 }
    499 
    500 static IMG_UINT8 tng__H264ES_calculate_level(context_ENC_p ctx)
    501 {
    502     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    503     IMG_UINT32 ui32MBf=0;
    504     IMG_UINT32 ui32MBs;
    505     IMG_UINT32 ui32Level=0;
    506     IMG_UINT32 ui32TempLevel=0;
    507     IMG_UINT32 ui32DpbMbs;
    508     // We need to calculate the level based on a few constraints these are
    509     // Macroblocks per second
    510     // picture size
    511     // decoded picture buffer size, and bitrate
    512     ui32MBf = (ctx->ui16Width)*(ctx->ui16FrameHeight) >> 8;
    513     ui32MBs = ui32MBf * psRCParams->ui32FrameRate;
    514 
    515 
    516     // could do these in nice tables, but this is clearer
    517     if      (ui32MBf > 22080) ui32Level = SH_LEVEL_51;
    518     else if (ui32MBf >  8704) ui32Level = SH_LEVEL_50;
    519     else if (ui32MBf >  8192) ui32Level = SH_LEVEL_42;
    520     else if (ui32MBf >  5120) ui32Level = SH_LEVEL_40;
    521     else if (ui32MBf >  3600) ui32Level = SH_LEVEL_32;
    522     else if (ui32MBf >  1620) ui32Level = SH_LEVEL_31;
    523     else if (ui32MBf >   792) ui32Level = SH_LEVEL_22;
    524     else if (ui32MBf >   396) ui32Level = SH_LEVEL_21;
    525     else if (ui32MBf >    99) ui32Level = SH_LEVEL_11;
    526     else ui32Level = SH_LEVEL_10;
    527 
    528     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    529         "%s: ui32MBf = %d, ui32MBs = %d, ui32Level = %d\n",
    530         __FUNCTION__, ui32MBf, ui32MBs, ui32Level);
    531 
    532     //ui32DpbMbs = ui32MBf * (psContext->ui32MaxNumRefFrames + 1);
    533     ui32DpbMbs = ui32MBf * (ctx->ui8MaxNumRefFrames + 1);
    534 
    535     if      (ui32DpbMbs > 110400) ui32TempLevel = SH_LEVEL_51;
    536     else if (ui32DpbMbs >  34816) ui32TempLevel = SH_LEVEL_50;
    537     else if (ui32DpbMbs >  32768) ui32TempLevel = SH_LEVEL_42;
    538     else if (ui32DpbMbs >  20480) ui32TempLevel = SH_LEVEL_40;
    539     else if (ui32DpbMbs >  18000) ui32TempLevel = SH_LEVEL_32;
    540     else if (ui32DpbMbs >   8100) ui32TempLevel = SH_LEVEL_31;
    541     else if (ui32DpbMbs >   4752) ui32TempLevel = SH_LEVEL_22;
    542     else if (ui32DpbMbs >   2376) ui32TempLevel = SH_LEVEL_21;
    543     else if (ui32DpbMbs >    900) ui32TempLevel = SH_LEVEL_12;
    544     else if (ui32DpbMbs >    396) ui32TempLevel = SH_LEVEL_11;
    545     else ui32TempLevel = SH_LEVEL_10;
    546     ui32Level = tng__max(ui32Level, ui32TempLevel);
    547 
    548     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    549         "%s: ui32DpbMbs = %d, ui32Level = %d\n",
    550         __FUNCTION__, ui32DpbMbs, ui32Level);
    551 
    552     // now restrict based on the number of macroblocks per second
    553     if      (ui32MBs > 589824) ui32TempLevel = SH_LEVEL_51;
    554     else if (ui32MBs > 522240) ui32TempLevel = SH_LEVEL_50;
    555     else if (ui32MBs > 245760) ui32TempLevel = SH_LEVEL_42;
    556     else if (ui32MBs > 216000) ui32TempLevel = SH_LEVEL_40;
    557     else if (ui32MBs > 108000) ui32TempLevel = SH_LEVEL_32;
    558     else if (ui32MBs >  40500) ui32TempLevel = SH_LEVEL_31;
    559     else if (ui32MBs >  20250) ui32TempLevel = SH_LEVEL_30;
    560     else if (ui32MBs >  19800) ui32TempLevel = SH_LEVEL_22;
    561     else if (ui32MBs >  11880) ui32TempLevel = SH_LEVEL_21;
    562     else if (ui32MBs >   6000) ui32TempLevel = SH_LEVEL_13;
    563     else if (ui32MBs >   3000) ui32TempLevel = SH_LEVEL_12;
    564     else if (ui32MBs >   1485) ui32TempLevel = SH_LEVEL_11;
    565     else ui32TempLevel = SH_LEVEL_10;
    566     ui32Level = tng__max(ui32Level, ui32TempLevel);
    567 
    568     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    569         "%s: ui32TempLevel = %d, ui32Level = %d\n",
    570         __FUNCTION__, ui32TempLevel, ui32Level);
    571 
    572     if (psRCParams->bRCEnable) {
    573         // now restrict based on the requested bitrate
    574         if      (psRCParams->ui32FrameRate > 135000000) ui32TempLevel = SH_LEVEL_51;
    575         else if (psRCParams->ui32FrameRate >  50000000) ui32TempLevel = SH_LEVEL_50;
    576         else if (psRCParams->ui32FrameRate >  20000000) ui32TempLevel = SH_LEVEL_41;
    577         else if (psRCParams->ui32FrameRate >  14000000) ui32TempLevel = SH_LEVEL_32;
    578         else if (psRCParams->ui32FrameRate >  10000000) ui32TempLevel = SH_LEVEL_31;
    579         else if (psRCParams->ui32FrameRate >   4000000) ui32TempLevel = SH_LEVEL_30;
    580         else if (psRCParams->ui32FrameRate >   2000000) ui32TempLevel = SH_LEVEL_21;
    581         else if (psRCParams->ui32FrameRate >    768000) ui32TempLevel = SH_LEVEL_20;
    582         else if (psRCParams->ui32FrameRate >    384000) ui32TempLevel = SH_LEVEL_13;
    583         else if (psRCParams->ui32FrameRate >    192000) ui32TempLevel = SH_LEVEL_12;
    584         else if (psRCParams->ui32FrameRate >    128000) ui32TempLevel = SH_LEVEL_11;
    585         else if (psRCParams->ui32FrameRate >     64000) ui32TempLevel = SH_LEVEL_1B;
    586         else ui32TempLevel = SH_LEVEL_10;
    587 
    588         ui32Level = tng__max(ui32Level, ui32TempLevel);
    589     }
    590 /*
    591     if (pParams->bLossless) {
    592         ui32Level = tng__max(ui32Level, 320);
    593     }
    594 */
    595     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    596         "%s: target level is %d, input level is %d\n",
    597         __FUNCTION__, ui32Level, ctx->ui8LevelIdc);
    598     return (IMG_UINT8)ui32Level;
    599 }
    600 
    601 static VAStatus tng__H264ES_process_sequence_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    602 {
    603     VAStatus vaStatus = VA_STATUS_SUCCESS;
    604     VAEncSequenceParameterBufferH264 *psSeqParams;
    605     H264_CROP_PARAMS* psCropParams = &(ctx->sCropParams);
    606     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
    607     FRAME_ORDER_INFO *psFrameInfo = &(ctx->sFrameOrderInfo);
    608     H264_VUI_PARAMS *psVuiParams = &(ctx->sVuiParams);
    609     IMG_UINT32 ui32MaxUnit32 = (IMG_UINT32)0x7ffa;
    610     IMG_UINT32 ui32IPCount = 0;
    611     IMG_UINT64 ui64Temp = 0;
    612 
    613     ASSERT(obj_buffer->type == VAEncSequenceParameterBufferType);
    614     ASSERT(obj_buffer->size == sizeof(VAEncSequenceParameterBufferH264));
    615 
    616     if (obj_buffer->size != sizeof(VAEncSequenceParameterBufferH264)) {
    617         vaStatus = VA_STATUS_ERROR_UNKNOWN;
    618         goto out1;
    619     }
    620 
    621     ctx->obj_context->frame_count = 0;
    622     psSeqParams = (VAEncSequenceParameterBufferH264 *) obj_buffer->buffer_data;
    623     obj_buffer->buffer_data = NULL;
    624     obj_buffer->size = 0;
    625 
    626 #ifdef _TOPAZHP_PDUMP_
    627     tng_H264ES_trace_seq_params(psSeqParams);
    628 #endif
    629 
    630     ctx->ui8LevelIdc = psSeqParams->level_idc;
    631     ctx->ui8MaxNumRefFrames = psSeqParams->max_num_ref_frames;
    632 
    633     ctx->ui32IdrPeriod = psSeqParams->intra_idr_period;
    634     ctx->ui32IntraCnt = psSeqParams->intra_period;
    635     ui32IPCount = (IMG_UINT32)(psSeqParams->ip_period);
    636 
    637     if ((ui32IPCount > 4) || (ui32IPCount == 0)) {
    638         drv_debug_msg(VIDEO_DEBUG_ERROR,
    639             "%s: ip_period %d, it should be in [1, 4]\n",
    640             __FUNCTION__, psSeqParams->ip_period);
    641         vaStatus = VA_STATUS_ERROR_INVALID_PARAMETER;
    642         goto out1;
    643     }
    644 
    645     if (ctx->ui32IntraCnt == 0) {
    646         if (ui32IPCount == 1)
    647             ctx->ui32IntraCnt = INT_MAX;
    648         else
    649             ctx->ui32IntraCnt = INT_MAX - (INT_MAX % ui32IPCount);
    650         ctx->ui32IdrPeriod = 1;
    651     } else if (ctx->ui32IntraCnt == 1) {
    652         //only I frame or IDR frames;
    653         ui32IPCount = 1;
    654         if (ctx->ui32IdrPeriod == 0)
    655             ctx->ui32IdrPeriod = INT_MAX;
    656     } else {
    657         if (ctx->ui32IdrPeriod == 0) {
    658             ctx->ui32IdrPeriod = INT_MAX / ctx->ui32IntraCnt;
    659         } else if (ctx->ui32IdrPeriod > 1) {
    660             ui64Temp = (IMG_UINT64)(ctx->ui32IdrPeriod) * (IMG_UINT64)(ctx->ui32IntraCnt);
    661             if (ui64Temp >= (IMG_UINT64)INT_MAX) {
    662                 ctx->ui32IdrPeriod = INT_MAX / ctx->ui32IntraCnt;
    663             }
    664         }
    665 
    666         if ((ctx->ui32IntraCnt % ui32IPCount) != 0) {
    667             if (ctx->ui32IntraCnt > INT_MAX - ui32IPCount + (ctx->ui32IntraCnt % ui32IPCount))
    668                 ctx->ui32IntraCnt = INT_MAX - ui32IPCount + (ctx->ui32IntraCnt % ui32IPCount);
    669             else
    670                 ctx->ui32IntraCnt += ui32IPCount - (ctx->ui32IntraCnt % ui32IPCount);
    671         }
    672     }
    673 
    674     if (ctx->ui32FrameCount[ctx->ui32StreamID] > 0) {
    675         ctx->idr_force_flag = 1;
    676 	if (ctx->ui32IntraCntSave != ctx->ui32IntraCnt) {
    677 	    drv_debug_msg(VIDEO_DEBUG_GENERAL,
    678 		"%s: intra_period updated from %d to %d\n",
    679 		__FUNCTION__, ctx->ui32IntraCntSave, ctx->ui32IntraCnt);
    680 	    ctx->rc_update_flag |= RC_MASK_intra_period;
    681 	}
    682     }
    683 
    684     ctx->ui32IntraCntSave = ctx->ui32IntraCnt;
    685 
    686     ctx->ui8SlotsInUse = ui32IPCount + 1; //Bframes + 2
    687 
    688     //bits per second
    689     if (!psSeqParams->bits_per_second) {
    690         psSeqParams->bits_per_second = ctx->ui16Width * ctx->ui16PictureHeight * 30 * 12;
    691     }
    692 
    693     if (psSeqParams->bits_per_second > TOPAZ_H264_MAX_BITRATE) {
    694         psSeqParams->bits_per_second = TOPAZ_H264_MAX_BITRATE;
    695         drv_debug_msg(VIDEO_DEBUG_ERROR,
    696             "%s: bits_per_second(%d) exceeds the maximum bitrate, set it with %d\n",
    697             __FUNCTION__, psSeqParams->bits_per_second,
    698             TOPAZ_H264_MAX_BITRATE);
    699     }
    700 
    701     if (psRCParams->ui32BitsPerSecond == 0)
    702         psRCParams->ui32BitsPerSecond = psSeqParams->bits_per_second;
    703 
    704     if (psSeqParams->bits_per_second != psRCParams->ui32BitsPerSecond) {
    705         psRCParams->ui32BitsPerSecond = psSeqParams->bits_per_second;
    706 	ctx->rc_update_flag |= RC_MASK_bits_per_second;
    707     }
    708 
    709     psRCParams->ui32IntraFreq = ctx->ui32IntraCnt;
    710     psRCParams->ui32TransferBitsPerSecond = psRCParams->ui32BitsPerSecond;
    711     psRCParams->ui16BFrames = ui32IPCount - 1;
    712 
    713     if (psRCParams->ui32FrameRate == 0)
    714         psRCParams->ui32FrameRate = 30;
    715 
    716     //set the B frames
    717     if (psRCParams->eRCMode == IMG_RCMODE_VCM)
    718         psRCParams->ui16BFrames = 0;
    719 
    720     if ((psRCParams->ui16BFrames > 0) && (ctx->ui8ProfileIdc == H264ES_PROFILE_BASELINE)) {
    721         ctx->ui8ProfileIdc = H264ES_PROFILE_MAIN;
    722     }
    723 
    724     if (psFrameInfo->slot_consume_dpy_order != NULL)
    725         free(psFrameInfo->slot_consume_dpy_order);
    726     if (psFrameInfo->slot_consume_enc_order != NULL)
    727         free(psFrameInfo->slot_consume_enc_order);
    728 
    729     if (psRCParams->ui16BFrames != 0) {
    730         memset(psFrameInfo, 0, sizeof(FRAME_ORDER_INFO));
    731         psFrameInfo->slot_consume_dpy_order = (int *)malloc(ctx->ui8SlotsInUse * sizeof(int));
    732         psFrameInfo->slot_consume_enc_order = (int *)malloc(ctx->ui8SlotsInUse * sizeof(int));
    733 
    734         if ((psFrameInfo->slot_consume_dpy_order == NULL) ||
    735             (psFrameInfo->slot_consume_enc_order == NULL)) {
    736             drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: error malloc slot order array\n", __FUNCTION__);
    737         }
    738     }
    739 
    740     //set the crop parameters
    741     psCropParams->bClip = psSeqParams->frame_cropping_flag;
    742     psCropParams->ui16LeftCropOffset = psSeqParams->frame_crop_left_offset;
    743     psCropParams->ui16RightCropOffset = psSeqParams->frame_crop_right_offset;
    744     psCropParams->ui16TopCropOffset = psSeqParams->frame_crop_top_offset;
    745     psCropParams->ui16BottomCropOffset = psSeqParams->frame_crop_bottom_offset;
    746 
    747     //set level idc parameter
    748     ctx->ui32VertMVLimit = 255 ;//(63.75 in qpel increments)
    749     ctx->bLimitNumVectors = IMG_FALSE;
    750 
    751     if (ctx->ui8LevelIdc == 111)
    752         ctx->ui8LevelIdc = SH_LEVEL_1B;
    753 
    754     ctx->ui8LevelIdc = tng__H264ES_calculate_level(ctx);
    755 
    756     /*Setting VertMVLimit and LimitNumVectors only for H264*/
    757     if (ctx->ui8LevelIdc >= SH_LEVEL_30)
    758         ctx->bLimitNumVectors = IMG_TRUE;
    759     else
    760         ctx->bLimitNumVectors = IMG_FALSE;
    761 
    762     if (ctx->ui8LevelIdc >= SH_LEVEL_31)
    763         ctx->ui32VertMVLimit = 2047 ;//(511.75 in qpel increments)
    764     else if (ctx->ui8LevelIdc >= SH_LEVEL_21)
    765         ctx->ui32VertMVLimit = 1023 ;//(255.75 in qpel increments)
    766     else if (ctx->ui8LevelIdc >= SH_LEVEL_11)
    767         ctx->ui32VertMVLimit = 511 ;//(127.75 in qpel increments)
    768 
    769     //set VUI info
    770     memset(psVuiParams, 0, sizeof(H264_VUI_PARAMS));
    771     if (psSeqParams->time_scale != 0 && psSeqParams->num_units_in_tick != 0
    772 		&& (psSeqParams->time_scale > psSeqParams->num_units_in_tick)) {
    773         psVuiParams->Time_Scale = psSeqParams->time_scale;
    774         psVuiParams->num_units_in_tick = psSeqParams->num_units_in_tick;
    775     }
    776 
    777 out1:
    778     free(obj_buffer->buffer_data);
    779     obj_buffer->buffer_data = NULL;
    780     obj_buffer->size = 0;
    781 
    782     return vaStatus;
    783 }
    784 
    785 #if 0
    786 static VAStatus tng__H264ES_process_picture_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    787 {
    788     VAStatus vaStatus = VA_STATUS_SUCCESS;
    789     context_ENC_mem *ps_mem = &(ctx->ctx_mem[ctx->ui32StreamID]);
    790     context_ENC_frame_buf *ps_buf = &(ctx->ctx_frame_buf[ctx->ui32StreamID]);
    791     IMG_RC_PARAMS * psRCParams = &(ctx->sRCParams);
    792     VAEncPictureParameterBufferH264 *psPicParams;
    793     IMG_BOOL bDepViewPPS = IMG_FALSE;
    794 
    795     drv_debug_msg(VIDEO_DEBUG_GENERAL, "%s: start\n",__FUNCTION__);
    796     ASSERT(obj_buffer->type == VAEncPictureParameterBufferType);
    797     if (obj_buffer->size != sizeof(VAEncPictureParameterBufferH264)) {
    798         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s L%d Invalid coded buffer handle\n", __FUNCTION__, __LINE__);
    799         return VA_STATUS_ERROR_UNKNOWN;
    800     }
    801 
    802     /* Transfer ownership of VAEncPictureParameterBufferH264 data */
    803     psPicParams = (VAEncPictureParameterBufferH264 *) obj_buffer->buffer_data;
    804 
    805     obj_buffer->buffer_data = NULL;
    806     obj_buffer->size = 0;
    807 
    808     ASSERT(ctx->ui16Width == psPicParams->picture_width);
    809     ASSERT(ctx->ui16PictureHeight == psPicParams->picture_height);
    810 
    811 #ifdef _TOPAZHP_OLD_LIBVA_
    812     ps_buf->ref_surface = SURFACE(psPicParams->ReferenceFrames[0].picture_id);
    813     ps_buf->coded_buf = BUFFER(psPicParams->coded_buf);
    814 #else
    815     {
    816         IMG_INT32 i;
    817         ps_buf->rec_surface = SURFACE(psPicParams->CurrPic.picture_id);
    818         for (i = 0; i < 16; i++)
    819             ps_buf->ref_surface[i] = SURFACE(psPicParams->ReferenceFrames[i].picture_id);
    820         ps_buf->coded_buf = BUFFER(psPicParams->coded_buf);
    821     }
    822 #endif
    823 
    824     if (NULL == ps_buf->coded_buf) {
    825         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s L%d Invalid coded buffer handle\n", __FUNCTION__, __LINE__);
    826         free(psPicParams);
    827         return VA_STATUS_ERROR_INVALID_BUFFER;
    828     }
    829 
    830     if ((ctx->bEnableMvc) && (ctx->ui16MVCViewIdx != 0) &&
    831         (ctx->ui16MVCViewIdx != (IMG_UINT16)(NON_MVC_VIEW))) {
    832         bDepViewPPS = IMG_TRUE;
    833     }
    834 
    835     /************* init ****************
    836     ctx->bCabacEnabled = psPicParams->pic_fields.bits.entropy_coding_mode_flag;
    837     ctx->bH2648x8Transform = psPicParams->pic_fields.bits.transform_8x8_mode_flag;
    838     ctx->bH264IntraConstrained = psPicParams->pic_fields.bits.constrained_intra_pred_flag;
    839     ctx->bWeightedPrediction = psPicParams->pic_fields.bits.weighted_pred_flag;
    840     ctx->ui8VPWeightedImplicitBiPred = psPicParams->pic_fields.bits.weighted_bipred_idc;
    841     ctx->bCustomScaling = psPicParams->pic_fields.bits.pic_scaling_matrix_present_flag;
    842     ************* set rc params *************/
    843 //    ctx->sRCParams.ui32InitialQp = psPicParams->pic_init_qp;
    844 //    ctx->sRCParams.i8QCPOffset = psPicParams->chroma_qp_index_offset;
    845     drv_debug_msg(VIDEO_DEBUG_GENERAL, "%s psRCParams->ui32InitialQp = %d, psRCParams->iMinQP = %d\n", __FUNCTION__, psPicParams->pic_init_qp, psPicParams->chroma_qp_index_offset);
    846     tng__H264ES_prepare_picture_header(
    847         ps_mem->bufs_pic_template.virtual_addr,
    848         0, //IMG_BOOL    bCabacEnabled,
    849         ctx->bH2648x8Transform, //IMG_BOOL    b_8x8transform,
    850         0, //IMG_BOOL    bIntraConstrained,
    851         0, //IMG_INT8    i8CQPOffset,
    852         0, //IMG_BOOL    bWeightedPrediction,
    853         0, //IMG_UINT8   ui8WeightedBiPred,
    854         0, //IMG_BOOL    bMvcPPS,
    855         0, //IMG_BOOL    bScalingMatrix,
    856         0  //IMG_BOOL    bScalingLists
    857     );
    858     free(psPicParams);
    859 /*
    860     if (psRCParams->ui16BFrames == 0) {
    861         tng_send_codedbuf(ctx, (ctx->obj_context->frame_count&1));
    862         tng_send_source_frame(ctx, (ctx->obj_context->frame_count&1), ctx->obj_context->frame_count);
    863     } else
    864         tng__H264ES_provide_buffer_for_BFrames(ctx);
    865 */
    866     drv_debug_msg(VIDEO_DEBUG_GENERAL, "%s: end\n",__FUNCTION__);
    867 
    868     return vaStatus;
    869 }
    870 #endif
    871 
    872 static VAStatus tng__H264ES_process_picture_param_base(context_ENC_p ctx, unsigned char *buf)
    873 {
    874     VAStatus vaStatus = VA_STATUS_SUCCESS;
    875     context_ENC_frame_buf *ps_buf = &(ctx->ctx_frame_buf);
    876     VAEncPictureParameterBufferH264 *psPicParams;
    877 #ifndef _TNG_FRAMES_
    878     IMG_INT32 i;
    879 #endif
    880     psPicParams = (VAEncPictureParameterBufferH264 *) buf;
    881 
    882 #ifdef _TOPAZHP_PDUMP_
    883     tng_H264ES_trace_pic_params(psPicParams);
    884 #endif
    885 
    886 #ifdef _TNG_FRAMES_
    887     ps_buf->rec_surface  = SURFACE(psPicParams->CurrPic.picture_id);
    888     ps_buf->ref_surface  = SURFACE(psPicParams->ReferenceFrames[0].picture_id);
    889     ps_buf->ref_surface1 = SURFACE(psPicParams->ReferenceFrames[1].picture_id);
    890     drv_debug_msg(VIDEO_DEBUG_GENERAL, "%s: psPicParams->coded_buf = 0x%08x, ps_buf->coded_buf = 0x%08x\n",
    891         __FUNCTION__, psPicParams->coded_buf, ps_buf->coded_buf);
    892 #else
    893     {
    894         ps_buf->rec_surface = SURFACE(psPicParams->CurrPic.picture_id);
    895         for (i = 0; i < 4; i++) {
    896             ps_buf->ref_surface[i] = SURFACE(psPicParams->ReferenceFrames[i].picture_id);
    897 	    ps_buf->ref_surface[i]->is_ref_surface = 1;
    898 	}
    899     }
    900 #endif
    901 
    902     ps_buf->coded_buf = BUFFER(psPicParams->coded_buf);
    903 
    904     if (NULL == ps_buf->coded_buf) {
    905         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s L%d Invalid coded buffer handle\n", __FUNCTION__, __LINE__);
    906         free(psPicParams);
    907         return VA_STATUS_ERROR_INVALID_BUFFER;
    908     }
    909 
    910     ctx->bH2648x8Transform = psPicParams->pic_fields.bits.transform_8x8_mode_flag;
    911     if ((ctx->bH2648x8Transform == 1) && (ctx->ui8ProfileIdc != H264ES_PROFILE_HIGH)) {
    912         drv_debug_msg(VIDEO_DEBUG_ERROR,
    913         "%s L%d only high profile could set bH2648x8Transform TRUE\n",
    914         __FUNCTION__, __LINE__);
    915         ctx->bH2648x8Transform = 0;
    916     }
    917 
    918     ctx->bH264IntraConstrained = psPicParams->pic_fields.bits.constrained_intra_pred_flag;
    919     if (ctx->bEnableMVC == 1) {
    920         drv_debug_msg(VIDEO_DEBUG_ERROR,
    921             "%s L%d MVC could not set bH264IntraConstrained TRUE\n",
    922             __FUNCTION__, __LINE__);
    923         ctx->bH264IntraConstrained = 0;
    924     }
    925 
    926     ctx->bCabacEnabled = psPicParams->pic_fields.bits.entropy_coding_mode_flag;
    927     ctx->bWeightedPrediction = psPicParams->pic_fields.bits.weighted_pred_flag;
    928     ctx->ui8VPWeightedImplicitBiPred = psPicParams->pic_fields.bits.weighted_bipred_idc;
    929 
    930     /************* init ****************
    931     ctx->bCustomScaling = psPicParams->pic_fields.bits.pic_scaling_matrix_present_flag;
    932     ************* set rc params *************/
    933     if (ctx->sRCParams.ui32InitialQp == 0)
    934         ctx->sRCParams.ui32InitialQp = psPicParams->pic_init_qp;
    935 
    936     ctx->ui32LastPicture = psPicParams->last_picture;
    937 
    938     return vaStatus;
    939 }
    940 
    941 static VAStatus tng__H264ES_process_picture_param_mvc(context_ENC_p ctx, unsigned char *buf)
    942 {
    943     VAStatus vaStatus = VA_STATUS_SUCCESS;
    944     VAEncPictureParameterBufferH264_MVC *psPicMvcParams;
    945 
    946     psPicMvcParams = (VAEncPictureParameterBufferH264_MVC *) buf;
    947     ctx->ui16MVCViewIdx = ctx->ui32StreamID = psPicMvcParams->view_id;
    948     //vaStatus = tng__H264ES_process_picture_param_base(ctx, (unsigned char*)&(psPicMvcParams->base_picture_param));
    949 
    950     return vaStatus;
    951 }
    952 
    953 static VAStatus tng__H264ES_process_picture_param(context_ENC_p ctx, object_buffer_p obj_buffer)
    954 {
    955     VAStatus vaStatus = VA_STATUS_SUCCESS;
    956 
    957     ASSERT(obj_buffer->type == VAEncPictureParameterBufferType);
    958 
    959     drv_debug_msg(VIDEO_DEBUG_GENERAL,
    960         "%s: ctx->bEnableMVC = %d\n", __FUNCTION__, ctx->bEnableMVC);
    961 
    962     if (ctx->bEnableMVC) {
    963         if (obj_buffer->size != sizeof(VAEncPictureParameterBufferH264_MVC)) {
    964             drv_debug_msg(VIDEO_DEBUG_ERROR,
    965                 "%s L%d Invalid picture parameter H264 mvc buffer handle\n",
    966                 __FUNCTION__, __LINE__);
    967             return VA_STATUS_ERROR_UNKNOWN;
    968         }
    969         vaStatus = tng__H264ES_process_picture_param_mvc(ctx, obj_buffer->buffer_data);
    970     } else {
    971         if (obj_buffer->size != sizeof(VAEncPictureParameterBufferH264)) {
    972             drv_debug_msg(VIDEO_DEBUG_ERROR,
    973                 "%s L%d Invalid picture parameter H264 buffer handle\n",
    974                 __FUNCTION__, __LINE__);
    975             return VA_STATUS_ERROR_UNKNOWN;
    976         }
    977         vaStatus = tng__H264ES_process_picture_param_base(ctx, obj_buffer->buffer_data);
    978     }
    979     free(obj_buffer->buffer_data);
    980     obj_buffer->buffer_data = NULL;
    981     obj_buffer->size = 0;
    982     return vaStatus;
    983 }
    984 
    985 static VAStatus tng__H264ES_process_slice_param_mrfld(context_ENC_p ctx, object_buffer_p obj_buffer)
    986 {
    987     VAStatus vaStatus = VA_STATUS_SUCCESS;
    988     VAEncSliceParameterBufferH264 *psSliceParamsH264;
    989     unsigned int i;
    990     unsigned int uiPreMBAddress = 0;
    991     unsigned int uiCurMBAddress = 0;
    992     unsigned int uiPreMBNumbers = 0;
    993     unsigned int uiCurMBNumbers = 0;
    994     unsigned int uiAllMBNumbers = 0;
    995     unsigned char ucPreDeblockIdc = 0;
    996     unsigned char ucCurDeblockIdc = 0;
    997 
    998     /* Transfer ownership of VAEncPictureParameterBufferH264 data */
    999     psSliceParamsH264 = (VAEncSliceParameterBufferH264*) obj_buffer->buffer_data;
   1000 
   1001 #ifdef _TOPAZHP_PDUMP_
   1002     tng_H264ES_trace_slice_params(psSliceParamsH264);
   1003 #endif
   1004 
   1005     ucPreDeblockIdc = psSliceParamsH264->disable_deblocking_filter_idc;
   1006 
   1007     for (i = 0; i < obj_buffer->num_elements; i++) {
   1008         uiCurMBAddress = psSliceParamsH264->macroblock_address;
   1009         uiCurMBNumbers = psSliceParamsH264->num_macroblocks;
   1010         if (uiCurMBAddress != uiPreMBAddress + uiPreMBNumbers) {
   1011             drv_debug_msg(VIDEO_DEBUG_ERROR,
   1012                 "%s L%d Error Macroblock Address (%d), address (%d), number (%d)\n",
   1013                 __FUNCTION__, __LINE__, i, psSliceParamsH264->macroblock_address,
   1014                 psSliceParamsH264->num_macroblocks);
   1015             return VA_STATUS_ERROR_INVALID_PARAMETER;
   1016         }
   1017         uiPreMBNumbers = uiCurMBNumbers;
   1018         uiPreMBAddress = uiCurMBAddress;
   1019         uiAllMBNumbers += uiCurMBNumbers;
   1020 
   1021         ucCurDeblockIdc = psSliceParamsH264->disable_deblocking_filter_idc;
   1022         if (ucPreDeblockIdc != ucCurDeblockIdc) {
   1023             drv_debug_msg(VIDEO_DEBUG_ERROR,
   1024                 "%s L%d Error Macroblock Address (%d), deblock idc pre (%d), cur (%d)\n",
   1025                 __FUNCTION__, __LINE__, i, ucPreDeblockIdc, ucCurDeblockIdc);
   1026             return VA_STATUS_ERROR_INVALID_PARAMETER;
   1027         }
   1028         psSliceParamsH264++;
   1029     }
   1030 
   1031     if (uiAllMBNumbers != (unsigned int)(((IMG_UINT16)(ctx->ui16Width) * (IMG_UINT16)(ctx->ui16PictureHeight)) >> 8)) {
   1032         drv_debug_msg(VIDEO_DEBUG_ERROR,
   1033             "%s L%d Error Macroblock all number (%d), (%d)\n",
   1034             __FUNCTION__, __LINE__, i, uiAllMBNumbers,
   1035             ((ctx->ui16Width * ctx->ui16PictureHeight) >> 8));
   1036         return VA_STATUS_ERROR_INVALID_PARAMETER;
   1037     }
   1038 
   1039     //deblocking behaviour
   1040     ctx->bArbitrarySO = IMG_FALSE;
   1041     ctx->ui8DeblockIDC = ucCurDeblockIdc;
   1042     ctx->ui8SlicesPerPicture = obj_buffer->num_elements;
   1043 
   1044     return vaStatus;
   1045 }
   1046 
   1047 static VAStatus tng__H264ES_process_slice_param_mdfld(context_ENC_p ctx, object_buffer_p obj_buffer)
   1048 {
   1049     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1050     VAEncSliceParameterBuffer *psSliceParams = NULL;
   1051     psSliceParams = (VAEncSliceParameterBuffer*) obj_buffer->buffer_data;
   1052 
   1053     //deblocking behaviour
   1054     ctx->bArbitrarySO = IMG_FALSE;
   1055     ctx->ui8DeblockIDC = psSliceParams->slice_flags.bits.disable_deblocking_filter_idc;
   1056     ctx->ui8SlicesPerPicture = obj_buffer->num_elements;
   1057     return vaStatus;
   1058 }
   1059 
   1060 static VAStatus tng__H264ES_process_misc_max_slice_size_param(context_ENC_p ctx, object_buffer_p obj_buffer)
   1061 {
   1062     VAEncMiscParameterBuffer *pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
   1063     VAEncMiscParameterMaxSliceSize *psMiscMaxSliceSizeParams = NULL;
   1064     IMG_RC_PARAMS *psRCParams = &(ctx->sRCParams);
   1065 
   1066     ASSERT(obj_buffer->type == VAEncMiscParameterTypeMaxSliceSize);
   1067     ASSERT(obj_buffer->size == sizeof(VAEncMiscParameterMaxSliceSize));
   1068 
   1069     psMiscMaxSliceSizeParams = (VAEncMiscParameterMaxSliceSize*)pBuffer->data;
   1070 
   1071     if (psMiscMaxSliceSizeParams->max_slice_size > 0) {
   1072 	psRCParams->ui32SliceByteLimit = psMiscMaxSliceSizeParams->max_slice_size;
   1073 	drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1074 	    "Max slice size is %d\n", psRCParams->ui32SliceByteLimit);
   1075     } else {
   1076         drv_debug_msg(VIDEO_DEBUG_ERROR,
   1077             "%s: ERROR: invalid max slice size(%d), should bigger than 0\n",
   1078             __FUNCTION__, psMiscMaxSliceSizeParams->max_slice_size);
   1079 	psRCParams->ui32SliceByteLimit = 0;
   1080         return VA_STATUS_ERROR_INVALID_PARAMETER;
   1081     }
   1082 
   1083     return VA_STATUS_SUCCESS;
   1084 }
   1085 
   1086 static VAStatus tng__H264ES_process_slice_param(context_ENC_p ctx, object_buffer_p obj_buffer)
   1087 {
   1088     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1089     ASSERT(obj_buffer->type == VAEncSliceParameterBufferType);
   1090     /* Prepare InParams for macros of current slice, insert slice header, insert do slice command */
   1091 
   1092     if (obj_buffer->size == sizeof(VAEncSliceParameterBufferH264)) {
   1093         drv_debug_msg(VIDEO_DEBUG_GENERAL, "Receive VAEncSliceParameterBufferH264 buffer\n");
   1094         vaStatus = tng__H264ES_process_slice_param_mrfld(ctx, obj_buffer);
   1095     } else if (obj_buffer->size == sizeof(VAEncSliceParameterBuffer)) {
   1096         drv_debug_msg(VIDEO_DEBUG_GENERAL, "Receive VAEncSliceParameterBuffer buffer\n");
   1097         vaStatus = tng__H264ES_process_slice_param_mdfld(ctx, obj_buffer);
   1098     } else {
   1099         drv_debug_msg(VIDEO_DEBUG_ERROR, "Buffer size(%d) is wrong. It should be %d or %d\n",
   1100             obj_buffer->size, sizeof(VAEncSliceParameterBuffer),
   1101             sizeof(VAEncSliceParameterBufferH264));
   1102         vaStatus = VA_STATUS_ERROR_INVALID_PARAMETER;
   1103     }
   1104 
   1105     free(obj_buffer->buffer_data);
   1106     obj_buffer->size = 0;
   1107     obj_buffer->buffer_data = NULL;
   1108     return vaStatus;
   1109 }
   1110 
   1111 static VAStatus tng__H264ES_process_misc_param(context_ENC_p ctx, object_buffer_p obj_buffer)
   1112 {
   1113     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1114     VAEncMiscParameterBuffer *pBuffer;
   1115 
   1116     ASSERT(obj_buffer->type == VAEncMiscParameterBufferType);
   1117     ASSERT(ctx != NULL);
   1118     /* Transfer ownership of VAEncMiscParameterBuffer data */
   1119     pBuffer = (VAEncMiscParameterBuffer *) obj_buffer->buffer_data;
   1120     obj_buffer->size = 0;
   1121 
   1122     switch (pBuffer->type) {
   1123         case VAEncMiscParameterTypeFrameRate:
   1124             vaStatus = tng__H264ES_process_misc_framerate_param(ctx, obj_buffer);
   1125             break;
   1126         case VAEncMiscParameterTypeRateControl:
   1127             vaStatus = tng__H264ES_process_misc_ratecontrol_param(ctx, obj_buffer);
   1128             break;
   1129         case VAEncMiscParameterTypeHRD:
   1130             vaStatus = tng__H264ES_process_misc_hrd_param(ctx, obj_buffer);
   1131             break;
   1132         case VAEncMiscParameterTypeAIR:
   1133             vaStatus = tng__H264ES_process_misc_air_param(ctx, obj_buffer);
   1134             break;
   1135 	case VAEncMiscParameterTypeCIR:
   1136             vaStatus = tng__H264ES_process_misc_cir_param(ctx, obj_buffer);
   1137             break;
   1138 	case VAEncMiscParameterTypeMaxSliceSize:
   1139 	    vaStatus = tng__H264ES_process_misc_max_slice_size_param(ctx, obj_buffer);
   1140             break;
   1141         default:
   1142             break;
   1143     }
   1144     free(obj_buffer->buffer_data);
   1145     obj_buffer->buffer_data = NULL;
   1146 
   1147     return vaStatus;
   1148 }
   1149 
   1150 static void tng_H264ES_QueryConfigAttributes(
   1151     VAProfile __maybe_unused profile,
   1152     VAEntrypoint __maybe_unused entrypoint,
   1153     VAConfigAttrib *attrib_list,
   1154     int num_attribs)
   1155 {
   1156     int i;
   1157 
   1158     /* RateControl attributes */
   1159     for (i = 0; i < num_attribs; i++) {
   1160         switch (attrib_list[i].type) {
   1161         case VAConfigAttribRTFormat:
   1162             break;
   1163 
   1164         case VAConfigAttribRateControl:
   1165             attrib_list[i].value = VA_RC_NONE | VA_RC_CBR | VA_RC_VBR | VA_RC_VCM;
   1166             break;
   1167 
   1168         case VAConfigAttribEncAutoReference:
   1169             attrib_list[i].value = 1;
   1170             break;
   1171 
   1172         case VAConfigAttribEncMaxRefFrames:
   1173             attrib_list[i].value = 4;
   1174             break;
   1175 
   1176         default:
   1177             attrib_list[i].value = VA_ATTRIB_NOT_SUPPORTED;
   1178             break;
   1179         }
   1180     }
   1181 }
   1182 
   1183 static VAStatus tng_H264ES_ValidateConfig(
   1184     object_config_p obj_config)
   1185 {
   1186     int i;
   1187 
   1188     /* Check all attributes */
   1189     for (i = 0; i < obj_config->attrib_count; i++) {
   1190         switch (obj_config->attrib_list[i].type) {
   1191             case VAConfigAttribRTFormat:
   1192                 /* Ignore */
   1193                 break;
   1194             case VAConfigAttribRateControl:
   1195                 break;
   1196             case VAConfigAttribEncAutoReference:
   1197                 break;
   1198             case VAConfigAttribEncMaxRefFrames:
   1199                 break;
   1200             default:
   1201                 return VA_STATUS_ERROR_ATTR_NOT_SUPPORTED;
   1202         }
   1203     }
   1204 
   1205     return VA_STATUS_SUCCESS;
   1206 }
   1207 
   1208 static VAStatus tng_H264ES_setup_profile_features(context_ENC_p ctx)
   1209 {
   1210     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1211 
   1212     IMG_ENCODE_FEATURES * pEncFeatures = &ctx->sEncFeatures;
   1213     pEncFeatures->bEnable8x16MVDetect = IMG_TRUE;
   1214     pEncFeatures->bEnable16x8MVDetect = IMG_TRUE;
   1215 
   1216     return vaStatus;
   1217 }
   1218 
   1219 
   1220 static VAStatus tng_H264ES_CreateContext(
   1221     object_context_p obj_context,
   1222     object_config_p obj_config)
   1223 {
   1224     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1225     context_ENC_p ctx;
   1226 
   1227     vaStatus = tng_CreateContext(obj_context, obj_config, 0);
   1228 
   1229     if (VA_STATUS_SUCCESS != vaStatus)
   1230         return VA_STATUS_ERROR_ALLOCATION_FAILED;
   1231 
   1232     ctx = (context_ENC_p) obj_context->format_data;
   1233     ctx->eStandard = IMG_STANDARD_H264;
   1234 
   1235     tng__H264ES_init_context(obj_context, obj_config);
   1236 
   1237     vaStatus = tng__H264ES_init_profile(obj_context, obj_config);
   1238     if (vaStatus != VA_STATUS_SUCCESS) {
   1239         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: tng__H264ES_init_profile\n", __FUNCTION__);
   1240     }
   1241 
   1242     vaStatus = tng__H264ES_init_format_mode(obj_context, obj_config);
   1243     if (vaStatus != VA_STATUS_SUCCESS) {
   1244         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: tng__H264ES_init_format_mode\n", __FUNCTION__);
   1245     }
   1246 
   1247     vaStatus = tng__H264ES_get_codec_type(obj_context, obj_config);
   1248     if (vaStatus != VA_STATUS_SUCCESS) {
   1249         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: tng__H264ES_init_rc_mode\n", __FUNCTION__);
   1250     }
   1251 
   1252     vaStatus = tng_H264ES_setup_profile_features(ctx);
   1253     if (vaStatus != VA_STATUS_SUCCESS) {
   1254         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: tng__profile_features\n", __FUNCTION__);
   1255     }
   1256 
   1257     vaStatus = tng__patch_hw_profile(ctx);
   1258     if (vaStatus != VA_STATUS_SUCCESS) {
   1259         drv_debug_msg(VIDEO_DEBUG_ERROR, "%s: tng__patch_hw_profile\n", __FUNCTION__);
   1260     }
   1261 
   1262     return vaStatus;
   1263 }
   1264 
   1265 static void tng_H264ES_DestroyContext(
   1266     object_context_p obj_context)
   1267 {
   1268     tng_DestroyContext(obj_context, 0);
   1269 }
   1270 
   1271 static VAStatus tng_H264ES_BeginPicture(
   1272     object_context_p obj_context)
   1273 {
   1274     INIT_CONTEXT_H264ES;
   1275     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1276     vaStatus = tng_BeginPicture(ctx);
   1277     return vaStatus;
   1278 }
   1279 
   1280 static VAStatus tng_H264ES_RenderPicture(
   1281     object_context_p obj_context,
   1282     object_buffer_p *buffers,
   1283     int num_buffers)
   1284 {
   1285     INIT_CONTEXT_H264ES;
   1286     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1287     int i;
   1288 
   1289     for (i = 0; i < num_buffers; i++) {
   1290         object_buffer_p obj_buffer = buffers[i];
   1291         drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1292             "%s: type = %d, num = %d\n",
   1293             __FUNCTION__, obj_buffer->type, num_buffers);
   1294 
   1295         switch (obj_buffer->type) {
   1296             case VAEncSequenceParameterBufferType:
   1297                 drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1298                     "tng_H264_RenderPicture got VAEncSequenceParameterBufferType\n");
   1299                 vaStatus = tng__H264ES_process_sequence_param(ctx, obj_buffer);
   1300                 DEBUG_FAILURE;
   1301                 break;
   1302             case VAEncPictureParameterBufferType:
   1303                 drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1304                     "tng_H264_RenderPicture got VAEncPictureParameterBuffer\n");
   1305                 vaStatus = tng__H264ES_process_picture_param(ctx, obj_buffer);
   1306                 DEBUG_FAILURE;
   1307                 break;
   1308 
   1309             case VAEncSliceParameterBufferType:
   1310                 drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1311                     "tng_H264_RenderPicture got VAEncSliceParameterBufferType\n");
   1312                 vaStatus = tng__H264ES_process_slice_param(ctx, obj_buffer);
   1313                 DEBUG_FAILURE;
   1314                 break;
   1315 
   1316             case VAEncMiscParameterBufferType:
   1317                 drv_debug_msg(VIDEO_DEBUG_GENERAL,
   1318                     "tng_H264_RenderPicture got VAEncMiscParameterBufferType\n");
   1319                 vaStatus = tng__H264ES_process_misc_param(ctx, obj_buffer);
   1320                 DEBUG_FAILURE;
   1321                 break;
   1322             default:
   1323                 vaStatus = VA_STATUS_ERROR_UNKNOWN;
   1324                 DEBUG_FAILURE;
   1325         }
   1326         if (vaStatus != VA_STATUS_SUCCESS) {
   1327             break;
   1328         }
   1329     }
   1330     return vaStatus;
   1331 }
   1332 
   1333 static VAStatus tng_H264ES_EndPicture(
   1334     object_context_p obj_context)
   1335 {
   1336     INIT_CONTEXT_H264ES;
   1337     VAStatus vaStatus = VA_STATUS_SUCCESS;
   1338     vaStatus = tng_EndPicture(ctx);
   1339     return vaStatus;
   1340 }
   1341 
   1342 struct format_vtable_s tng_H264ES_vtable = {
   1343 queryConfigAttributes:
   1344     tng_H264ES_QueryConfigAttributes,
   1345 validateConfig:
   1346     tng_H264ES_ValidateConfig,
   1347 createContext:
   1348     tng_H264ES_CreateContext,
   1349 destroyContext:
   1350     tng_H264ES_DestroyContext,
   1351 beginPicture:
   1352     tng_H264ES_BeginPicture,
   1353 renderPicture:
   1354     tng_H264ES_RenderPicture,
   1355 endPicture:
   1356     tng_H264ES_EndPicture
   1357 };
   1358 
   1359 /*EOF*/
   1360