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

📄 umc_mp4_video_parser.cpp

📁 audio-video-codecs.rar语音编解码器
💻 CPP
📖 第 1 页 / 共 4 页
字号:
/* ///////////////////////////////////////////////////////////////////////
//
//               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.
//
//  Description:    MPEG-4 video headers parsing.
//
*/

#include "umc_mp4_video_parser.h"
#include "umc_mp4_spl.h"
#include "umc_automatic_mutex.h"

using namespace UMC;

const Ipp8u mp4_aux_comp_count[MP4_SHAPE_EXT_NUM+1] = {1, 1, 2, 2, 3, 1, 2, 1, 1, 2, 3, 2, 3, 0};

Ipp32u mp4_ShowBits(mp4_Info* pInfo, Ipp32s n)
{
    Ipp8u* ptr = pInfo->bufptr;
    Ipp32u tmp = (ptr[0] << 24) | (ptr[1] << 16) | (ptr[2] <<  8) | (ptr[3]);
    tmp <<= pInfo->bitoff;
    tmp >>= 32 - n;
    return tmp;
}


Ipp32u mp4_ShowBit(mp4_Info* pInfo)
{
    Ipp32u tmp = pInfo->bufptr[0];
    tmp >>= 7 - pInfo->bitoff;
    return (tmp & 1);
}


Ipp32u mp4_ShowBits9(mp4_Info* pInfo, Ipp32s n)
{
    Ipp8u* ptr = pInfo->bufptr;
    Ipp32u tmp = (ptr[0] <<  8) | ptr[1];
    tmp <<= (pInfo->bitoff + 16);
    tmp >>= 32 - n;
    return tmp;
}


void mp4_FlushBits(mp4_Info* pInfo, Ipp32s n)
{
    n = n + pInfo->bitoff;
    pInfo->bufptr += n >> 3;
    pInfo->bitoff = n & 7;
}


Ipp32u mp4_GetBits(mp4_Info* pInfo, Ipp32s n)
{
    Ipp8u* ptr = pInfo->bufptr;
    Ipp32u tmp = (ptr[0] << 24) | (ptr[1] << 16) | (ptr[2] <<  8) | (ptr[3]);
    tmp <<= pInfo->bitoff;
    tmp >>= 32 - n;
    n = n + pInfo->bitoff;
    pInfo->bufptr += n >> 3;
    pInfo->bitoff = n & 7;
    return tmp;
}


Ipp32u mp4_GetBit(mp4_Info* pInfo)
{
    Ipp32u tmp = pInfo->bufptr[0];
    if (pInfo->bitoff == 7) {
        pInfo->bitoff = 0;
        pInfo->bufptr ++;
    } else {
        tmp >>= 7 - pInfo->bitoff;
        pInfo->bitoff ++;
    }
    return (tmp & 1);
}


Ipp32u mp4_GetBits9(mp4_Info* pInfo, Ipp32s n)
{
    Ipp8u* ptr = pInfo->bufptr;
    Ipp32u tmp = (ptr[0] << 8) | ptr[1];
    tmp <<= (pInfo->bitoff + 16);
    tmp >>= 32 - n;
    n = n + pInfo->bitoff;
    pInfo->bufptr += n >> 3;
    pInfo->bitoff = n & 7;
    return tmp;
}


Ipp32s mp4_GetMarkerBit(mp4_Info* pInfo) {
    if (!mp4_GetBit(pInfo)) {
        mp4_Error("Error: wrong marker bit");
        return 0;
    }
    return 1;
}

mp4_Status mp4_Parse_VisualObject(mp4_Info* pInfo)
{
    mp4_VisualObject  *VO = &pInfo->VisualObject;

    VO->is_identifier = mp4_GetBit(pInfo);
    if (VO->is_identifier) {
        VO->verid = mp4_GetBits9(pInfo, 4);
        if ((VO->verid != 1) && (VO->verid != 2) && (VO->verid != 4) && (VO->verid != 5)) {
            VO->verid = 1;
            mp4_Error("Warning: invalid version number in VO");
        }
        VO->priority = mp4_GetBits9(pInfo, 3);
    } else
        VO->verid = 1;
    VO->type = mp4_GetBits9(pInfo, 4);
    if (VO->type != MP4_VISUAL_OBJECT_TYPE_VIDEO) {
        mp4_Error("Error: Unsupported object: visual_object_type != video ID");
        return MP4_STATUS_NOTSUPPORT;
    }
    VO->VideoSignalType.video_range = 0;
    VO->VideoSignalType.matrix_coefficients = MP4_VIDEO_COLORS_ITU_R_BT_709;
    if (VO->type == MP4_VISUAL_OBJECT_TYPE_VIDEO || VO->type == MP4_VISUAL_OBJECT_TYPE_TEXTURE) {
        VO->VideoSignalType.is_video_signal_type = mp4_GetBit(pInfo);
        if (VO->VideoSignalType.is_video_signal_type) {
            VO->VideoSignalType.video_format = mp4_GetBits9(pInfo, 3);
            VO->VideoSignalType.video_range = mp4_GetBit(pInfo);
            VO->VideoSignalType.is_colour_description = mp4_GetBit(pInfo);
            if (VO->VideoSignalType.is_colour_description) {
                VO->VideoSignalType.colour_primaries = mp4_GetBits9(pInfo, 8);
                VO->VideoSignalType.transfer_characteristics = mp4_GetBits9(pInfo, 8);
                VO->VideoSignalType.matrix_coefficients = mp4_GetBits9(pInfo, 8);
            }
        }
    }
    return MP4_STATUS_OK;
}

