⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 umc_avs_dec_bit_stream.cpp

📁 audio-video-codecs.rar语音编解码器
💻 CPP
字号:
/*
//
//              INTEL CORPORATION PROPRIETARY INFORMATION
//  This software is supplied under the terms of a license  agreement or
//  nondisclosure agreement with Intel Corporation and may not be copied
//  or disclosed except in  accordance  with the terms of that agreement.
//    Copyright (c) 2007 Intel Corporation. All Rights Reserved.
//
//
*/

#include "umc_defs.h"
#if defined(UMC_ENABLE_AVS_VIDEO_DECODER)

#include "umc_avs_dec_bit_stream.h"
#include "umc_avs_sequence_header.h"
#include "umc_avs_picture_header.h"
#include "umc_avs_slice_header.h"

namespace UMC
{

void DecodePicHeader(AVS_BIT_STREAM_CONTEXT *pCtx,
                     AVS_SEQUENCE_HEADER *pSeqHeader,
                     AVS_PICTURE_HEADER *pPicHeader)
{
    // reset header
    memset(pPicHeader, 0, sizeof(AVS_PICTURE_HEADER));

    // read the start code
    SkipBits(pCtx, 24);

    // get picture type
    pPicHeader->picture_start_code = GetBits(pCtx, 8);

    // read information about I frame
    if (I_PICTURE_START_CODE == pPicHeader->picture_start_code)
    {
        pPicHeader->PictureType = AVS_I_PICTURE;
        pPicHeader->bbv_delay = GetBits(pCtx, 16);
        pPicHeader->time_code_flag = GetBit(pCtx);
        if (pPicHeader->time_code_flag)
            pPicHeader->time_code = GetBits(pCtx, 24);
        // NOTE: it is absent in standard, but
        // reference code has the following 1 bit skipping
        SkipBits(pCtx, 1);
        pPicHeader->picture_distance = GetBits(pCtx, 8);
        if (pSeqHeader->low_delay)
            pPicHeader->bbv_check_times = GetUE(pCtx);
        pPicHeader->progressive_frame = GetBit(pCtx);
        if (0 == pPicHeader->progressive_frame)
            pPicHeader->picture_structure = GetBit(pCtx);
        else
            pPicHeader->picture_structure = 1;
        pPicHeader->top_field_first = GetBit(pCtx);
        pPicHeader->repeat_first_field = GetBit(pCtx);
        pPicHeader->fixed_picture_qp = GetBit(pCtx);
        pPicHeader->picture_qp = GetBits(pCtx, 6);
        if ((0 == pPicHeader->progressive_frame) &&
            (0 == pPicHeader->picture_structure))
            pPicHeader->skip_mode_flag = GetBit(pCtx);
        SkipBits(pCtx, 4);
        pPicHeader->loop_filter_disable = GetBit(pCtx);
        if (0 == pPicHeader->loop_filter_disable)
        {
            pPicHeader->loop_filter_parameter_flag = GetBit(pCtx);
            if (pPicHeader->loop_filter_parameter_flag)
            {
                pPicHeader->alpha_c_offset = GetSE(pCtx);
                pPicHeader->beta_offset = GetSE(pCtx);
            }
        }
    }
    // read information about P,B frame
    else
    {
        pPicHeader->bbv_delay = GetBits(pCtx, 16);
        pPicHeader->picture_coding_type = GetBits(pCtx, 2);
        pPicHeader->PictureType = (1 == pPicHeader->picture_coding_type) ? (AVS_P_PICTURE) : (AVS_B_PICTURE);
        pPicHeader->picture_distance = GetBits(pCtx, 8);
        if (pSeqHeader->low_delay)
            pPicHeader->bbv_check_times = GetUE(pCtx);

        pPicHeader->progressive_frame = GetBit(pCtx);
        if (0 == pPicHeader->progressive_frame)
        {
            pPicHeader->picture_structure = GetBit(pCtx);
            if (0 == pPicHeader->picture_structure)
                pPicHeader->advanced_pred_mode_disable = GetBit(pCtx);
        }
        else
            pPicHeader->picture_structure = 1;
        pPicHeader->top_field_first = GetBit(pCtx);
        pPicHeader->repeat_first_field = GetBit(pCtx);
        pPicHeader->fixed_picture_qp = GetBit(pCtx);
        pPicHeader->picture_qp = GetBits(pCtx, 6);
        if ((AVS_P_PICTURE == pPicHeader->PictureType) ||
            (0 == pPicHeader->picture_structure))
            pPicHeader->picture_reference_flag = GetBit(pCtx);
        pPicHeader->no_forward_reference_flag = GetBit(pCtx);
        SkipBits(pCtx, 3);
        pPicHeader->skip_mode_flag = GetBit(pCtx);
        pPicHeader->loop_filter_disable = GetBit(pCtx);
        if (0 == pPicHeader->loop_filter_disable)
        {
            pPicHeader->loop_filter_parameter_flag = GetBit(pCtx);
            if (pPicHeader->loop_filter_parameter_flag)
            {
                pPicHeader->alpha_c_offset = GetSE(pCtx);
                pPicHeader->beta_offset = GetSE(pCtx);
            }
        }
    }

} // void DecodePicHeader(AVS_BIT_STREAM_CONTEXT *pCtx,

void DecodeSlcHeader(AVS_BIT_STREAM_CONTEXT *pCtx,
                     AVS_SEQUENCE_HEADER *pSeqHeader,
                     AVS_PICTURE_HEADER *pPicHeader,
                     AVS_SLICE_HEADER *pSlcHeader)
{
    Ipp32s MbRow, MbIndex, MbWidth, MbHeight;

    // reset header
    memset(pSlcHeader, 0, sizeof(AVS_SLICE_HEADER));

    // read the start code
    SkipBits(pCtx, 24);

    // read information
    pSlcHeader->slice_vertical_position = GetBits(pCtx, 8);
    if (2800 < pSeqHeader->vertical_size)
        pSlcHeader->slice_vertical_position_extension = GetBits(pCtx, 3);
    if (0 == pPicHeader->fixed_picture_qp)
    {
        pSlcHeader->fixed_slice_qp = GetBit(pCtx);
        pSlcHeader->slice_qp = GetBits(pCtx, 6);
    }

    // calculate frame dimensions
    MbWidth = (pSeqHeader->horizontal_size + 15) / 16;
    if (pPicHeader->picture_structure)
        MbHeight = ((pSeqHeader->vertical_size + 15) / 16);
    else
        MbHeight = 2 * ((pSeqHeader->vertical_size + 31) / 32);

    // calculate the slice position
    MbRow = pSlcHeader->slice_vertical_position;
    if (2800 < pSeqHeader->vertical_size)
        MbRow += (pSlcHeader->slice_vertical_position_extension << 7);
    MbIndex = MbRow * MbWidth;
    pSlcHeader->first_mb = MbIndex;

    // correct first mb number when the second field is decoded
    if ((0 == pPicHeader->picture_structure) &&
        (MbWidth * MbHeight / 2 <= MbIndex))
    {
        pSlcHeader->first_mb -= MbWidth * MbHeight / 2;
        pSlcHeader->isSecondField = 1;
    }

    if (AVS_I_PICTURE != pPicHeader->PictureType)
    {
        pSlcHeader->slice_weighting_flag = GetBit(pCtx);
        if (pSlcHeader->slice_weighting_flag)
        {
            Ipp32s i, NumberOfReferenceFwd, NumberOfReferenceBwd;

            // calculate number of references
            NumberOfReferenceFwd = 0;
            NumberOfReferenceBwd = 0;
            // second field of I frame is always P field
            if (I_PICTURE_START_CODE == pPicHeader->picture_start_code)
            {
                NumberOfReferenceFwd = 1;
            }
            else if (AVS_P_PICTURE == pPicHeader->PictureType)
            {
                if (pPicHeader->picture_structure)
                    NumberOfReferenceFwd = 2;
                else
                    NumberOfReferenceFwd = 4;
            }
            else
            {
                if (pPicHeader->picture_structure)
                {
                    NumberOfReferenceFwd = 1;
                    NumberOfReferenceBwd = 1;
                }
                else
                {
                    NumberOfReferenceFwd = 2;
                    NumberOfReferenceBwd = 2;
                }
            }

            // read forward weighting parameters
            for (i = 0; i < NumberOfReferenceFwd; i += 1)
            {
                pSlcHeader->luma_scale[AVS_FORWARD][i] = GetBits(pCtx, 8);
                pSlcHeader->luma_shift[AVS_FORWARD][i] = GetSignedBits(pCtx, 8);
                SkipBits(pCtx, 1);
                pSlcHeader->chroma_scale[AVS_FORWARD][i] = GetBits(pCtx, 8);
                pSlcHeader->chroma_shift[AVS_FORWARD][i] = GetSignedBits(pCtx, 8);
                SkipBits(pCtx, 1);
            }
            // read backward weighting parameters
            for (i = 0; i < NumberOfReferenceBwd; i += 1)
            {
                pSlcHeader->luma_scale[AVS_BACKWARD][i] = GetBits(pCtx, 8);
                pSlcHeader->luma_shift[AVS_BACKWARD][i] = GetSignedBits(pCtx, 8);
                SkipBits(pCtx, 1);
                pSlcHeader->chroma_scale[AVS_BACKWARD][i] = GetBits(pCtx, 8);
                pSlcHeader->chroma_shift[AVS_BACKWARD][i] = GetSignedBits(pCtx, 8);
                SkipBits(pCtx, 1);
            }
            pSlcHeader->mb_weighting_flag = GetBit(pCtx);
        }
    }

} // void DecodeSlcHeader(AVS_BIT_STREAM_CONTEXT *pCtx,

Ipp32s GetFieldNum(Ipp32u *pSlcData,
                   AVS_SEQUENCE_HEADER *pSeqHeader,
                   AVS_PICTURE_HEADER *pPicHeader)
{
    AVS_BIT_STREAM_CONTEXT ctx;
    Ipp32u slice_vertical_position;
    Ipp32u slice_vertical_position_extension;
    Ipp32u MbHeight, MbRow;

    // this is a frame, there are no fields
    if (pPicHeader->picture_structure)
        return 0;

    ctx.src = pSlcData;
    ctx.offset = 31;

    // read the start code
    SkipBits(&ctx, 24);

    // read information
    slice_vertical_position = GetBits(&ctx, 8);
    if (2800 < pSeqHeader->vertical_size)
        slice_vertical_position_extension = GetBits(&ctx, 3);
    else
        slice_vertical_position_extension = 0;

    // calculate frame dimensions
    if (pPicHeader->picture_structure)
        MbHeight = ((pSeqHeader->vertical_size + 15) / 16);
    else
        MbHeight = 2 * ((pSeqHeader->vertical_size + 31) / 32);

    // calculate the slice position
    MbRow = slice_vertical_position;
    if (2800 < pSeqHeader->vertical_size)
        MbRow += (slice_vertical_position_extension << 7);

    if (MbHeight / 2 <= MbRow)
        return 1;
    else
        return 0;

} // Ipp32s GetFieldNum(Ipp32u *pSlcData,

} // namespace UMC

#endif // #if defined(UMC_ENABLE_AVS_VIDEO_DECODER)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -