Commit dd80d6a6 by xiongziliang

Merge branch 'dev' of https://github.com/zqsong/ZLMediaKit into zqsong

parents 1f890198 0d57664f
......@@ -32,24 +32,40 @@ namespace mediakit{
bool getAVCH265Info(const string& strSps,int &iVideoWidth, int &iVideoHeight, float &iVideoFps) {
return getAVC265Info(strSps.data(),strSps.size(),iVideoWidth,iVideoHeight,iVideoFps);
bool getAVCH265Info(const string& strVps, const string& strSps,int &iVideoWidth, int &iVideoHeight, float &iVideoFps) {
return getAVC265Info(strVps.data(),strVps.size(),strSps.data(),strSps.size(),iVideoWidth,iVideoHeight,iVideoFps);
}
bool getAVC265Info(const char * sps,int sps_len,int &iVideoWidth, int &iVideoHeight, float &iVideoFps){
bool getAVC265Info(const char * vps, int vps_len,const char * sps,int sps_len,int &iVideoWidth, int &iVideoHeight, float &iVideoFps){
T_GetBitContext tGetBitBuf;
T_HEVCSPS tH265SpsInfo;
T_HEVCVPS tH265VpsInfo;
if ( vps_len > 2 ){
memset(&tGetBitBuf,0,sizeof(tGetBitBuf));
memset(&tH265VpsInfo,0,sizeof(tH265VpsInfo));
tGetBitBuf.pu8Buf = (uint8_t*)vps+2;
tGetBitBuf.iBufSize = vps_len-2;
if(0 != h265DecVideoParameterSet((void *) &tGetBitBuf, &tH265VpsInfo)){
return false;
}
}
if ( sps_len > 2 ){
memset(&tGetBitBuf,0,sizeof(tGetBitBuf));
memset(&tH265SpsInfo,0,sizeof(tH265SpsInfo));
tGetBitBuf.pu8Buf = (uint8_t*)sps ;
tGetBitBuf.iBufSize = sps_len ;
tGetBitBuf.pu8Buf = (uint8_t*)sps+2;
tGetBitBuf.iBufSize = sps_len-2;
if(0 != h265DecSeqParameterSet((void *) &tGetBitBuf, &tH265SpsInfo)){
return false;
}
}
else
return false;
h265GetWidthHeight(&tH265SpsInfo, &iVideoWidth, &iVideoHeight);
h265GeFramerate(&tH265SpsInfo, &iVideoFps);
//ErrorL << iVideoWidth << " " << iVideoHeight << " " << iVideoFps;
iVideoFps = 0;
h265GeFramerate(&tH265VpsInfo, &tH265SpsInfo, &iVideoFps);
// ErrorL << iVideoWidth << " " << iVideoHeight << " " << iVideoFps;
return true;
}
......
......@@ -36,8 +36,8 @@ using namespace toolkit;
namespace mediakit {
bool getAVCH265Info(const string& strSps,int &iVideoWidth, int &iVideoHeight, float &iVideoFps);
bool getAVC265Info(const char * sps,int sps_len,int &iVideoWidth, int &iVideoHeight, float &iVideoFps);
bool getAVCH265Info(const string& strVps,const string& strSps,int &iVideoWidth, int &iVideoHeight, float &iVideoFps);
bool getAVC265Info(const char * vps, int vps_len,const char * sps,int sps_len,int &iVideoWidth, int &iVideoHeight, float &iVideoFps);
/**
* 265帧类
......@@ -336,7 +336,7 @@ private:
* 解析sps获取宽高fps
*/
void onReady(){
getAVCH265Info(_sps,_width,_height,_fps);
getAVCH265Info(_vps,_sps,_width,_height,_fps);
}
Track::Ptr clone() override {
return std::make_shared<std::remove_reference<decltype(*this)>::type>(*this);
......
......@@ -129,15 +129,15 @@ const uint8_t g_au8FfZigzagDirect[64] = {
};
static const uint8_t hevc_sub_width_c[] = {
static const uint8_t sg_au8HevcSubWidthC[] = {
1, 2, 2, 1
};
static const uint8_t hevc_sub_height_c[] = {
static const uint8_t sg_au8HevcSubHeightC[] = {
1, 2, 1, 1
};
static const uint8_t default_scaling_list_intra[] = {
static const uint8_t sg_au8DefaultScalingListIntra[] = {
16, 16, 16, 16, 17, 18, 21, 24,
16, 16, 16, 16, 17, 19, 22, 25,
16, 16, 17, 18, 20, 22, 25, 29,
......@@ -148,7 +148,7 @@ static const uint8_t default_scaling_list_intra[] = {
24, 25, 29, 36, 47, 65, 88, 115
};
static const uint8_t default_scaling_list_inter[] = {
static const uint8_t sg_au8DefaultScalingListInter[] = {
16, 16, 16, 16, 17, 18, 20, 24,
16, 16, 16, 17, 18, 20, 24, 25,
16, 16, 17, 18, 20, 24, 25, 28,
......@@ -160,21 +160,21 @@ static const uint8_t default_scaling_list_inter[] = {
};
const uint8_t ff_hevc_diag_scan4x4_x[16] = {
const uint8_t g_au8HevcDiagScan4x4X[16] = {
0, 0, 1, 0,
1, 2, 0, 1,
2, 3, 1, 2,
3, 2, 3, 3,
};
const uint8_t ff_hevc_diag_scan4x4_y[16] = {
const uint8_t g_au8HevcDiagScan4x4Y[16] = {
0, 1, 0, 2,
1, 0, 3, 2,
1, 0, 3, 2,
1, 3, 2, 3,
};
const uint8_t ff_hevc_diag_scan8x8_x[64] = {
const uint8_t g_au8HevcDiagScan8x8X[64] = {
0, 0, 1, 0,
1, 2, 0, 1,
2, 3, 0, 1,
......@@ -193,7 +193,7 @@ const uint8_t ff_hevc_diag_scan8x8_x[64] = {
7, 6, 7, 7,
};
const uint8_t ff_hevc_diag_scan8x8_y[64] = {
const uint8_t g_au8HevcDiagScan8x8Y[64] = {
0, 1, 0, 2,
1, 0, 3, 2,
1, 0, 4, 3,
......@@ -212,7 +212,7 @@ const uint8_t ff_hevc_diag_scan8x8_y[64] = {
5, 7, 6, 7,
};
static const T_AVRational vui_sar[] = {
static const T_AVRational sg_atVuiSar[] = {
{ 0, 1 },
{ 1, 1 },
{ 12, 11 },
......@@ -733,17 +733,17 @@ static inline int decodeVuiParameters(void *pvBuf, T_SPS *ptSps)
ptSps->tSar.den = 0;
}
if (getOneBit(pvBuf)) /* overscan_info_present_flag */
getOneBit(pvBuf); /* overscan_appropriate_flag */
if (getOneBit(pvBuf)) /* iOverscanInfoPresentFlag */
getOneBit(pvBuf); /* iOverscanAppropriateFlag */
ptSps->iVideoSignalTypePresentFlag = getOneBit(pvBuf);
if (ptSps->iVideoSignalTypePresentFlag) {
getBits(pvBuf, 3); /* video_format */
ptSps->iFullRange = getOneBit(pvBuf); /* video_full_range_flag */
ptSps->iFullRange = getOneBit(pvBuf); /* iVideoFullRangeFlag */
ptSps->iColourDescriptionPresentFlag = getOneBit(pvBuf);
if (ptSps->iColourDescriptionPresentFlag) {
ptSps->tColorPrimaries = getBits(pvBuf, 8); /* colour_primaries */
ptSps->tColorPrimaries = getBits(pvBuf, 8); /* u8ColourPrimaries */
ptSps->tColorTrc = getBits(pvBuf, 8); /* transfer_characteristics */
ptSps->tColorspace = getBits(pvBuf, 8); /* matrix_coefficients */
if (ptSps->tColorPrimaries >= AVCOL_PRI_NB)
......@@ -1035,8 +1035,8 @@ int h264DecSeqParameterSet(void *pvBufSrc, T_SPS *ptSps)
unsigned int uiCropRight = parseUe(pvBuf);
unsigned int uiCropTop = parseUe(pvBuf);
unsigned int uiCropBottom = parseUe(pvBuf);
int width = 16 * ptSps->iMbWidth;
int height = 16 * ptSps->iMbHeight * (2 - ptSps->iFrameMbsOnlyFlag);
int iWidth = 16 * ptSps->iMbWidth;
int iHeight = 16 * ptSps->iMbHeight * (2 - ptSps->iFrameMbsOnlyFlag);
if(1)
{
......@@ -1055,11 +1055,11 @@ int h264DecSeqParameterSet(void *pvBufSrc, T_SPS *ptSps)
uiCropRight > (unsigned)INT_MAX / 4 / step_x ||
uiCropTop > (unsigned)INT_MAX / 4 / step_y ||
uiCropBottom> (unsigned)INT_MAX / 4 / step_y ||
(uiCropLeft + uiCropRight ) * step_x >= width ||
(uiCropTop + uiCropBottom) * step_y >= height
(uiCropLeft + uiCropRight ) * step_x >= iWidth ||
(uiCropTop + uiCropBottom) * step_y >= iHeight
)
{
RPT(RPT_ERR, "crop values invalid %d %d %d %d / %d %d\n", uiCropLeft, uiCropRight, uiCropTop, uiCropBottom, width, height);
RPT(RPT_ERR, "crop values invalid %d %d %d %d / %d %d\n", uiCropLeft, uiCropRight, uiCropTop, uiCropBottom, iWidth, iHeight);
iRet = -1;
goto exit;
}
......@@ -1129,37 +1129,37 @@ exit:
}
static int decodeProfileTierLevel(T_GetBitContext *pvBuf, T_PTLCommon *ptl)
static int decodeProfileTierLevel(T_GetBitContext *pvBuf, T_PTLCommon *tPtl)
{
int i;
if (getBitsLeft(pvBuf) < 2+1+5 + 32 + 4 + 16 + 16 + 12)
return -1;
ptl->profile_space = getBits(pvBuf, 2);
ptl->tier_flag = getOneBit(pvBuf);
ptl->profile_idc = getBits(pvBuf, 5);
if (ptl->profile_idc == T_PROFILE_HEVC_MAIN)
tPtl->u8ProfileSpace = getBits(pvBuf, 2);
tPtl->u8TierFlag = getOneBit(pvBuf);
tPtl->u8ProfileIdc = getBits(pvBuf, 5);
if (tPtl->u8ProfileIdc == T_PROFILE_HEVC_MAIN)
RPT(RPT_DBG, "Main profile bitstream\n");
else if (ptl->profile_idc == T_PROFILE_HEVC_MAIN_10)
else if (tPtl->u8ProfileIdc == T_PROFILE_HEVC_MAIN_10)
RPT(RPT_DBG, "Main 10 profile bitstream\n");
else if (ptl->profile_idc == T_PROFILE_HEVC_MAIN_STILL_PICTURE)
else if (tPtl->u8ProfileIdc == T_PROFILE_HEVC_MAIN_STILL_PICTURE)
RPT(RPT_DBG, "Main Still Picture profile bitstream\n");
else if (ptl->profile_idc == T_PROFILE_HEVC_REXT)
else if (tPtl->u8ProfileIdc == T_PROFILE_HEVC_REXT)
RPT(RPT_DBG, "Range Extension profile bitstream\n");
else
RPT(RPT_WRN, "Unknown HEVC profile: %d\n", ptl->profile_idc);
RPT(RPT_WRN, "Unknown HEVC profile: %d\n", tPtl->u8ProfileIdc);
for (i = 0; i < 32; i++) {
ptl->profile_compatibility_flag[i] = getOneBit(pvBuf);
tPtl->au8ProfileCompatibilityFlag[i] = getOneBit(pvBuf);
if (ptl->profile_idc == 0 && i > 0 && ptl->profile_compatibility_flag[i])
ptl->profile_idc = i;
if (tPtl->u8ProfileIdc == 0 && i > 0 && tPtl->au8ProfileCompatibilityFlag[i])
tPtl->u8ProfileIdc = i;
}
ptl->progressive_source_flag = getOneBit(pvBuf);
ptl->interlaced_source_flag = getOneBit(pvBuf);
ptl->non_packed_constraint_flag = getOneBit(pvBuf);
ptl->frame_only_constraint_flag = getOneBit(pvBuf);
tPtl->u8ProgressiveSourceFlag = getOneBit(pvBuf);
tPtl->u8InterlacedSourceFlag = getOneBit(pvBuf);
tPtl->u8NonPackedConstraintFlag = getOneBit(pvBuf);
tPtl->u8FrameOnlyConstraintFlag = getOneBit(pvBuf);
getBits(pvBuf, 16); // XXX_reserved_zero_44bits[0..15]
getBits(pvBuf, 16); // XXX_reserved_zero_44bits[16..31]
......@@ -1169,39 +1169,39 @@ static int decodeProfileTierLevel(T_GetBitContext *pvBuf, T_PTLCommon *ptl)
}
static int parsePtl(T_GetBitContext *pvBuf, T_PTL *ptl, int max_num_sub_layers)
static int parsePtl(T_GetBitContext *pvBuf, T_PTL *tPtl, int max_num_sub_layers)
{
int i;
if (decodeProfileTierLevel(pvBuf, &ptl->general_ptl) < 0 ||
if (decodeProfileTierLevel(pvBuf, &tPtl->tGeneralPtl) < 0 ||
getBitsLeft(pvBuf) < 8 + (8*2 * (max_num_sub_layers - 1 > 0))) {
RPT(RPT_ERR, "PTL information too short\n");
return -1;
}
ptl->general_ptl.level_idc = getBits(pvBuf, 8);
tPtl->tGeneralPtl.u8LevelIdc = getBits(pvBuf, 8);
for (i = 0; i < max_num_sub_layers - 1; i++) {
ptl->sub_layer_profile_present_flag[i] = getOneBit(pvBuf);
ptl->sub_layer_level_present_flag[i] = getOneBit(pvBuf);
tPtl->au8SubLayerProfilePresentFlag[i] = getOneBit(pvBuf);
tPtl->au8SubLayerLevelPresentFlag[i] = getOneBit(pvBuf);
}
if (max_num_sub_layers - 1> 0)
for (i = max_num_sub_layers - 1; i < 8; i++)
getBits(pvBuf, 2); // reserved_zero_2bits[i]
for (i = 0; i < max_num_sub_layers - 1; i++) {
if (ptl->sub_layer_profile_present_flag[i] &&
decodeProfileTierLevel(pvBuf, &ptl->sub_layer_ptl[i]) < 0) {
if (tPtl->au8SubLayerProfilePresentFlag[i] &&
decodeProfileTierLevel(pvBuf, &tPtl->atSubLayerPtl[i]) < 0) {
RPT(RPT_ERR,
"PTL information for sublayer %i too short\n", i);
return -1;
}
if (ptl->sub_layer_level_present_flag[i]) {
if (tPtl->au8SubLayerLevelPresentFlag[i]) {
if (getBitsLeft(pvBuf) < 8) {
RPT(RPT_ERR,
"Not enough data for sublayer %i level_idc\n", i);
return -1;
} else
ptl->sub_layer_ptl[i].level_idc = getBits(pvBuf, 8);
tPtl->atSubLayerPtl[i].u8LevelIdc = getBits(pvBuf, 8);
}
}
......@@ -1215,31 +1215,31 @@ static void setDefaultScalingListData(T_ScalingList *sl)
for (matrixId = 0; matrixId < 6; matrixId++) {
// 4x4 default is 16
memset(sl->sl[0][matrixId], 16, 16);
sl->sl_dc[0][matrixId] = 16; // default for 16x16
sl->sl_dc[1][matrixId] = 16; // default for 32x32
}
memcpy(sl->sl[1][0], default_scaling_list_intra, 64);
memcpy(sl->sl[1][1], default_scaling_list_intra, 64);
memcpy(sl->sl[1][2], default_scaling_list_intra, 64);
memcpy(sl->sl[1][3], default_scaling_list_inter, 64);
memcpy(sl->sl[1][4], default_scaling_list_inter, 64);
memcpy(sl->sl[1][5], default_scaling_list_inter, 64);
memcpy(sl->sl[2][0], default_scaling_list_intra, 64);
memcpy(sl->sl[2][1], default_scaling_list_intra, 64);
memcpy(sl->sl[2][2], default_scaling_list_intra, 64);
memcpy(sl->sl[2][3], default_scaling_list_inter, 64);
memcpy(sl->sl[2][4], default_scaling_list_inter, 64);
memcpy(sl->sl[2][5], default_scaling_list_inter, 64);
memcpy(sl->sl[3][0], default_scaling_list_intra, 64);
memcpy(sl->sl[3][1], default_scaling_list_intra, 64);
memcpy(sl->sl[3][2], default_scaling_list_intra, 64);
memcpy(sl->sl[3][3], default_scaling_list_inter, 64);
memcpy(sl->sl[3][4], default_scaling_list_inter, 64);
memcpy(sl->sl[3][5], default_scaling_list_inter, 64);
memset(sl->aaau8Sl[0][matrixId], 16, 16);
sl->aau8SlDc[0][matrixId] = 16; // default for 16x16
sl->aau8SlDc[1][matrixId] = 16; // default for 32x32
}
memcpy(sl->aaau8Sl[1][0], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[1][1], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[1][2], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[1][3], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[1][4], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[1][5], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[2][0], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[2][1], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[2][2], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[2][3], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[2][4], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[2][5], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[3][0], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[3][1], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[3][2], sg_au8DefaultScalingListIntra, 64);
memcpy(sl->aaau8Sl[3][3], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[3][4], sg_au8DefaultScalingListInter, 64);
memcpy(sl->aaau8Sl[3][5], sg_au8DefaultScalingListInter, 64);
}
static int scalingListData(T_GetBitContext *pvBuf, T_ScalingList *sl, T_HEVCSPS *sps)
static int scalingListData(T_GetBitContext *pvBuf, T_ScalingList *sl, T_HEVCSPS *ptSps)
{
uint8_t scaling_list_pred_mode_flag;
int32_t scaling_list_dc_coef[2][6];
......@@ -1262,11 +1262,11 @@ static int scalingListData(T_GetBitContext *pvBuf, T_ScalingList *sl, T_HEVCSPS
return -1;
}
memcpy(sl->sl[size_id][matrix_id],
sl->sl[size_id][matrix_id - delta],
memcpy(sl->aaau8Sl[size_id][matrix_id],
sl->aaau8Sl[size_id][matrix_id - delta],
size_id > 0 ? 64 : 16);
if (size_id > 1)
sl->sl_dc[size_id - 2][matrix_id] = sl->sl_dc[size_id - 2][matrix_id - delta];
sl->aau8SlDc[size_id - 2][matrix_id] = sl->aau8SlDc[size_id - 2][matrix_id - delta];
}
} else {
int next_coef, coef_num;
......@@ -1277,34 +1277,34 @@ static int scalingListData(T_GetBitContext *pvBuf, T_ScalingList *sl, T_HEVCSPS
if (size_id > 1) {
scaling_list_dc_coef[size_id - 2][matrix_id] = parseSe(pvBuf) + 8;
next_coef = scaling_list_dc_coef[size_id - 2][matrix_id];
sl->sl_dc[size_id - 2][matrix_id] = next_coef;
sl->aau8SlDc[size_id - 2][matrix_id] = next_coef;
}
for (i = 0; i < coef_num; i++) {
if (size_id == 0)
pos = 4 * ff_hevc_diag_scan4x4_y[i] +
ff_hevc_diag_scan4x4_x[i];
pos = 4 * g_au8HevcDiagScan4x4Y[i] +
g_au8HevcDiagScan4x4X[i];
else
pos = 8 * ff_hevc_diag_scan8x8_y[i] +
ff_hevc_diag_scan8x8_x[i];
pos = 8 * g_au8HevcDiagScan8x8Y[i] +
g_au8HevcDiagScan8x8X[i];
scaling_list_delta_coef = parseSe(pvBuf);
next_coef = (next_coef + 256U + scaling_list_delta_coef) % 256;
sl->sl[size_id][matrix_id][pos] = next_coef;
sl->aaau8Sl[size_id][matrix_id][pos] = next_coef;
}
}
}
if (sps->chroma_format_idc == 3) {
if (ptSps->iChromaFormatIdc == 3) {
for (i = 0; i < 64; i++) {
sl->sl[3][1][i] = sl->sl[2][1][i];
sl->sl[3][2][i] = sl->sl[2][2][i];
sl->sl[3][4][i] = sl->sl[2][4][i];
sl->sl[3][5][i] = sl->sl[2][5][i];
sl->aaau8Sl[3][1][i] = sl->aaau8Sl[2][1][i];
sl->aaau8Sl[3][2][i] = sl->aaau8Sl[2][2][i];
sl->aaau8Sl[3][4][i] = sl->aaau8Sl[2][4][i];
sl->aaau8Sl[3][5][i] = sl->aaau8Sl[2][5][i];
}
sl->sl_dc[1][1] = sl->sl_dc[0][1];
sl->sl_dc[1][2] = sl->sl_dc[0][2];
sl->sl_dc[1][4] = sl->sl_dc[0][4];
sl->sl_dc[1][5] = sl->sl_dc[0][5];
sl->aau8SlDc[1][1] = sl->aau8SlDc[0][1];
sl->aau8SlDc[1][2] = sl->aau8SlDc[0][2];
sl->aau8SlDc[1][4] = sl->aau8SlDc[0][4];
sl->aau8SlDc[1][5] = sl->aau8SlDc[0][5];
}
......@@ -1312,60 +1312,60 @@ static int scalingListData(T_GetBitContext *pvBuf, T_ScalingList *sl, T_HEVCSPS
}
int hevcDecodeShortTermRps(T_GetBitContext *pvBuf,
T_ShortTermRPS *rps, const T_HEVCSPS *sps, int is_slice_header)
T_ShortTermRPS *rps, const T_HEVCSPS *ptSps, int is_slice_header)
{
uint8_t rps_predict = 0;
int delta_poc;
int au32DeltaPoc;
int k0 = 0;
int k1 = 0;
int k = 0;
int i;
if (rps != sps->st_rps && sps->nb_st_rps)
if (rps != ptSps->atStRps && ptSps->uiNbStRps)
rps_predict = getOneBit(pvBuf);
if (rps_predict) {
const T_ShortTermRPS *rps_ridx;
int delta_rps;
unsigned abs_delta_rps;
uint8_t use_delta_flag = 0;
uint8_t delta_rps_sign;
const T_ShortTermRPS *ptRpsRidx;
int iDeltaRps;
unsigned int uiAbsDeltaRps;
uint8_t u8UseDeltaFlag = 0;
uint8_t u8DeltaRpsSign;
if (is_slice_header) {
unsigned int delta_idx = parseUe(pvBuf) + 1;
if (delta_idx > sps->nb_st_rps) {
unsigned int uiDeltaIdx = parseUe(pvBuf) + 1;
if (u8DeltaRpsSign > ptSps->uiNbStRps) {
RPT(RPT_ERR,
"Invalid value of delta_idx in slice header RPS: %d > %d.\n",
delta_idx, sps->nb_st_rps);
u8DeltaRpsSign, ptSps->uiNbStRps);
return -1;
}
rps_ridx = &sps->st_rps[sps->nb_st_rps - delta_idx];
rps->rps_idx_num_delta_pocs = rps_ridx->num_delta_pocs;
ptRpsRidx = &ptSps->atStRps[ptSps->uiNbStRps - u8DeltaRpsSign];
rps->iRpsIdxNumDeltaPocs = ptRpsRidx->iNumDeltaPocs;
} else
rps_ridx = &sps->st_rps[rps - sps->st_rps - 1];
ptRpsRidx = &ptSps->atStRps[rps - ptSps->atStRps - 1];
delta_rps_sign = getOneBit(pvBuf);
abs_delta_rps = parseUe(pvBuf) + 1;
if (abs_delta_rps < 1 || abs_delta_rps > 32768) {
u8DeltaRpsSign = getOneBit(pvBuf);
uiAbsDeltaRps = parseUe(pvBuf) + 1;
if (uiAbsDeltaRps < 1 || uiAbsDeltaRps > 32768) {
RPT(RPT_ERR,
"Invalid value of abs_delta_rps: %d\n",
abs_delta_rps);
"Invalid value of uiAbsDeltaRps: %d\n",
uiAbsDeltaRps);
return -1;
}
delta_rps = (1 - (delta_rps_sign << 1)) * abs_delta_rps;
for (i = 0; i <= rps_ridx->num_delta_pocs; i++) {
int used = rps->used[k] = getOneBit(pvBuf);
iDeltaRps = (1 - (u8DeltaRpsSign << 1)) * uiAbsDeltaRps;
for (i = 0; i <= ptRpsRidx->iNumDeltaPocs; i++) {
int used = rps->au8Used[k] = getOneBit(pvBuf);
if (!used)
use_delta_flag = getOneBit(pvBuf);
u8UseDeltaFlag = getOneBit(pvBuf);
if (used || use_delta_flag) {
if (i < rps_ridx->num_delta_pocs)
delta_poc = delta_rps + rps_ridx->delta_poc[i];
if (used || u8UseDeltaFlag) {
if (i < ptRpsRidx->iNumDeltaPocs)
au32DeltaPoc = iDeltaRps + ptRpsRidx->au32DeltaPoc[i];
else
delta_poc = delta_rps;
rps->delta_poc[k] = delta_poc;
if (delta_poc < 0)
au32DeltaPoc = iDeltaRps;
rps->au32DeltaPoc[k] = au32DeltaPoc;
if (au32DeltaPoc < 0)
k0++;
else
k1++;
......@@ -1373,83 +1373,83 @@ int hevcDecodeShortTermRps(T_GetBitContext *pvBuf,
}
}
if (k >= FF_ARRAY_ELEMS(rps->used)) {
if (k >= FF_ARRAY_ELEMS(rps->au8Used)) {
RPT(RPT_ERR,
"Invalid num_delta_pocs: %d\n", k);
"Invalid iNumDeltaPocs: %d\n", k);
return -1;
}
rps->num_delta_pocs = k;
rps->num_negative_pics = k0;
rps->iNumDeltaPocs = k;
rps->uiNumNegativePics = k0;
// sort in increasing order (smallest first)
if (rps->num_delta_pocs != 0) {
if (rps->iNumDeltaPocs != 0) {
int used, tmp;
for (i = 1; i < rps->num_delta_pocs; i++) {
delta_poc = rps->delta_poc[i];
used = rps->used[i];
for (i = 1; i < rps->iNumDeltaPocs; i++) {
au32DeltaPoc = rps->au32DeltaPoc[i];
used = rps->au8Used[i];
for (k = i - 1; k >= 0; k--) {
tmp = rps->delta_poc[k];
if (delta_poc < tmp) {
rps->delta_poc[k + 1] = tmp;
rps->used[k + 1] = rps->used[k];
rps->delta_poc[k] = delta_poc;
rps->used[k] = used;
tmp = rps->au32DeltaPoc[k];
if (au32DeltaPoc < tmp) {
rps->au32DeltaPoc[k + 1] = tmp;
rps->au8Used[k + 1] = rps->au8Used[k];
rps->au32DeltaPoc[k] = au32DeltaPoc;
rps->au8Used[k] = used;
}
}
}
}
if ((rps->num_negative_pics >> 1) != 0) {
if ((rps->uiNumNegativePics >> 1) != 0) {
int used;
k = rps->num_negative_pics - 1;
k = rps->uiNumNegativePics - 1;
// flip the negative values to largest first
for (i = 0; i < rps->num_negative_pics >> 1; i++) {
delta_poc = rps->delta_poc[i];
used = rps->used[i];
rps->delta_poc[i] = rps->delta_poc[k];
rps->used[i] = rps->used[k];
rps->delta_poc[k] = delta_poc;
rps->used[k] = used;
for (i = 0; i < rps->uiNumNegativePics >> 1; i++) {
au32DeltaPoc = rps->au32DeltaPoc[i];
used = rps->au8Used[i];
rps->au32DeltaPoc[i] = rps->au32DeltaPoc[k];
rps->au8Used[i] = rps->au8Used[k];
rps->au32DeltaPoc[k] = au32DeltaPoc;
rps->au8Used[k] = used;
k--;
}
}
} else {
unsigned int prev, nb_positive_pics;
rps->num_negative_pics = parseUe(pvBuf);
nb_positive_pics = parseUe(pvBuf);
unsigned int uiPrev, uiNbPositivePics;
rps->uiNumNegativePics = parseUe(pvBuf);
uiNbPositivePics = parseUe(pvBuf);
if (rps->num_negative_pics >= HEVC_MAX_REFS ||
nb_positive_pics >= HEVC_MAX_REFS) {
if (rps->uiNumNegativePics >= HEVC_MAX_REFS ||
uiNbPositivePics >= HEVC_MAX_REFS) {
RPT(RPT_ERR, "Too many refs in a short term RPS.\n");
return -1;
}
rps->num_delta_pocs = rps->num_negative_pics + nb_positive_pics;
if (rps->num_delta_pocs) {
prev = 0;
for (i = 0; i < rps->num_negative_pics; i++) {
delta_poc = parseUe(pvBuf) + 1;
if (delta_poc < 1 || delta_poc > 32768) {
rps->iNumDeltaPocs = rps->uiNumNegativePics + uiNbPositivePics;
if (rps->iNumDeltaPocs) {
uiPrev = 0;
for (i = 0; i < rps->uiNumNegativePics; i++) {
au32DeltaPoc = parseUe(pvBuf) + 1;
if (au32DeltaPoc < 1 || au32DeltaPoc > 32768) {
RPT(RPT_ERR,
"Invalid value of delta_poc: %d\n",
delta_poc);
"Invalid value of au32DeltaPoc: %d\n",
au32DeltaPoc);
return -1;
}
prev -= delta_poc;
rps->delta_poc[i] = prev;
rps->used[i] = getOneBit(pvBuf);
uiPrev -= au32DeltaPoc;
rps->au32DeltaPoc[i] = uiPrev;
rps->au8Used[i] = getOneBit(pvBuf);
}
prev = 0;
for (i = 0; i < nb_positive_pics; i++) {
delta_poc = parseUe(pvBuf) + 1;
if (delta_poc < 1 || delta_poc > 32768) {
uiPrev = 0;
for (i = 0; i < uiNbPositivePics; i++) {
au32DeltaPoc = parseUe(pvBuf) + 1;
if (au32DeltaPoc < 1 || au32DeltaPoc > 32768) {
RPT(RPT_ERR,
"Invalid value of delta_poc: %d\n",
delta_poc);
"Invalid value of au32DeltaPoc: %d\n",
au32DeltaPoc);
return -1;
}
prev += delta_poc;
rps->delta_poc[rps->num_negative_pics + i] = prev;
rps->used[rps->num_negative_pics + i] = getOneBit(pvBuf);
uiPrev += au32DeltaPoc;
rps->au32DeltaPoc[rps->uiNumNegativePics + i] = uiPrev;
rps->au8Used[rps->uiNumNegativePics + i] = getOneBit(pvBuf);
}
}
}
......@@ -1457,7 +1457,7 @@ int hevcDecodeShortTermRps(T_GetBitContext *pvBuf,
}
static void decodeSublayerHrd(T_GetBitContext *pvBuf, unsigned int nb_cpb,
int subpic_params_present)
int iSubpicParamsPresent)
{
int i;
......@@ -1465,7 +1465,7 @@ static void decodeSublayerHrd(T_GetBitContext *pvBuf, unsigned int nb_cpb,
parseUe(pvBuf); // bit_rate_value_minus1
parseUe(pvBuf); // cpb_size_value_minus1
if (subpic_params_present) {
if (iSubpicParamsPresent) {
parseUe(pvBuf); // cpb_size_du_value_minus1
parseUe(pvBuf); // bit_rate_du_value_minus1
}
......@@ -1476,18 +1476,18 @@ static void decodeSublayerHrd(T_GetBitContext *pvBuf, unsigned int nb_cpb,
static int decodeHrd(T_GetBitContext *pvBuf, int common_inf_present,
int max_sublayers)
{
int nal_params_present = 0, vcl_params_present = 0;
int subpic_params_present = 0;
int iNalParamsPresent = 0, iVclParamsPresent = 0;
int iSubpicParamsPresent = 0;
int i;
if (common_inf_present) {
nal_params_present = getOneBit(pvBuf);
vcl_params_present = getOneBit(pvBuf);
iNalParamsPresent = getOneBit(pvBuf);
iVclParamsPresent = getOneBit(pvBuf);
if (nal_params_present || vcl_params_present) {
subpic_params_present = getOneBit(pvBuf);
if (iNalParamsPresent || iVclParamsPresent) {
iSubpicParamsPresent = getOneBit(pvBuf);
if (subpic_params_present) {
if (iSubpicParamsPresent) {
getBits(pvBuf, 8); // tick_divisor_minus2
getBits(pvBuf, 5); // du_cpb_removal_delay_increment_length_minus1
getBits(pvBuf, 1); // sub_pic_cpb_params_in_pic_timing_sei_flag
......@@ -1497,7 +1497,7 @@ static int decodeHrd(T_GetBitContext *pvBuf, int common_inf_present,
getBits(pvBuf, 4); // bit_rate_scale
getBits(pvBuf, 4); // cpb_size_scale
if (subpic_params_present)
if (iSubpicParamsPresent)
getBits(pvBuf, 4); // cpb_size_du_scale
getBits(pvBuf, 5); // initial_cpb_removal_delay_length_minus1
......@@ -1509,12 +1509,12 @@ static int decodeHrd(T_GetBitContext *pvBuf, int common_inf_present,
for (i = 0; i < max_sublayers; i++) {
int low_delay = 0;
unsigned int nb_cpb = 1;
int fixed_rate = getOneBit(pvBuf);
int iFixedRate = getOneBit(pvBuf);
if (!fixed_rate)
fixed_rate = getOneBit(pvBuf);
if (!iFixedRate)
iFixedRate = getOneBit(pvBuf);
if (fixed_rate)
if (iFixedRate)
parseUe(pvBuf); // elemental_duration_in_tc_minus1
else
low_delay = getOneBit(pvBuf);
......@@ -1527,20 +1527,20 @@ static int decodeHrd(T_GetBitContext *pvBuf, int common_inf_present,
}
}
if (nal_params_present)
decodeSublayerHrd(pvBuf, nb_cpb, subpic_params_present);
if (vcl_params_present)
decodeSublayerHrd(pvBuf, nb_cpb, subpic_params_present);
if (iNalParamsPresent)
decodeSublayerHrd(pvBuf, nb_cpb, iSubpicParamsPresent);
if (iVclParamsPresent)
decodeSublayerHrd(pvBuf, nb_cpb, iSubpicParamsPresent);
}
return 0;
}
static void decodeVui(T_GetBitContext *pvBuf, T_HEVCSPS *sps)
static void decodeVui(T_GetBitContext *pvBuf, T_HEVCSPS *ptSps)
{
T_VUI backup_vui, *vui = &sps->vui;
T_GetBitContext backup;
T_VUI tBackupVui, *tVui = &ptSps->tVui;
T_GetBitContext tBackup;
int sar_present, alt = 0;
RPT(RPT_DBG, "Decoding VUI\n");
......@@ -1548,166 +1548,145 @@ static void decodeVui(T_GetBitContext *pvBuf, T_HEVCSPS *sps)
sar_present = getOneBit(pvBuf);
if (sar_present) {
uint8_t sar_idx = getBits(pvBuf, 8);
if (sar_idx < FF_ARRAY_ELEMS(vui_sar))
vui->sar = vui_sar[sar_idx];
if (sar_idx < FF_ARRAY_ELEMS(sg_atVuiSar))
tVui->tSar = sg_atVuiSar[sar_idx];
else if (sar_idx == 255) {
vui->sar.num = getBits(pvBuf, 16);
vui->sar.den = getBits(pvBuf, 16);
tVui->tSar.num = getBits(pvBuf, 16);
tVui->tSar.den = getBits(pvBuf, 16);
} else
RPT(RPT_WRN,
"Unknown SAR index: %u.\n", sar_idx);
}
vui->overscan_info_present_flag = getOneBit(pvBuf);
if (vui->overscan_info_present_flag)
vui->overscan_appropriate_flag = getOneBit(pvBuf);
vui->video_signal_type_present_flag = getOneBit(pvBuf);
if (vui->video_signal_type_present_flag) {
vui->video_format = getBits(pvBuf, 3);
vui->video_full_range_flag = getOneBit(pvBuf);
vui->colour_description_present_flag = getOneBit(pvBuf);
// if (vui->video_full_range_flag && sps->pix_fmt == AV_PIX_FMT_YUV420P)
// sps->pix_fmt = AV_PIX_FMT_YUVJ420P;
if (vui->colour_description_present_flag) {
vui->colour_primaries = getBits(pvBuf, 8);
vui->transfer_characteristic = getBits(pvBuf, 8);
vui->matrix_coeffs = getBits(pvBuf, 8);
#if 0
// Set invalid values to "unspecified"
if (!av_color_primaries_name(vui->colour_primaries))
vui->colour_primaries = AVCOL_PRI_UNSPECIFIED;
if (!av_color_transfer_name(vui->transfer_characteristic))
vui->transfer_characteristic = AVCOL_TRC_UNSPECIFIED;
if (!av_color_space_name(vui->matrix_coeffs))
vui->matrix_coeffs = AVCOL_SPC_UNSPECIFIED;
if (vui->matrix_coeffs == AVCOL_SPC_RGB) {
switch (sps->pix_fmt) {
case AV_PIX_FMT_YUV444P:
sps->pix_fmt = AV_PIX_FMT_GBRP;
break;
case AV_PIX_FMT_YUV444P10:
sps->pix_fmt = AV_PIX_FMT_GBRP10;
break;
case AV_PIX_FMT_YUV444P12:
sps->pix_fmt = AV_PIX_FMT_GBRP12;
break;
}
}
#endif
tVui->iOverscanInfoPresentFlag = getOneBit(pvBuf);
if (tVui->iOverscanInfoPresentFlag)
tVui->iOverscanAppropriateFlag = getOneBit(pvBuf);
tVui->iVideoSignalTypePresentFlag = getOneBit(pvBuf);
if (tVui->iVideoSignalTypePresentFlag) {
tVui->iVideoFormat = getBits(pvBuf, 3);
tVui->iVideoFullRangeFlag = getOneBit(pvBuf);
tVui->iColourDescriptionPresentFlag = getOneBit(pvBuf);
// if (tVui->iVideoFullRangeFlag && ptSps->pix_fmt == AV_PIX_FMT_YUV420P)
// ptSps->pix_fmt = AV_PIX_FMT_YUVJ420P;
if (tVui->iColourDescriptionPresentFlag) {
tVui->u8ColourPrimaries = getBits(pvBuf, 8);
tVui->u8TransferCharacteristic = getBits(pvBuf, 8);
tVui->u8MatrixCoeffs = getBits(pvBuf, 8);
}
}
vui->chroma_loc_info_present_flag = getOneBit(pvBuf);
if (vui->chroma_loc_info_present_flag) {
vui->chroma_sample_loc_type_top_field = parseUe(pvBuf);
vui->chroma_sample_loc_type_bottom_field = parseUe(pvBuf);
tVui->iChromaLocInfoPresentFlag = getOneBit(pvBuf);
if (tVui->iChromaLocInfoPresentFlag) {
tVui->iChromaSampleLocTypeTopField = parseUe(pvBuf);
tVui->iChromaSampleLocTypeBottomField = parseUe(pvBuf);
}
vui->neutra_chroma_indication_flag = getOneBit(pvBuf);
vui->field_seq_flag = getOneBit(pvBuf);
vui->frame_field_info_present_flag = getOneBit(pvBuf);
tVui->iNeutraChromaIndicationFlag = getOneBit(pvBuf);
tVui->iFieldSeqFlag = getOneBit(pvBuf);
tVui->iFrameFieldInfoPresentFlag = getOneBit(pvBuf);
// Backup context in case an alternate header is detected
memcpy(&backup, pvBuf, sizeof(backup));
memcpy(&backup_vui, vui, sizeof(backup_vui));
memcpy(&tBackup, pvBuf, sizeof(tBackup));
memcpy(&tBackupVui, tVui, sizeof(tBackupVui));
if (getBitsLeft(pvBuf) >= 68 && showBitsLong(pvBuf, 21) == 0x100000) {
vui->default_display_window_flag = 0;
tVui->iDefaultDisplayWindowFlag = 0;
RPT(RPT_WRN, "Invalid default display window\n");
} else
vui->default_display_window_flag = getOneBit(pvBuf);
tVui->iDefaultDisplayWindowFlag = getOneBit(pvBuf);
if (vui->default_display_window_flag) {
int vert_mult = hevc_sub_height_c[sps->chroma_format_idc];
int horiz_mult = hevc_sub_width_c[sps->chroma_format_idc];
vui->def_disp_win.left_offset = parseUe(pvBuf) * horiz_mult;
vui->def_disp_win.right_offset = parseUe(pvBuf) * horiz_mult;
vui->def_disp_win.top_offset = parseUe(pvBuf) * vert_mult;
vui->def_disp_win.bottom_offset = parseUe(pvBuf) * vert_mult;
if (tVui->iDefaultDisplayWindowFlag) {
int vert_mult = sg_au8HevcSubHeightC[ptSps->iChromaFormatIdc];
int horiz_mult = sg_au8HevcSubWidthC[ptSps->iChromaFormatIdc];
tVui->tDefDispWin.uiLeftOffset = parseUe(pvBuf) * horiz_mult;
tVui->tDefDispWin.uiRightOffset = parseUe(pvBuf) * horiz_mult;
tVui->tDefDispWin.uiTopOffset = parseUe(pvBuf) * vert_mult;
tVui->tDefDispWin.uiBottomOffset = parseUe(pvBuf) * vert_mult;
}
timing_info:
vui->vui_timing_info_present_flag = getOneBit(pvBuf);
tVui->iVuiTimingInfoPresentFlag = getOneBit(pvBuf);
if (vui->vui_timing_info_present_flag) {
if (tVui->iVuiTimingInfoPresentFlag) {
if( getBitsLeft(pvBuf) < 66 && !alt) {
// The alternate syntax seem to have timing info located
// at where def_disp_win is normally located
// at where tDefDispWin is normally located
RPT(RPT_WRN,
"Strange VUI timing information, retrying...\n");
memcpy(vui, &backup_vui, sizeof(backup_vui));
memcpy(pvBuf, &backup, sizeof(backup));
memcpy(tVui, &tBackupVui, sizeof(tBackupVui));
memcpy(pvBuf, &tBackup, sizeof(tBackup));
alt = 1;
goto timing_info;
}
vui->vui_num_units_in_tick = getBits(pvBuf, 32);
vui->vui_time_scale = getBits(pvBuf, 32);
tVui->u32VuiNumUnitsInTick = getBits(pvBuf, 32);
tVui->u32VuiTimeScale = getBits(pvBuf, 32);
if (alt) {
RPT(RPT_INF, "Retry got %u/%u fps\n",
vui->vui_time_scale, vui->vui_num_units_in_tick);
tVui->u32VuiTimeScale, tVui->u32VuiNumUnitsInTick);
}
vui->vui_poc_proportional_to_timing_flag = getOneBit(pvBuf);
if (vui->vui_poc_proportional_to_timing_flag)
vui->vui_num_ticks_poc_diff_one_minus1 = parseUe(pvBuf);
vui->vui_hrd_parameters_present_flag = getOneBit(pvBuf);
if (vui->vui_hrd_parameters_present_flag)
decodeHrd(pvBuf, 1, sps->max_sub_layers);
tVui->iVuiPocProportionalToTimingFlag = getOneBit(pvBuf);
if (tVui->iVuiPocProportionalToTimingFlag)
tVui->iVuiNumTicksPocDiffOneMinus1 = parseUe(pvBuf);
tVui->iVuiHrdParametersPresentFlag = getOneBit(pvBuf);
if (tVui->iVuiHrdParametersPresentFlag)
decodeHrd(pvBuf, 1, ptSps->iMaxSubLayers);
}
vui->bitstream_restriction_flag = getOneBit(pvBuf);
if (vui->bitstream_restriction_flag) {
tVui->iBitstreamRestrictionFlag = getOneBit(pvBuf);
if (tVui->iBitstreamRestrictionFlag) {
if (getBitsLeft(pvBuf) < 8 && !alt) {
RPT(RPT_WRN,
"Strange VUI bitstream restriction information, retrying"
" from timing information...\n");
memcpy(vui, &backup_vui, sizeof(backup_vui));
memcpy(pvBuf, &backup, sizeof(backup));
memcpy(tVui, &tBackupVui, sizeof(tBackupVui));
memcpy(pvBuf, &tBackup, sizeof(tBackup));
alt = 1;
goto timing_info;
}
vui->tiles_fixed_structure_flag = getOneBit(pvBuf);
vui->motion_vectors_over_pic_boundaries_flag = getOneBit(pvBuf);
vui->restricted_ref_pic_lists_flag = getOneBit(pvBuf);
vui->min_spatial_segmentation_idc = parseUe(pvBuf);
vui->max_bytes_per_pic_denom = parseUe(pvBuf);
vui->max_bits_per_min_cu_denom = parseUe(pvBuf);
vui->log2_max_mv_length_horizontal = parseUe(pvBuf);
vui->log2_max_mv_length_vertical = parseUe(pvBuf);
tVui->iTilesFixedStructureFlag = getOneBit(pvBuf);
tVui->iMotionVectorsOverPicBoundariesFlag = getOneBit(pvBuf);
tVui->iRestrictedRefPicListsFlag = getOneBit(pvBuf);
tVui->iMinSpatialSegmentationIdc = parseUe(pvBuf);
tVui->iMaxBytesPerPicDenom = parseUe(pvBuf);
tVui->iMaxBitsPerMinCuDenom = parseUe(pvBuf);
tVui->iLog2MaxMvLengthHorizontal = parseUe(pvBuf);
tVui->iLog2MaxMvLengthVertical = parseUe(pvBuf);
}
if (getBitsLeft(pvBuf) < 1 && !alt) {
// XXX: Alternate syntax when sps_range_extension_flag != 0?
// XXX: Alternate syntax when iSpsRangeExtensionFlag != 0?
RPT(RPT_WRN,
"Overread in VUI, retrying from timing information...\n");
memcpy(vui, &backup_vui, sizeof(backup_vui));
memcpy(pvBuf, &backup, sizeof(backup));
memcpy(tVui, &tBackupVui, sizeof(tBackupVui));
memcpy(pvBuf, &tBackup, sizeof(tBackup));
alt = 1;
goto timing_info;
}
}
static unsigned avModUintp2c(unsigned a, unsigned p)
{
return a & ((1 << p) - 1);
}
int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *sps )
int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *ptSps )
{
T_HEVCWindow *ow;
// int ret = 0;
int log2_diff_max_min_transform_block_size;
int bit_depth_chroma, start, vui_present, sublayer_ordering_info;
int iLog2DiffMaxMinTransformBlockSize;
int iBitDepthChroma, iStart, iVuiPresent, iSublayerOrderingInfo;
int i;
int iRet = 0;
void *pvBuf = NULL;
if(NULL == pvBufSrc || NULL == sps)
if(NULL == pvBufSrc || NULL == ptSps)
{
RPT(RPT_ERR,"ERR null pointer\n");
iRet = -1;
goto exit;
}
memset((void *)sps, 0, sizeof(T_HEVCSPS));
memset((void *)ptSps, 0, sizeof(T_HEVCSPS));
pvBuf = deEmulationPrevention(pvBufSrc);
if(NULL == pvBuf)
......@@ -1717,34 +1696,25 @@ int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *sps )
goto exit;
}
// Coded parameters
sps->vps_id = getBits(pvBuf, 4);
if (sps->vps_id >= HEVC_MAX_VPS_COUNT) {
RPT(RPT_ERR, "VPS id out of range: %d\n", sps->vps_id);
ptSps->uiVpsId = getBits(pvBuf, 4);
if (ptSps->uiVpsId >= HEVC_MAX_VPS_COUNT) {
RPT(RPT_ERR, "VPS id out of range: %d\n", ptSps->uiVpsId);
iRet = -1;
goto exit;
}
#if 0
if (vps_list && !vps_list[sps->vps_id]) {
RPT(RPT_ERR, "VPS %d does not exist\n",
sps->vps_id);
return AVERROR_INVALIDDATA;
}
#endif
sps->max_sub_layers = getBits(pvBuf, 3) + 1;
if (sps->max_sub_layers > HEVC_MAX_SUB_LAYERS) {
ptSps->iMaxSubLayers = getBits(pvBuf, 3) + 1;
if (ptSps->iMaxSubLayers > HEVC_MAX_SUB_LAYERS) {
RPT(RPT_ERR, "sps_max_sub_layers out of range: %d\n",
sps->max_sub_layers);
ptSps->iMaxSubLayers);
iRet = -1;
goto exit;
}
sps->temporal_id_nesting_flag = getBits(pvBuf, 1);
if ((iRet = parsePtl(pvBuf, &sps->ptl, sps->max_sub_layers)) < 0)
ptSps->u8temporalIdNestingFlag = getBits(pvBuf, 1);
if ((iRet = parsePtl(pvBuf, &ptSps->tPtl, ptSps->iMaxSubLayers)) < 0)
goto exit;
int sps_id = parseUe(pvBuf);
......@@ -1754,320 +1724,290 @@ int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *sps )
goto exit;
}
sps->chroma_format_idc = parseUe(pvBuf);
if (sps->chroma_format_idc > 3U) {
RPT(RPT_ERR, "chroma_format_idc %d is invalid\n", sps->chroma_format_idc);
ptSps->iChromaFormatIdc = parseUe(pvBuf);
if (ptSps->iChromaFormatIdc > 3U) {
RPT(RPT_ERR, "iChromaFormatIdc %d is invalid\n", ptSps->iChromaFormatIdc);
iRet = -1;
goto exit;
}
if (sps->chroma_format_idc == 3)
sps->separate_colour_plane_flag = getOneBit(pvBuf);
if (sps->separate_colour_plane_flag)
sps->chroma_format_idc = 0;
if (ptSps->iChromaFormatIdc == 3)
ptSps->u8SeparateColourPlaneFlag = getOneBit(pvBuf);
sps->width = parseUe(pvBuf);
sps->height = parseUe(pvBuf);
if (ptSps->u8SeparateColourPlaneFlag)
ptSps->iChromaFormatIdc = 0;
// if ((iRet = av_image_check_size(sps->width,
// sps->height, 0, avctx)) < 0)
// goto exit;
ptSps->iWidth = parseUe(pvBuf);
ptSps->iHeight = parseUe(pvBuf);
if (getOneBit(pvBuf)) { // pic_conformance_flag
int vert_mult = hevc_sub_height_c[sps->chroma_format_idc];
int horiz_mult = hevc_sub_width_c[sps->chroma_format_idc];
sps->pic_conf_win.left_offset = parseUe(pvBuf) * horiz_mult;
sps->pic_conf_win.right_offset = parseUe(pvBuf) * horiz_mult;
sps->pic_conf_win.top_offset = parseUe(pvBuf) * vert_mult;
sps->pic_conf_win.bottom_offset = parseUe(pvBuf) * vert_mult;
int vert_mult = sg_au8HevcSubHeightC[ptSps->iChromaFormatIdc];
int horiz_mult = sg_au8HevcSubWidthC[ptSps->iChromaFormatIdc];
ptSps->tPicConfWin.uiLeftOffset = parseUe(pvBuf) * horiz_mult;
ptSps->tPicConfWin.uiRightOffset = parseUe(pvBuf) * horiz_mult;
ptSps->tPicConfWin.uiTopOffset = parseUe(pvBuf) * vert_mult;
ptSps->tPicConfWin.uiBottomOffset = parseUe(pvBuf) * vert_mult;
sps->output_window = sps->pic_conf_win;
ptSps->tOutputWindow = ptSps->tPicConfWin;
}
sps->bit_depth = parseUe(pvBuf) + 8;
bit_depth_chroma = parseUe(pvBuf) + 8;
ptSps->iBitDepth = parseUe(pvBuf) + 8;
iBitDepthChroma = parseUe(pvBuf) + 8;
if (sps->chroma_format_idc && bit_depth_chroma != sps->bit_depth) {
if (ptSps->iChromaFormatIdc && iBitDepthChroma != ptSps->iBitDepth) {
RPT(RPT_ERR,
"Luma bit depth (%d) is different from chroma bit depth (%d), "
"this is unsupported.\n",
sps->bit_depth, bit_depth_chroma);
ptSps->iBitDepth, iBitDepthChroma);
iRet = -1;
goto exit;
}
sps->bit_depth_chroma = bit_depth_chroma;
#if 0
iRet = map_pixel_format(avctx, sps);
if (iRet < 0)
goto exit;
#endif
#if 0
ptSps->iBitDepthChroma = iBitDepthChroma;
sps->log2_max_poc_lsb = parseUe(pvBuf) + 4;
if (sps->log2_max_poc_lsb > 16) {
ptSps->uiLog2MaxPocLsb = parseUe(pvBuf) + 4;
if (ptSps->uiLog2MaxPocLsb > 16) {
RPT(RPT_ERR, "log2_max_pic_order_cnt_lsb_minus4 out range: %d\n",
sps->log2_max_poc_lsb - 4);
ptSps->uiLog2MaxPocLsb - 4);
iRet = -1;
goto exit;
}
sublayer_ordering_info = getOneBit(pvBuf);
start = sublayer_ordering_info ? 0 : sps->max_sub_layers - 1;
for (i = start; i < sps->max_sub_layers; i++) {
sps->temporal_layer[i].max_dec_pic_buffering = parseUe(pvBuf) + 1;
sps->temporal_layer[i].num_reorder_pics = parseUe(pvBuf);
sps->temporal_layer[i].max_latency_increase = parseUe(pvBuf) - 1;
if (sps->temporal_layer[i].max_dec_pic_buffering > (unsigned)HEVC_MAX_DPB_SIZE) {
iSublayerOrderingInfo = getOneBit(pvBuf);
iStart = iSublayerOrderingInfo ? 0 : ptSps->iMaxSubLayers - 1;
for (i = iStart; i < ptSps->iMaxSubLayers; i++) {
ptSps->stTemporalLayer[i].iMaxDecPicBuffering = parseUe(pvBuf) + 1;
ptSps->stTemporalLayer[i].iNumReorderPics = parseUe(pvBuf);
ptSps->stTemporalLayer[i].iMaxLatencyIncrease = parseUe(pvBuf) - 1;
if (ptSps->stTemporalLayer[i].iMaxDecPicBuffering > (unsigned)HEVC_MAX_DPB_SIZE) {
RPT(RPT_ERR, "sps_max_dec_pic_buffering_minus1 out of range: %d\n",
sps->temporal_layer[i].max_dec_pic_buffering - 1U);
ptSps->stTemporalLayer[i].iMaxDecPicBuffering - 1U);
iRet = -1;
goto exit;
}
if (sps->temporal_layer[i].num_reorder_pics > sps->temporal_layer[i].max_dec_pic_buffering - 1) {
if (ptSps->stTemporalLayer[i].iNumReorderPics > ptSps->stTemporalLayer[i].iMaxDecPicBuffering - 1) {
RPT(RPT_WRN, "sps_max_num_reorder_pics out of range: %d\n",
sps->temporal_layer[i].num_reorder_pics);
if (sps->temporal_layer[i].num_reorder_pics > HEVC_MAX_DPB_SIZE - 1) {
ptSps->stTemporalLayer[i].iNumReorderPics);
if (ptSps->stTemporalLayer[i].iNumReorderPics > HEVC_MAX_DPB_SIZE - 1) {
iRet = -1;
goto exit;
}
sps->temporal_layer[i].max_dec_pic_buffering = sps->temporal_layer[i].num_reorder_pics + 1;
ptSps->stTemporalLayer[i].iMaxDecPicBuffering = ptSps->stTemporalLayer[i].iNumReorderPics + 1;
}
}
if (!sublayer_ordering_info) {
for (i = 0; i < start; i++) {
sps->temporal_layer[i].max_dec_pic_buffering = sps->temporal_layer[start].max_dec_pic_buffering;
sps->temporal_layer[i].num_reorder_pics = sps->temporal_layer[start].num_reorder_pics;
sps->temporal_layer[i].max_latency_increase = sps->temporal_layer[start].max_latency_increase;
if (!iSublayerOrderingInfo) {
for (i = 0; i < iStart; i++) {
ptSps->stTemporalLayer[i].iMaxDecPicBuffering = ptSps->stTemporalLayer[iStart].iMaxDecPicBuffering;
ptSps->stTemporalLayer[i].iNumReorderPics = ptSps->stTemporalLayer[iStart].iNumReorderPics;
ptSps->stTemporalLayer[i].iMaxLatencyIncrease = ptSps->stTemporalLayer[iStart].iMaxLatencyIncrease;
}
}
sps->log2_min_cb_size = parseUe(pvBuf) + 3;
sps->log2_diff_max_min_coding_block_size = parseUe(pvBuf);
sps->log2_min_tb_size = parseUe(pvBuf) + 2;
log2_diff_max_min_transform_block_size = parseUe(pvBuf);
sps->log2_max_trafo_size = log2_diff_max_min_transform_block_size +
sps->log2_min_tb_size;
ptSps->uiLog2MinCbSize = parseUe(pvBuf) + 3;
ptSps->uiLog2DiffMaxMinCodingBlockSize = parseUe(pvBuf);
ptSps->uiLog2MinTbSize = parseUe(pvBuf) + 2;
iLog2DiffMaxMinTransformBlockSize = parseUe(pvBuf);
ptSps->uiLog2MaxTrafoSize = iLog2DiffMaxMinTransformBlockSize +
ptSps->uiLog2MinTbSize;
if (sps->log2_min_cb_size < 3 || sps->log2_min_cb_size > 30) {
RPT(RPT_ERR, "Invalid value %d for log2_min_cb_size", sps->log2_min_cb_size);
if (ptSps->uiLog2MinCbSize < 3 || ptSps->uiLog2MinCbSize > 30) {
RPT(RPT_ERR, "Invalid value %d for uiLog2MinCbSize", ptSps->uiLog2MinCbSize);
iRet = -1;
goto exit;
}
if (sps->log2_diff_max_min_coding_block_size > 30) {
RPT(RPT_ERR, "Invalid value %d for log2_diff_max_min_coding_block_size", sps->log2_diff_max_min_coding_block_size);
if (ptSps->uiLog2DiffMaxMinCodingBlockSize > 30) {
RPT(RPT_ERR, "Invalid value %d for uiLog2DiffMaxMinCodingBlockSize", ptSps->uiLog2DiffMaxMinCodingBlockSize);
iRet = -1;
goto exit;
}
if (sps->log2_min_tb_size >= sps->log2_min_cb_size || sps->log2_min_tb_size < 2) {
RPT(RPT_ERR, "Invalid value for log2_min_tb_size");
if (ptSps->uiLog2MinTbSize >= ptSps->uiLog2MinCbSize || ptSps->uiLog2MinTbSize < 2) {
RPT(RPT_ERR, "Invalid value for uiLog2MinTbSize");
iRet = -1;
goto exit;
}
if (log2_diff_max_min_transform_block_size < 0 || log2_diff_max_min_transform_block_size > 30) {
RPT(RPT_ERR, "Invalid value %d for log2_diff_max_min_transform_block_size", log2_diff_max_min_transform_block_size);
if (iLog2DiffMaxMinTransformBlockSize < 0 || iLog2DiffMaxMinTransformBlockSize > 30) {
RPT(RPT_ERR, "Invalid value %d for iLog2DiffMaxMinTransformBlockSize", iLog2DiffMaxMinTransformBlockSize);
iRet = -1;
goto exit;
}
sps->max_transform_hierarchy_depth_inter = parseUe(pvBuf);
sps->max_transform_hierarchy_depth_intra = parseUe(pvBuf);
ptSps->iMaxTransformHierarchyDepthInter = parseUe(pvBuf);
ptSps->iMaxTransformHierarchyDepthIntra = parseUe(pvBuf);
sps->scaling_list_enable_flag = getOneBit(pvBuf);
ptSps->u8ScalingListEnableFlag = getOneBit(pvBuf);
printf("sps->scaling_list_enable_flag: %d\n",sps->scaling_list_enable_flag);
if (sps->scaling_list_enable_flag) {
setDefaultScalingListData(&sps->scaling_list);
if (ptSps->u8ScalingListEnableFlag) {
setDefaultScalingListData(&ptSps->tScalingList);
if (getOneBit(pvBuf)) {
iRet = scalingListData(pvBuf, &sps->scaling_list, sps);
iRet = scalingListData(pvBuf, &ptSps->tScalingList, ptSps);
if (iRet < 0)
goto exit;
}
}
sps->amp_enabled_flag = getOneBit(pvBuf);
sps->sao_enabled = getOneBit(pvBuf);
ptSps->u8AmpEnabledFlag = getOneBit(pvBuf);
ptSps->u8SaoEnabled = getOneBit(pvBuf);
sps->pcm_enabled_flag = getOneBit(pvBuf);
ptSps->iPcmEnabledFlag = getOneBit(pvBuf);
printf("sps->pcm_enabled_flag: %d\n",sps->pcm_enabled_flag);
if (sps->pcm_enabled_flag) {
sps->pcm.bit_depth = getBits(pvBuf, 4) + 1;
sps->pcm.bit_depth_chroma = getBits(pvBuf, 4) + 1;
sps->pcm.log2_min_pcm_cb_size = parseUe(pvBuf) + 3;
sps->pcm.log2_max_pcm_cb_size = sps->pcm.log2_min_pcm_cb_size +
if (ptSps->iPcmEnabledFlag) {
ptSps->pcm.u8BitDepth = getBits(pvBuf, 4) + 1;
ptSps->pcm.u8BitDepthChroma = getBits(pvBuf, 4) + 1;
ptSps->pcm.uiLog2MinPcmCbSize = parseUe(pvBuf) + 3;
ptSps->pcm.uiLog2MaxPcmCbSize = ptSps->pcm.uiLog2MinPcmCbSize +
parseUe(pvBuf);
if (FFMAX(sps->pcm.bit_depth, sps->pcm.bit_depth_chroma) > sps->bit_depth) {
if (FFMAX(ptSps->pcm.u8BitDepth, ptSps->pcm.u8BitDepthChroma) > ptSps->iBitDepth) {
RPT(RPT_ERR,
"PCM bit depth (%d, %d) is greater than normal bit depth (%d)\n",
sps->pcm.bit_depth, sps->pcm.bit_depth_chroma, sps->bit_depth);
ptSps->pcm.u8BitDepth, ptSps->pcm.u8BitDepthChroma, ptSps->iBitDepth);
iRet = -1;
goto exit;
}
sps->pcm.loop_filter_disable_flag = getOneBit(pvBuf);
ptSps->pcm.u8LoopFilterDisableFlag = getOneBit(pvBuf);
}
sps->nb_st_rps = parseUe(pvBuf);
if (sps->nb_st_rps > HEVC_MAX_SHORT_TERM_REF_PIC_SETS) {
ptSps->uiNbStRps = parseUe(pvBuf);
if (ptSps->uiNbStRps > HEVC_MAX_SHORT_TERM_REF_PIC_SETS) {
RPT(RPT_ERR, "Too many short term RPS: %d.\n",
sps->nb_st_rps);
ptSps->uiNbStRps);
iRet = -1;
goto exit;
}
printf("sps->nb_st_rps: %d\n",sps->nb_st_rps);
for (i = 0; i < sps->nb_st_rps; i++) {
if ((iRet = hevcDecodeShortTermRps(pvBuf, &sps->st_rps[i],
sps, 0)) < 0)
for (i = 0; i < ptSps->uiNbStRps; i++) {
if ((iRet = hevcDecodeShortTermRps(pvBuf, &ptSps->atStRps[i],
ptSps, 0)) < 0)
goto exit;
}
sps->long_term_ref_pics_present_flag = getOneBit(pvBuf);
if (sps->long_term_ref_pics_present_flag) {
sps->num_long_term_ref_pics_sps = parseUe(pvBuf);
if (sps->num_long_term_ref_pics_sps > HEVC_MAX_LONG_TERM_REF_PICS) {
ptSps->u8LongTermRefPicsPresentFlag = getOneBit(pvBuf);
if (ptSps->u8LongTermRefPicsPresentFlag) {
ptSps->u8NumLongTermRefPicsSps = parseUe(pvBuf);
if (ptSps->u8NumLongTermRefPicsSps > HEVC_MAX_LONG_TERM_REF_PICS) {
RPT(RPT_ERR, "Too many long term ref pics: %d.\n",
sps->num_long_term_ref_pics_sps);
ptSps->u8NumLongTermRefPicsSps);
iRet = -1;
goto exit;
}
for (i = 0; i < sps->num_long_term_ref_pics_sps; i++) {
sps->lt_ref_pic_poc_lsb_sps[i] = getBits(pvBuf, sps->log2_max_poc_lsb);
sps->used_by_curr_pic_lt_sps_flag[i] = getOneBit(pvBuf);
for (i = 0; i < ptSps->u8NumLongTermRefPicsSps; i++) {
ptSps->au16LtRefPicPocLsbSps[i] = getBits(pvBuf, ptSps->uiLog2MaxPocLsb);
ptSps->au8UsedByCurrPicLtSpsFlag[i] = getOneBit(pvBuf);
}
}
sps->sps_temporal_mvp_enabled_flag = getOneBit(pvBuf);
sps->sps_strong_intra_smoothing_enable_flag = getOneBit(pvBuf);
sps->vui.sar = (T_AVRational){0, 1};
vui_present = getOneBit(pvBuf);
if (vui_present==1)
decodeVui(pvBuf, sps);
ptSps->u8SpsTemporalMvpEnabledFlag = getOneBit(pvBuf);
ptSps->u8SpsStrongIntraMmoothingEnableFlag = getOneBit(pvBuf);
ptSps->tVui.tSar = (T_AVRational){0, 1};
ptSps->iVuiPresent = getOneBit(pvBuf);
if (ptSps->iVuiPresent)
decodeVui(pvBuf, ptSps);
#endif
#if 0
if (getOneBit(pvBuf)) { // sps_extension_flag
int sps_range_extension_flag = getOneBit(pvBuf);
int iSpsRangeExtensionFlag = getOneBit(pvBuf);
getBits(pvBuf, 7); //sps_extension_7bits = getBits(pvBuf, 7);
if (sps_range_extension_flag) {
int extended_precision_processing_flag;
int cabac_bypass_alignment_enabled_flag;
if (iSpsRangeExtensionFlag) {
int iExtendedPrecisionProcessingFlag;
int iCabacBypassAlignmentEnabledFlag;
sps->transform_skip_rotation_enabled_flag = getOneBit(pvBuf);
sps->transform_skip_context_enabled_flag = getOneBit(pvBuf);
sps->implicit_rdpcm_enabled_flag = getOneBit(pvBuf);
ptSps->iTransformSkipRotationEnabledFlag = getOneBit(pvBuf);
ptSps->iTransformSkipContextEnabledFlag = getOneBit(pvBuf);
ptSps->iImplicitRdpcmEnabledFlag = getOneBit(pvBuf);
sps->explicit_rdpcm_enabled_flag = getOneBit(pvBuf);
ptSps->iExplicitRdpcmEnabledFlag = getOneBit(pvBuf);
extended_precision_processing_flag = getOneBit(pvBuf);
if (extended_precision_processing_flag)
iExtendedPrecisionProcessingFlag = getOneBit(pvBuf);
if (iExtendedPrecisionProcessingFlag)
RPT(RPT_WRN,
"extended_precision_processing_flag not yet implemented\n");
"iExtendedPrecisionProcessingFlag not yet implemented\n");
sps->intra_smoothing_disabled_flag = getOneBit(pvBuf);
sps->high_precision_offsets_enabled_flag = getOneBit(pvBuf);
if (sps->high_precision_offsets_enabled_flag)
ptSps->iIntraSmoothingDisabledFlag = getOneBit(pvBuf);
ptSps->iHighPrecisionOffsetsEnabledFlag = getOneBit(pvBuf);
if (ptSps->iHighPrecisionOffsetsEnabledFlag)
RPT(RPT_WRN,
"high_precision_offsets_enabled_flag not yet implemented\n");
"iHighPrecisionOffsetsEnabledFlag not yet implemented\n");
sps->persistent_rice_adaptation_enabled_flag = getOneBit(pvBuf);
ptSps->iPersistentRiceAdaptationEnabledFlag = getOneBit(pvBuf);
cabac_bypass_alignment_enabled_flag = getOneBit(pvBuf);
if (cabac_bypass_alignment_enabled_flag)
iCabacBypassAlignmentEnabledFlag = getOneBit(pvBuf);
if (iCabacBypassAlignmentEnabledFlag)
RPT(RPT_WRN,
"cabac_bypass_alignment_enabled_flag not yet implemented\n");
"iCabacBypassAlignmentEnabledFlag not yet implemented\n");
}
}
if (apply_defdispwin) {
sps->output_window.left_offset += sps->vui.def_disp_win.left_offset;
sps->output_window.right_offset += sps->vui.def_disp_win.right_offset;
sps->output_window.top_offset += sps->vui.def_disp_win.top_offset;
sps->output_window.bottom_offset += sps->vui.def_disp_win.bottom_offset;
}
ow = &sps->output_window;
if (ow->left_offset >= INT_MAX - ow->right_offset ||
ow->top_offset >= INT_MAX - ow->bottom_offset ||
ow->left_offset + ow->right_offset >= sps->width ||
ow->top_offset + ow->bottom_offset >= sps->height) {
ow = &ptSps->tOutputWindow;
if (ow->uiLeftOffset >= INT_MAX - ow->uiRightOffset ||
ow->uiTopOffset >= INT_MAX - ow->uiBottomOffset ||
ow->uiLeftOffset + ow->uiRightOffset >= ptSps->iWidth ||
ow->uiTopOffset + ow->uiBottomOffset >= ptSps->iHeight) {
RPT(RPT_WRN, "Invalid cropping offsets: %u/%u/%u/%u\n",
ow->left_offset, ow->right_offset, ow->top_offset, ow->bottom_offset);
if (avctx->err_recognition & AV_EF_EXPLODE) {
return AVERROR_INVALIDDATA;
}
ow->uiLeftOffset, ow->uiRightOffset, ow->uiTopOffset, ow->uiBottomOffset);
RPT(RPT_WRN,
"Displaying the whole video surface.\n");
memset(ow, 0, sizeof(*ow));
memset(&sps->pic_conf_win, 0, sizeof(sps->pic_conf_win));
memset(&ptSps->tPicConfWin, 0, sizeof(ptSps->tPicConfWin));
}
// Inferred parameters
sps->log2_ctb_size = sps->log2_min_cb_size +
sps->log2_diff_max_min_coding_block_size;
sps->log2_min_pu_size = sps->log2_min_cb_size - 1;
ptSps->uiLog2CtbSize = ptSps->uiLog2MinCbSize +
ptSps->uiLog2DiffMaxMinCodingBlockSize;
ptSps->uiLog2MinPuSize = ptSps->uiLog2MinCbSize - 1;
if (sps->log2_ctb_size > HEVC_MAX_LOG2_CTB_SIZE) {
RPT(RPT_ERR, "CTB size out of range: 2^%d\n", sps->log2_ctb_size);
iRet = -1;
if (ptSps->uiLog2CtbSize > HEVC_MAX_LOG2_CTB_SIZE) {
RPT(RPT_ERR, "CTB size out of range: 2^%d\n", ptSps->uiLog2CtbSize);
iRet = -1;
goto exit;
}
if (sps->log2_ctb_size < 4) {
if (ptSps->uiLog2CtbSize < 4) {
RPT(RPT_ERR,
"log2_ctb_size %d differs from the bounds of any known profile\n",
sps->log2_ctb_size);
avpriv_request_sample(avctx, "log2_ctb_size %d", sps->log2_ctb_size);
iRet = -1;
"uiLog2CtbSize %d differs from the bounds of any known profile\n",
ptSps->uiLog2CtbSize);
iRet = -1;
goto exit;
}
sps->ctb_width = (sps->width + (1 << sps->log2_ctb_size) - 1) >> sps->log2_ctb_size;
sps->ctb_height = (sps->height + (1 << sps->log2_ctb_size) - 1) >> sps->log2_ctb_size;
sps->ctb_size = sps->ctb_width * sps->ctb_height;
ptSps->iCtbWidth = (ptSps->iWidth + (1 << ptSps->uiLog2CtbSize) - 1) >> ptSps->uiLog2CtbSize;
ptSps->iCtbHeight = (ptSps->iHeight + (1 << ptSps->uiLog2CtbSize) - 1) >> ptSps->uiLog2CtbSize;
ptSps->iCtbSize = ptSps->iCtbWidth * ptSps->iCtbHeight;
sps->min_cb_width = sps->width >> sps->log2_min_cb_size;
sps->min_cb_height = sps->height >> sps->log2_min_cb_size;
sps->min_tb_width = sps->width >> sps->log2_min_tb_size;
sps->min_tb_height = sps->height >> sps->log2_min_tb_size;
sps->min_pu_width = sps->width >> sps->log2_min_pu_size;
sps->min_pu_height = sps->height >> sps->log2_min_pu_size;
sps->tb_mask = (1 << (sps->log2_ctb_size - sps->log2_min_tb_size)) - 1;
ptSps->iMinCbWidth = ptSps->iWidth >> ptSps->uiLog2MinCbSize;
ptSps->iMinCbHeight = ptSps->iHeight >> ptSps->uiLog2MinCbSize;
ptSps->iMinTbWidth = ptSps->iWidth >> ptSps->uiLog2MinTbSize;
ptSps->iMinTbHeight = ptSps->iHeight >> ptSps->uiLog2MinTbSize;
ptSps->iMinPuWidth = ptSps->iWidth >> ptSps->uiLog2MinPuSize;
ptSps->iMinPuHeight = ptSps->iHeight >> ptSps->uiLog2MinPuSize;
ptSps->iTbMask = (1 << (ptSps->uiLog2CtbSize - ptSps->uiLog2MinTbSize)) - 1;
sps->qp_bd_offset = 6 * (sps->bit_depth - 8);
ptSps->iQpBdOffset = 6 * (ptSps->iBitDepth - 8);
if (av_mod_uintp2(sps->width, sps->log2_min_cb_size) ||
av_mod_uintp2(sps->height, sps->log2_min_cb_size)) {
if (avModUintp2c(ptSps->iWidth, ptSps->uiLog2MinCbSize) ||
avModUintp2c(ptSps->iHeight, ptSps->uiLog2MinCbSize)) {
RPT(RPT_ERR, "Invalid coded frame dimensions.\n");
iRet = -1;
goto exit;
}
if (sps->max_transform_hierarchy_depth_inter > sps->log2_ctb_size - sps->log2_min_tb_size) {
RPT(RPT_ERR, "max_transform_hierarchy_depth_inter out of range: %d\n",
sps->max_transform_hierarchy_depth_inter);
if (ptSps->iMaxTransformHierarchyDepthInter > ptSps->uiLog2CtbSize - ptSps->uiLog2MinTbSize) {
RPT(RPT_ERR, "iMaxTransformHierarchyDepthInter out of range: %d\n",
ptSps->iMaxTransformHierarchyDepthInter);
iRet = -1;
goto exit;
}
if (sps->max_transform_hierarchy_depth_intra > sps->log2_ctb_size - sps->log2_min_tb_size) {
RPT(RPT_ERR, "max_transform_hierarchy_depth_intra out of range: %d\n",
sps->max_transform_hierarchy_depth_intra);
if (ptSps->iMaxTransformHierarchyDepthIntra > ptSps->uiLog2CtbSize - ptSps->uiLog2MinTbSize) {
RPT(RPT_ERR, "iMaxTransformHierarchyDepthIntra out of range: %d\n",
ptSps->iMaxTransformHierarchyDepthIntra);
iRet = -1;
goto exit;
}
if (sps->log2_max_trafo_size > FFMIN(sps->log2_ctb_size, 5)) {
if (ptSps->uiLog2MaxTrafoSize > FFMIN(ptSps->uiLog2CtbSize, 5)) {
RPT(RPT_ERR,
"max transform block size out of range: %d\n",
sps->log2_max_trafo_size);
ptSps->uiLog2MaxTrafoSize);
iRet = -1;
goto exit;
}
......@@ -2078,7 +2018,6 @@ int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *sps )
iRet = -1;
goto exit;
}
#endif
exit:
......@@ -2089,6 +2028,141 @@ exit:
}
int h265DecVideoParameterSet( void *pvBufSrc, T_HEVCVPS *ptVps )
{
int iRet = 0;
int i,j;
int uiVpsId = 0;
void *pvBuf = NULL;
if(NULL == pvBufSrc || NULL == ptVps)
{
RPT(RPT_ERR,"ERR null pointer\n");
iRet = -1;
goto exit;
}
memset((void *)ptVps, 0, sizeof(T_HEVCVPS));
pvBuf = deEmulationPrevention(pvBufSrc);
if(NULL == pvBuf)
{
RPT(RPT_ERR,"ERR null pointer\n");
iRet = -1;
goto exit;
}
RPT(RPT_DBG, "Decoding VPS\n");
uiVpsId = getBits(pvBuf, 4);
if (uiVpsId >= HEVC_MAX_VPS_COUNT) {
RPT(RPT_ERR, "VPS id out of range: %d\n", uiVpsId);
iRet = -1;
goto exit;
}
if (getBits(pvBuf, 2) != 3) { // vps_reserved_three_2bits
RPT(RPT_ERR, "vps_reserved_three_2bits is not three\n");
iRet = -1;
goto exit;
}
ptVps->iVpsMaxLayers = getBits(pvBuf, 6) + 1;
ptVps->iVpsMaxSubLayers = getBits(pvBuf, 3) + 1;
ptVps->u8VpsTemporalIdNestingFlag = getOneBit(pvBuf);
if (getBits(pvBuf, 16) != 0xffff) { // vps_reserved_ffff_16bits
RPT(RPT_ERR, "vps_reserved_ffff_16bits is not 0xffff\n");
iRet = -1;
goto exit;
}
if (ptVps->iVpsMaxSubLayers > HEVC_MAX_SUB_LAYERS) {
RPT(RPT_ERR, "iVpsMaxSubLayers out of range: %d\n",
ptVps->iVpsMaxSubLayers);
iRet = -1;
goto exit;
}
if (parsePtl(pvBuf, &ptVps->tPtl, ptVps->iVpsMaxSubLayers) < 0){
iRet = -1;
goto exit;
}
ptVps->iVpsSubLayerOrderingInfoPresentFlag = getOneBit(pvBuf);
i = ptVps->iVpsSubLayerOrderingInfoPresentFlag ? 0 : ptVps->iVpsMaxSubLayers - 1;
for (; i < ptVps->iVpsMaxSubLayers; i++) {
ptVps->uiVpsMaxDecPicBuffering[i] = parseUe(pvBuf) + 1;
ptVps->auiVpsNumReorderPics[i] = parseUe(pvBuf);
ptVps->auiVpsMaxLatencyIncrease[i] = parseUe(pvBuf) - 1;
if (ptVps->uiVpsMaxDecPicBuffering[i] > HEVC_MAX_DPB_SIZE || !ptVps->uiVpsMaxDecPicBuffering[i]) {
RPT(RPT_ERR, "vps_max_dec_pic_buffering_minus1 out of range: %d\n",
ptVps->uiVpsMaxDecPicBuffering[i] - 1);
iRet = -1;
goto exit;
}
if (ptVps->auiVpsNumReorderPics[i] > ptVps->uiVpsMaxDecPicBuffering[i] - 1) {
RPT(RPT_WRN, "vps_max_num_reorder_pics out of range: %d\n",
ptVps->auiVpsNumReorderPics[i]);
}
}
ptVps->iVpsMaxLayerId = getBits(pvBuf, 6);
ptVps->iVpsNumLayerSets = parseUe(pvBuf) + 1;
if (ptVps->iVpsNumLayerSets < 1 || ptVps->iVpsNumLayerSets > 1024 ||
(ptVps->iVpsNumLayerSets - 1LL) * (ptVps->iVpsMaxLayerId + 1LL) > getBitsLeft(pvBuf)) {
RPT(RPT_ERR, "too many layer_id_included_flags\n");
iRet = -1;
goto exit;
}
for (i = 1; i < ptVps->iVpsNumLayerSets; i++)
for (j = 0; j <= ptVps->iVpsMaxLayerId; j++)
getBits(pvBuf, 1); // layer_id_included_flag[i][j]
ptVps->u8VpsTimingInfoPresentFlag = getOneBit(pvBuf);
if (ptVps->u8VpsTimingInfoPresentFlag) {
ptVps->u32VpsNumUnitsInTick = getBits(pvBuf, 32);
ptVps->u32VpsTimeScale = getBits(pvBuf, 32);
ptVps->u8VpsPocProportionalToTimingFlag = getOneBit(pvBuf);
if (ptVps->u8VpsPocProportionalToTimingFlag)
ptVps->iVpsNumTicksPocDiffOne = parseUe(pvBuf) + 1;
ptVps->iVpsNumHrdParameters = parseUe(pvBuf);
if (ptVps->iVpsNumHrdParameters > (unsigned)ptVps->iVpsNumLayerSets) {
RPT(RPT_ERR,
"iVpsNumHrdParameters %d is invalid\n", ptVps->iVpsNumHrdParameters);
iRet = -1;
goto exit;
}
for (i = 0; i < ptVps->iVpsNumHrdParameters; i++) {
int common_inf_present = 1;
parseUe(pvBuf); // hrd_layer_set_idx
if (i)
common_inf_present = getOneBit(pvBuf);
decodeHrd(pvBuf, common_inf_present, ptVps->iVpsMaxSubLayers);
}
}
getOneBit(pvBuf); /* vps_extension_flag */
if (getBitsLeft(pvBuf) < 0) {
RPT(RPT_ERR,
"Overread VPS by %d bits\n", -getBitsLeft(pvBuf));
iRet = -1;
goto exit;
}
exit:
getBitContextFree(pvBuf);
return iRet;
}
void h264GetWidthHeight(T_SPS *ptSps, int *piWidth, int *piHeight)
{
// ¿í¸ß¼ÆË㹫ʽ
......@@ -2191,28 +2265,39 @@ void h264GeFramerate(T_SPS *ptSps, float *pfFramerate)
void h265GetWidthHeight(T_HEVCSPS *ptSps, int *piWidth, int *piHeight)
{
#if 1
// ¿í¸ß¼ÆË㹫ʽ
int iCodeWidth = 0;
int iCodedHeight = 0;
iCodeWidth = ptSps->width;
iCodedHeight = ptSps->height;
*piWidth = ptSps->width - ptSps->pic_conf_win.left_offset - ptSps->pic_conf_win.right_offset;
*piHeight = ptSps->height - ptSps->pic_conf_win.top_offset - ptSps->pic_conf_win.bottom_offset;
iCodeWidth = ptSps->iWidth;
iCodedHeight = ptSps->iHeight;
*piWidth = ptSps->iWidth - ptSps->tOutputWindow.uiLeftOffset - ptSps->tOutputWindow.uiRightOffset;
*piHeight = ptSps->iHeight - ptSps->tOutputWindow.uiTopOffset - ptSps->tOutputWindow.uiBottomOffset;
RPT(RPT_DBG, "iCodeWidth:%d, iCodedHeight:%d\n", iCodeWidth, iCodedHeight);
RPT(RPT_DBG, "*piWidth:%d, *piHeight:%d\n", *piWidth, *piHeight);
// RPT(RPT_DBG, "ptSps->uiCropRight:%d, ptSps->uiCropLeft:%d\n", ptSps->uiCropRight, ptSps->uiCropLeft);
RPT(RPT_DBG, "ptSps->tOutputWindow.uiRightOffset:%d, ptSps->tOutputWindow.uiLeftOffset:%d\n", ptSps->tOutputWindow.uiRightOffset, ptSps->tOutputWindow.uiLeftOffset);
// RPT(RPT_DBG, "ptSps->uiCropTop:%d, ptSps->uiCropBottom:%d\n", ptSps->uiCropTop, ptSps->uiCropBottom);
RPT(RPT_DBG, "ptSps->tOutputWindow.uiTopOffset:%d, ptSps->tOutputWindow.uiBottomOffset:%d\n", ptSps->tOutputWindow.uiTopOffset, ptSps->tOutputWindow.uiBottomOffset);
#endif
}
void h265GeFramerate(T_HEVCSPS *ptSps, float *pfFramerate)
void h265GeFramerate(T_HEVCVPS *ptVps, T_HEVCSPS *ptSps,float *pfFramerate)
{
if (ptVps && ptVps->u8VpsTimingInfoPresentFlag) {
*pfFramerate = (float)(ptVps->u32VpsTimeScale) / (float)(ptVps->u32VpsNumUnitsInTick);
} else if (ptSps && ptSps->tVui.iVuiTimingInfoPresentFlag && ptSps->iVuiPresent) {
*pfFramerate = (float)(ptSps->tVui.u32VuiTimeScale) / (float)(ptSps->tVui.u32VuiNumUnitsInTick);
}
else{
//vps sps可能不包含帧率
*pfFramerate = 0.0F;
RPT(RPT_WRN, "frame rate:0");
}
}
......@@ -237,184 +237,204 @@ typedef struct T_PPS {
typedef struct T_HEVCWindow {
unsigned int left_offset;
unsigned int right_offset;
unsigned int top_offset;
unsigned int bottom_offset;
unsigned int uiLeftOffset;
unsigned int uiRightOffset;
unsigned int uiTopOffset;
unsigned int uiBottomOffset;
} T_HEVCWindow;
typedef struct T_VUI {
T_AVRational sar;
int overscan_info_present_flag;
int overscan_appropriate_flag;
int video_signal_type_present_flag;
int video_format;
int video_full_range_flag;
int colour_description_present_flag;
uint8_t colour_primaries;
uint8_t transfer_characteristic;
uint8_t matrix_coeffs;
int chroma_loc_info_present_flag;
int chroma_sample_loc_type_top_field;
int chroma_sample_loc_type_bottom_field;
int neutra_chroma_indication_flag;
int field_seq_flag;
int frame_field_info_present_flag;
int default_display_window_flag;
T_HEVCWindow def_disp_win;
int vui_timing_info_present_flag;
uint32_t vui_num_units_in_tick;
uint32_t vui_time_scale;
int vui_poc_proportional_to_timing_flag;
int vui_num_ticks_poc_diff_one_minus1;
int vui_hrd_parameters_present_flag;
int bitstream_restriction_flag;
int tiles_fixed_structure_flag;
int motion_vectors_over_pic_boundaries_flag;
int restricted_ref_pic_lists_flag;
int min_spatial_segmentation_idc;
int max_bytes_per_pic_denom;
int max_bits_per_min_cu_denom;
int log2_max_mv_length_horizontal;
int log2_max_mv_length_vertical;
T_AVRational tSar;
int iOverscanInfoPresentFlag;
int iOverscanAppropriateFlag;
int iVideoSignalTypePresentFlag;
int iVideoFormat;
int iVideoFullRangeFlag;
int iColourDescriptionPresentFlag;
uint8_t u8ColourPrimaries;
uint8_t u8TransferCharacteristic;
uint8_t u8MatrixCoeffs;
int iChromaLocInfoPresentFlag;
int iChromaSampleLocTypeTopField;
int iChromaSampleLocTypeBottomField;
int iNeutraChromaIndicationFlag;
int iFieldSeqFlag;
int iFrameFieldInfoPresentFlag;
int iDefaultDisplayWindowFlag;
T_HEVCWindow tDefDispWin;
int iVuiTimingInfoPresentFlag;
uint32_t u32VuiNumUnitsInTick;
uint32_t u32VuiTimeScale;
int iVuiPocProportionalToTimingFlag;
int iVuiNumTicksPocDiffOneMinus1;
int iVuiHrdParametersPresentFlag;
int iBitstreamRestrictionFlag;
int iTilesFixedStructureFlag;
int iMotionVectorsOverPicBoundariesFlag;
int iRestrictedRefPicListsFlag;
int iMinSpatialSegmentationIdc;
int iMaxBytesPerPicDenom;
int iMaxBitsPerMinCuDenom;
int iLog2MaxMvLengthHorizontal;
int iLog2MaxMvLengthVertical;
} T_VUI;
typedef struct T_PTLCommon {
uint8_t profile_space;
uint8_t tier_flag;
uint8_t profile_idc;
uint8_t profile_compatibility_flag[32];
uint8_t level_idc;
uint8_t progressive_source_flag;
uint8_t interlaced_source_flag;
uint8_t non_packed_constraint_flag;
uint8_t frame_only_constraint_flag;
uint8_t u8ProfileSpace;
uint8_t u8TierFlag;
uint8_t u8ProfileIdc;
uint8_t au8ProfileCompatibilityFlag[32];
uint8_t u8LevelIdc;
uint8_t u8ProgressiveSourceFlag;
uint8_t u8InterlacedSourceFlag;
uint8_t u8NonPackedConstraintFlag;
uint8_t u8FrameOnlyConstraintFlag;
} T_PTLCommon;
typedef struct T_PTL {
T_PTLCommon general_ptl;
T_PTLCommon sub_layer_ptl[HEVC_MAX_SUB_LAYERS];
T_PTLCommon tGeneralPtl;
T_PTLCommon atSubLayerPtl[HEVC_MAX_SUB_LAYERS];
uint8_t sub_layer_profile_present_flag[HEVC_MAX_SUB_LAYERS];
uint8_t sub_layer_level_present_flag[HEVC_MAX_SUB_LAYERS];
uint8_t au8SubLayerProfilePresentFlag[HEVC_MAX_SUB_LAYERS];
uint8_t au8SubLayerLevelPresentFlag[HEVC_MAX_SUB_LAYERS];
} T_PTL;
typedef struct T_ScalingList {
/* This is a little wasteful, since sizeID 0 only needs 8 coeffs,
* and size ID 3 only has 2 arrays, not 6. */
uint8_t sl[4][6][64];
uint8_t sl_dc[2][6];
uint8_t aaau8Sl[4][6][64];
uint8_t aau8SlDc[2][6];
} T_ScalingList;
typedef struct T_ShortTermRPS {
unsigned int num_negative_pics;
int num_delta_pocs;
int rps_idx_num_delta_pocs;
int32_t delta_poc[32];
uint8_t used[32];
unsigned int uiNumNegativePics;
int iNumDeltaPocs;
int iRpsIdxNumDeltaPocs;
int32_t au32DeltaPoc[32];
uint8_t au8Used[32];
} T_ShortTermRPS;
typedef struct T_HEVCVPS {
uint8_t u8VpsTemporalIdNestingFlag;
int iVpsMaxLayers;
int iVpsMaxSubLayers; ///< vps_max_temporal_layers_minus1 + 1
T_PTL tPtl;
int iVpsSubLayerOrderingInfoPresentFlag;
unsigned int uiVpsMaxDecPicBuffering[HEVC_MAX_SUB_LAYERS];
unsigned int auiVpsNumReorderPics[HEVC_MAX_SUB_LAYERS];
unsigned int auiVpsMaxLatencyIncrease[HEVC_MAX_SUB_LAYERS];
int iVpsMaxLayerId;
int iVpsNumLayerSets; ///< vps_num_layer_sets_minus1 + 1
uint8_t u8VpsTimingInfoPresentFlag;
uint32_t u32VpsNumUnitsInTick;
uint32_t u32VpsTimeScale;
uint8_t u8VpsPocProportionalToTimingFlag;
int iVpsNumTicksPocDiffOne; ///< vps_num_ticks_poc_diff_one_minus1 + 1
int iVpsNumHrdParameters;
} T_HEVCVPS;
typedef struct T_HEVCSPS {
unsigned vps_id;
int chroma_format_idc;
uint8_t separate_colour_plane_flag;
unsigned int uiVpsId;
int iChromaFormatIdc;
uint8_t u8SeparateColourPlaneFlag;
///< output (i.e. cropped) values
int output_width, output_height;
T_HEVCWindow output_window;
int iIutputWidth, iOutputHeight;
T_HEVCWindow tOutputWindow;
T_HEVCWindow pic_conf_win;
T_HEVCWindow tPicConfWin;
int bit_depth;
int bit_depth_chroma;
int pixel_shift;
// enum AVPixelFormat pix_fmt;
int iBitDepth;
int iBitDepthChroma;
int iPixelShift;
unsigned int log2_max_poc_lsb;
int pcm_enabled_flag;
unsigned int uiLog2MaxPocLsb;
int iPcmEnabledFlag;
int max_sub_layers;
int iMaxSubLayers;
struct {
int max_dec_pic_buffering;
int num_reorder_pics;
int max_latency_increase;
} temporal_layer[HEVC_MAX_SUB_LAYERS];
uint8_t temporal_id_nesting_flag;
int iMaxDecPicBuffering;
int iNumReorderPics;
int iMaxLatencyIncrease;
} stTemporalLayer[HEVC_MAX_SUB_LAYERS];
uint8_t u8temporalIdNestingFlag;
T_VUI vui;
T_PTL ptl;
T_VUI tVui;
T_PTL tPtl;
uint8_t scaling_list_enable_flag;
T_ScalingList scaling_list;
uint8_t u8ScalingListEnableFlag;
T_ScalingList tScalingList;
unsigned int nb_st_rps;
T_ShortTermRPS st_rps[HEVC_MAX_SHORT_TERM_RPS_COUNT];
unsigned int uiNbStRps;
T_ShortTermRPS atStRps[HEVC_MAX_SHORT_TERM_RPS_COUNT];
uint8_t amp_enabled_flag;
uint8_t sao_enabled;
uint8_t u8AmpEnabledFlag;
uint8_t u8SaoEnabled;
uint8_t long_term_ref_pics_present_flag;
uint16_t lt_ref_pic_poc_lsb_sps[32];
uint8_t used_by_curr_pic_lt_sps_flag[32];
uint8_t num_long_term_ref_pics_sps;
uint8_t u8LongTermRefPicsPresentFlag;
uint16_t au16LtRefPicPocLsbSps[32];
uint8_t au8UsedByCurrPicLtSpsFlag[32];
uint8_t u8NumLongTermRefPicsSps;
struct {
uint8_t bit_depth;
uint8_t bit_depth_chroma;
unsigned int log2_min_pcm_cb_size;
unsigned int log2_max_pcm_cb_size;
uint8_t loop_filter_disable_flag;
uint8_t u8BitDepth;
uint8_t u8BitDepthChroma;
unsigned int uiLog2MinPcmCbSize;
unsigned int uiLog2MaxPcmCbSize;
uint8_t u8LoopFilterDisableFlag;
} pcm;
uint8_t sps_temporal_mvp_enabled_flag;
uint8_t sps_strong_intra_smoothing_enable_flag;
unsigned int log2_min_cb_size;
unsigned int log2_diff_max_min_coding_block_size;
unsigned int log2_min_tb_size;
unsigned int log2_max_trafo_size;
unsigned int log2_ctb_size;
unsigned int log2_min_pu_size;
int max_transform_hierarchy_depth_inter;
int max_transform_hierarchy_depth_intra;
int transform_skip_rotation_enabled_flag;
int transform_skip_context_enabled_flag;
int implicit_rdpcm_enabled_flag;
int explicit_rdpcm_enabled_flag;
int intra_smoothing_disabled_flag;
int persistent_rice_adaptation_enabled_flag;
uint8_t u8SpsTemporalMvpEnabledFlag;
uint8_t u8SpsStrongIntraMmoothingEnableFlag;
unsigned int uiLog2MinCbSize;
unsigned int uiLog2DiffMaxMinCodingBlockSize;
unsigned int uiLog2MinTbSize;
unsigned int uiLog2MaxTrafoSize;
unsigned int uiLog2CtbSize;
unsigned int uiLog2MinPuSize;
int iMaxTransformHierarchyDepthInter;
int iMaxTransformHierarchyDepthIntra;
int iTransformSkipRotationEnabledFlag;
int iTransformSkipContextEnabledFlag;
int iImplicitRdpcmEnabledFlag;
int iExplicitRdpcmEnabledFlag;
int iIntraSmoothingDisabledFlag;
int iHighPrecisionOffsetsEnabledFlag;
int iPersistentRiceAdaptationEnabledFlag;
///< coded frame dimension in various units
int width;
int height;
int ctb_width;
int ctb_height;
int ctb_size;
int min_cb_width;
int min_cb_height;
int min_tb_width;
int min_tb_height;
int min_pu_width;
int min_pu_height;
int tb_mask;
int hshift[3];
int vshift[3];
int qp_bd_offset;
uint8_t data[4096];
int data_size;
int iWidth;
int iHeight;
int iCtbWidth;
int iCtbHeight;
int iCtbSize;
int iMinCbWidth;
int iMinCbHeight;
int iMinTbWidth;
int iMinTbHeight;
int iMinPuWidth;
int iMinPuHeight;
int iTbMask;
int aiHshift[3];
int aiVshift[3];
int iQpBdOffset;
int iVuiPresent;
}T_HEVCSPS;
......@@ -428,13 +448,15 @@ typedef struct T_GetBitContext{
int h264DecSeqParameterSet(void *pvBuf, T_SPS *ptSps);
int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *p_sps );
int h265DecSeqParameterSet( void *pvBufSrc, T_HEVCSPS *ptSps );
int h265DecVideoParameterSet( void *pvBufSrc, T_HEVCVPS *ptVps );
void h264GetWidthHeight(T_SPS *ptSps, int *piWidth, int *piHeight);
void h265GetWidthHeight(T_HEVCSPS *ptSps, int *piWidth, int *piHeight);
void h264GeFramerate(T_SPS *ptSps, float *pfFramerate);
void h265GeFramerate(T_HEVCSPS *ptSps, float *pfFramerate);
void h265GeFramerate(T_HEVCVPS *ptVps, T_HEVCSPS *ptSps,float *pfFramerate);
#if defined (__cplusplus)
}
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论