static mp4_Status mp4_Parse_QuantMatrix(mp4_Info* pInfo)
{
    Ipp32u  code;
    Ipp32s  i;

    for (i = 0; i < 64; i ++) {
        code = mp4_GetBits9(pInfo, 8);
        if (code == 0) break;
    }
    return MP4_STATUS_OK;
}

mp4_Status mp4_Parse_VideoObject(mp4_Info* pInfo)
{
    Ipp32u  code;
    Ipp32s  i;
    mp4_VisualObject  *VO = &pInfo->VisualObject;
    mp4_VideoObject  *VOL = &pInfo->VisualObject.VideoObject;

    VOL->short_video_header = 0;
    VOL->random_accessible_vol = mp4_GetBit(pInfo);
    VOL->type_indication = mp4_GetBits9(pInfo, 8);

    VOL->is_identifier = mp4_GetBit(pInfo);
    if (VOL->is_identifier) {
        VOL->verid = mp4_GetBits9(pInfo, 4);
        if ((VOL->verid != 1) && (VOL->verid != 2) && (VOL->verid != 4) && (VOL->verid != 5)) {
            mp4_Error("Warning: invalid version number in VOL");
            VOL->verid = VO->verid;
        }
        VOL->priority = mp4_GetBits9(pInfo, 3);
    } else
        VOL->verid = VO->verid;
    VOL->aspect_ratio_info = mp4_GetBits9(pInfo, 4);
    if (VOL->aspect_ratio_info == MP4_ASPECT_RATIO_EXTPAR) {
        VOL->aspect_ratio_info_par_width = mp4_GetBits9(pInfo, 8);
        VOL->aspect_ratio_info_par_height = mp4_GetBits9(pInfo, 8);
    }
    VOL->is_vol_control_parameters = mp4_GetBit(pInfo);
    if (VOL->is_vol_control_parameters) {
        VOL->VOLControlParameters.chroma_format = mp4_GetBits9(pInfo, 2);
        if (VOL->VOLControlParameters.chroma_format != MP4_CHROMA_FORMAT_420) {
            mp4_Error("Error: vol_control_parameters.chroma_format != 4:2:0");
            return MP4_STATUS_PARSE_ERROR;
        }
        VOL->VOLControlParameters.low_delay = mp4_GetBit(pInfo);
        VOL->VOLControlParameters.vbv_parameters = mp4_GetBit(pInfo);
        if (VOL->VOLControlParameters.vbv_parameters) {
            VOL->VOLControlParameters.bit_rate = mp4_GetBits(pInfo, 15) << 15;
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            VOL->VOLControlParameters.bit_rate += mp4_GetBits(pInfo, 15);
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            if (VOL->VOLControlParameters.bit_rate == 0) {
                mp4_Error("Error: vbv_parameters bit_rate == 0");
                return MP4_STATUS_PARSE_ERROR;
            }
            VOL->VOLControlParameters.vbv_buffer_size = mp4_GetBits(pInfo, 15) << 3;
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            VOL->VOLControlParameters.vbv_buffer_size += mp4_GetBits9(pInfo, 3);
            if (VOL->VOLControlParameters.vbv_buffer_size == 0) {
                mp4_Error("Error: vbv_parameters vbv_buffer_size == 0");
                return MP4_STATUS_PARSE_ERROR;
            }
            VOL->VOLControlParameters.vbv_occupancy = mp4_GetBits(pInfo, 11) << 15;
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            VOL->VOLControlParameters.vbv_occupancy += mp4_GetBits(pInfo, 15);
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
        }
    }
    VOL->shape = mp4_GetBits9(pInfo, 2);
    if (VOL->shape != MP4_SHAPE_TYPE_RECTANGULAR) {
        mp4_Error("Error: video_object_layer_shape != rectangular (not supported)");
        return MP4_STATUS_NOTSUPPORT;
    }
    if (VOL->verid != 1 && VOL->shape == MP4_SHAPE_TYPE_GRAYSCALE) {
        VOL->shape_extension = mp4_GetBits9(pInfo, 4);
        if (VOL->shape_extension >= MP4_SHAPE_EXT_NUM) {
            mp4_Error("Error: wrong value for video_object_layer_shape_extension");
            return MP4_STATUS_PARSE_ERROR;
        }
    } else
        VOL->shape_extension = MP4_SHAPE_EXT_NUM;
    if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
    VOL->vop_time_increment_resolution = mp4_GetBits(pInfo, 16);
    if (VOL->vop_time_increment_resolution == 0) {
        mp4_Error("Error: wrong value for vop_time_increment_resolution");
        return MP4_STATUS_PARSE_ERROR;
    }
    if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
    // define number bits in vop_time_increment_resolution
    code = VOL->vop_time_increment_resolution - 1;
    i = 0;
    do {
        code >>= 1;
        i ++;
    } while (code);
    VOL->vop_time_increment_resolution_bits = i;
    VOL->fixed_vop_rate = mp4_GetBit(pInfo);
    if (VOL->fixed_vop_rate) {
        VOL->fixed_vop_time_increment = mp4_GetBits(pInfo, VOL->vop_time_increment_resolution_bits);
    }
    if (VOL->shape != MP4_SHAPE_TYPE_BINARYONLY) {
        if (VOL->shape == MP4_SHAPE_TYPE_RECTANGULAR) {
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            VOL->width = mp4_GetBits(pInfo, 13);
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;
            VOL->height = mp4_GetBits(pInfo, 13);
            if (!mp4_GetMarkerBit(pInfo)) return MP4_STATUS_PARSE_ERROR;

⌨️ 快捷键说明

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