diff --git a/CMakeLists.txt b/CMakeLists.txt index e9cf95032c5f874c3923dd3f41fecc90525a6a49..cb85f8dc6e8ad22b6a31ccfbb81f0a4c0e1f6271 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -68,7 +68,6 @@ if( XCODE ) bb_enable_warnings( clang warnings-as-errors -Wno-deprecated-declarations -Wno-unknown-attributes - -Wno-deprecated-register -Wno-pessimizing-move -Wno-absolute-value -Wno-unused-const-variable @@ -76,7 +75,6 @@ if( XCODE ) else() bb_enable_warnings( clang warnings-as-errors -Wno-unknown-attributes - -Wno-deprecated-register -Wno-pessimizing-move -Wno-absolute-value -Wno-unused-const-variable ) diff --git a/source/Lib/CommonLib/Rom.cpp b/source/Lib/CommonLib/Rom.cpp index b93240340aa95da1f3a60f7c08856aa4142cf33b..01ee8947a5d8fbdd0b32ef648afc83b7de0dd804 100644 --- a/source/Lib/CommonLib/Rom.cpp +++ b/source/Lib/CommonLib/Rom.cpp @@ -713,4 +713,3 @@ int8_t g_dis[GEO_NUM_ANGLES] = { 8, 8, 8, 8, 4, 4, 2, 1, 0, -1, -2, -4, int8_t g_angle2mirror[GEO_NUM_ANGLES] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 2, 2, 2, 2 }; //! \} - diff --git a/source/Lib/CommonLib/Slice.cpp b/source/Lib/CommonLib/Slice.cpp index b4b49b1f427920d6eeccea12db6bf3aad537f499..b15cf3b3bf5a18c277cb552464153d8c4b7ef951 100644 --- a/source/Lib/CommonLib/Slice.cpp +++ b/source/Lib/CommonLib/Slice.cpp @@ -55,8 +55,7 @@ Slice::Slice() , m_prevGDRSubpicPOC(-MAX_INT) , m_prevIRAPSubpicPOC(-MAX_INT) , m_prevIRAPSubpicType(NAL_UNIT_INVALID) - , m_rpl0Idx(-1) - , m_rpl1Idx(-1) + , m_rplIdx{ -1, -1 } , m_eNalUnitType(NAL_UNIT_CODED_SLICE_IDR_W_RADL) , m_pictureHeaderInSliceHeader(false) , m_eSliceType(I_SLICE) @@ -216,18 +215,11 @@ void Slice::inheritFromPicHeader( PicHeader *picHeader, const PPS *pps, const SP { if (pps->getRplInfoInPhFlag()) { - setRPL0idx( picHeader->getRPL0idx() ); - m_RPL0 = *picHeader->getRPL0(); - if(getRPL0idx() != -1) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - m_RPL0 = *sps->getRPLList0()->getReferencePictureList(getRPL0idx()); - } - - setRPL1idx( picHeader->getRPL1idx() ); - m_RPL1 = *picHeader->getRPL1(); - if(getRPL1idx() != -1) - { - m_RPL1 = *sps->getRPLList1()->getReferencePictureList(getRPL1idx()); + const int rplIdx = picHeader->getRplIdx(l); + setRplIdx(l, rplIdx); + m_rpl[l] = rplIdx == -1 ? *picHeader->getRpl(l) : *sps->getRplList(l)->getReferencePictureList(rplIdx); } } @@ -423,11 +415,10 @@ void Slice::setRefPOCList () void Slice::setList1IdxToList0Idx() { - int idxL0, idxL1; - for ( idxL1 = 0; idxL1 < getNumRefIdx( REF_PIC_LIST_1 ); idxL1++ ) + for (int idxL1 = 0; idxL1 < getNumRefIdx(REF_PIC_LIST_1); idxL1++) { m_list1IdxToList0Idx[idxL1] = -1; - for ( idxL0 = 0; idxL0 < getNumRefIdx( REF_PIC_LIST_0 ); idxL0++ ) + for (int idxL0 = 0; idxL0 < getNumRefIdx(REF_PIC_LIST_0); idxL0++) { if ( m_apcRefPicList[REF_PIC_LIST_0][idxL0]->getPOC() == m_apcRefPicList[REF_PIC_LIST_1][idxL1]->getPOC() ) { @@ -448,84 +439,54 @@ void Slice::constructRefPicList(PicList& rcListPic) return; } - Picture *pcRefPic = nullptr; - - uint32_t numOfActiveRef = 0; - //construct L0 - numOfActiveRef = getNumRefIdx(REF_PIC_LIST_0); - int layerIdx = m_pcPic->cs->vps == nullptr ? 0 : m_pcPic->cs->vps->getGeneralLayerIdx( m_pcPic->layerId ); - - for (int ii = 0; ii < m_RPL0.getNumRefEntries(); ii++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if( m_RPL0.isInterLayerRefPic( ii ) ) - { - CHECK( m_RPL0.getInterLayerRefPicIdx( ii ) == NOT_VALID, "Wrong ILRP index" ); + const uint32_t numOfActiveRef = getNumRefIdx(l); - int refLayerId = m_pcPic->cs->vps->getLayerId( m_pcPic->cs->vps->getDirectRefLayerIdx( layerIdx, m_RPL0.getInterLayerRefPicIdx( ii ) ) ); - - pcRefPic = xGetRefPic( rcListPic, getPOC(), refLayerId ); - pcRefPic->longTerm = true; - } - else if (!m_RPL0.isRefPicLongterm(ii)) + for (int ii = 0; ii < m_rpl[l].getNumRefEntries(); ii++) { - pcRefPic = xGetRefPic(rcListPic, getPOC() + m_RPL0.getRefPicIdentifier(ii), m_pcPic->layerId); - pcRefPic->longTerm = false; - } - else - { - int pocBits = getSPS()->getBitsForPOC(); - int pocMask = (1 << pocBits) - 1; - int ltrpPoc = m_RPL0.getRefPicIdentifier(ii) & pocMask; - if(m_RPL0.getDeltaPocMSBPresentFlag(ii)) + Picture *refPic = nullptr; + + if (m_rpl[l].isInterLayerRefPic(ii)) { - ltrpPoc += getPOC() - m_RPL0.getDeltaPocMSBCycleLT(ii) * (pocMask + 1) - (getPOC() & pocMask); - } - pcRefPic = xGetLongTermRefPicCandidate( rcListPic, ltrpPoc, m_RPL0.getDeltaPocMSBPresentFlag( ii ), m_pcPic->layerId ); - pcRefPic->longTerm = true; - } - if(ii < numOfActiveRef) - { - pcRefPic->extendPicBorder( getPPS() ); - m_apcRefPicList[REF_PIC_LIST_0][ii] = pcRefPic; - m_bIsUsedAsLongTerm[REF_PIC_LIST_0][ii] = pcRefPic->longTerm; - } - } + const VPS *vps = m_pcPic->cs->vps; - //construct L1 - numOfActiveRef = getNumRefIdx(REF_PIC_LIST_1); - for (int ii = 0; ii < m_RPL1.getNumRefEntries(); ii++) - { - if( m_RPL1.isInterLayerRefPic( ii ) ) - { - CHECK( m_RPL1.getInterLayerRefPicIdx( ii ) == NOT_VALID, "Wrong ILRP index" ); + const int interLayerIdx = m_rpl[l].getInterLayerRefPicIdx(ii); + CHECK(interLayerIdx == NOT_VALID, "Wrong ILRP index"); - int refLayerId = m_pcPic->cs->vps->getLayerId( m_pcPic->cs->vps->getDirectRefLayerIdx( layerIdx, m_RPL1.getInterLayerRefPicIdx( ii ) ) ); + const int layerIdx = vps->getGeneralLayerIdx(m_pcPic->layerId); + const int refLayerId = vps->getLayerId(vps->getDirectRefLayerIdx(layerIdx, interLayerIdx)); - pcRefPic = xGetRefPic( rcListPic, getPOC(), refLayerId ); - pcRefPic->longTerm = true; - } - else if (!m_RPL1.isRefPicLongterm(ii)) - { - pcRefPic = xGetRefPic(rcListPic, getPOC() + m_RPL1.getRefPicIdentifier(ii), m_pcPic->layerId); - pcRefPic->longTerm = false; - } - else - { - int pocBits = getSPS()->getBitsForPOC(); - int pocMask = (1 << pocBits) - 1; - int ltrpPoc = m_RPL1.getRefPicIdentifier(ii) & pocMask; - if(m_RPL1.getDeltaPocMSBPresentFlag(ii)) + refPic = xGetRefPic(rcListPic, getPOC(), refLayerId); + + refPic->longTerm = true; + } + else if (!m_rpl[l].isRefPicLongterm(ii)) { - ltrpPoc += getPOC() - m_RPL1.getDeltaPocMSBCycleLT(ii) * (pocMask + 1) - (getPOC() & pocMask); + refPic = xGetRefPic(rcListPic, getPOC() + m_rpl[l].getRefPicIdentifier(ii), m_pcPic->layerId); + + refPic->longTerm = false; + } + else + { + const int pocBits = getSPS()->getBitsForPOC(); + const int pocMask = (1 << pocBits) - 1; + int ltrpPoc = m_rpl[l].getRefPicIdentifier(ii) & pocMask; + const bool pocHasMsb = m_rpl[l].getDeltaPocMSBPresentFlag(ii); + if (pocHasMsb) + { + ltrpPoc += (getPOC() & ~pocMask) - m_rpl[l].getDeltaPocMSBCycleLT(ii) * (pocMask + 1); + } + refPic = xGetLongTermRefPicCandidate(rcListPic, ltrpPoc, pocHasMsb, m_pcPic->layerId); + + refPic->longTerm = true; + } + if (ii < numOfActiveRef) + { + refPic->extendPicBorder(getPPS()); + m_apcRefPicList[l][ii] = refPic; + m_bIsUsedAsLongTerm[l][ii] = refPic->longTerm; } - pcRefPic = xGetLongTermRefPicCandidate( rcListPic, ltrpPoc, m_RPL1.getDeltaPocMSBPresentFlag( ii ), m_pcPic->layerId ); - pcRefPic->longTerm = true; - } - if(ii < numOfActiveRef) - { - pcRefPic->extendPicBorder( getPPS() ); - m_apcRefPicList[REF_PIC_LIST_1][ii] = pcRefPic; - m_bIsUsedAsLongTerm[REF_PIC_LIST_1][ii] = pcRefPic->longTerm; } } } @@ -577,7 +538,7 @@ void Slice::checkCRA(const ReferencePictureList* pRPL0, const ReferencePictureLi THROW("Invalid state"); } - uint32_t numRefPic = pRPL0->getNumberOfShorttermPictures() + pRPL0->getNumberOfLongtermPictures() + pRPL0->getNumberOfInterLayerPictures(); + uint32_t numRefPic = pRPL0->getNumRefEntries(); for (int i = 0; i < numRefPic; i++) { if (!pRPL0->isRefPicLongterm(i)) @@ -615,7 +576,7 @@ void Slice::checkCRA(const ReferencePictureList* pRPL0, const ReferencePictureLi } } } - numRefPic = pRPL1->getNumberOfShorttermPictures() + pRPL1->getNumberOfLongtermPictures() + pRPL1->getNumberOfInterLayerPictures(); + numRefPic = pRPL1->getNumRefEntries(); for (int i = 0; i < numRefPic; i++) { if (!pRPL1->isRefPicLongterm(i)) @@ -667,9 +628,11 @@ void Slice::checkRPL(const ReferencePictureList* pRPL0, const ReferencePictureLi int irapPOC = getAssociatedIRAPPOC(); - int numEntries[] = { pRPL0->getNumberOfShorttermPictures() + pRPL0->getNumberOfLongtermPictures() + pRPL0->getNumberOfInterLayerPictures(), pRPL1->getNumberOfShorttermPictures() + pRPL1->getNumberOfLongtermPictures() + pRPL1->getNumberOfInterLayerPictures() }; - const int numActiveEntries[] = { getNumRefIdx( REF_PIC_LIST_0 ), getNumRefIdx( REF_PIC_LIST_1 ) }; - const ReferencePictureList* rpl[] = { pRPL0, pRPL1 }; + const int numEntries[NUM_REF_PIC_LIST_01] = { pRPL0->getNumRefEntries(), pRPL1->getNumRefEntries() }; + const int numActiveEntries[NUM_REF_PIC_LIST_01] = { getNumRefIdx(REF_PIC_LIST_0), getNumRefIdx(REF_PIC_LIST_1) }; + + const ReferencePictureList *rpl[NUM_REF_PIC_LIST_01] = { pRPL0, pRPL1 }; + const bool fieldSeqFlag = getSPS()->getFieldSeqFlag(); const int layerIdx = m_pcPic->cs->vps == nullptr ? 0 : m_pcPic->cs->vps->getGeneralLayerIdx( m_pcPic->layerId ); @@ -1001,11 +964,8 @@ void Slice::copySliceInfo(Slice *pSrc, bool cpyAlmostAll) // access channel if (cpyAlmostAll) { - m_RPL0 = pSrc->m_RPL0; - } - if (cpyAlmostAll) - { - m_RPL1 = pSrc->m_RPL1; + m_rpl[REF_PIC_LIST_0] = pSrc->m_rpl[REF_PIC_LIST_0]; + m_rpl[REF_PIC_LIST_1] = pSrc->m_rpl[REF_PIC_LIST_1]; } m_iLastIDR = pSrc->m_iLastIDR; @@ -1402,162 +1362,103 @@ void Slice::checkSubpicTypeConstraints(PicList& rcListPic, const ReferencePictur } } - //subpic RPL related constraints - Picture* pcRefPic; - int refPicPOC; - int refPicDecodingOrderNumber; - - int numEntriesL0 = pRPL0->getNumberOfShorttermPictures() + pRPL0->getNumberOfLongtermPictures() + pRPL0->getNumberOfInterLayerPictures(); - int numEntriesL1 = pRPL1->getNumberOfShorttermPictures() + pRPL1->getNumberOfLongtermPictures() + pRPL1->getNumberOfInterLayerPictures(); - - int numActiveEntriesL0 = getNumRefIdx(REF_PIC_LIST_0); - int numActiveEntriesL1 = getNumRefIdx(REF_PIC_LIST_1); - - int layerIdx = m_pcPic->cs->vps == nullptr ? 0 : m_pcPic->cs->vps->getGeneralLayerIdx(m_pcPic->layerId); - for (int i = 0; i < numEntriesL0; i++) + // subpic RPL related constraints + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if (pRPL0->isInterLayerRefPic(i)) - { - int refLayerId = m_pcPic->cs->vps->getLayerId(m_pcPic->cs->vps->getDirectRefLayerIdx(layerIdx, pRPL0->getInterLayerRefPicIdx(i))); - pcRefPic = xGetRefPic(rcListPic, getPOC(), refLayerId); - refPicPOC = pcRefPic->getPOC(); - } - else if (!pRPL0->isRefPicLongterm(i)) - { - refPicPOC = getPOC() + pRPL0->getRefPicIdentifier(i); - pcRefPic = xGetRefPic(rcListPic, refPicPOC, m_pcPic->layerId); - } - else - { - int pocBits = getSPS()->getBitsForPOC(); - int pocMask = (1 << pocBits) - 1; - int ltrpPoc = pRPL0->getRefPicIdentifier(i) & pocMask; - if(pRPL0->getDeltaPocMSBPresentFlag(i)) - { - ltrpPoc += getPOC() - pRPL0->getDeltaPocMSBCycleLT(i) * (pocMask + 1) - (getPOC() & pocMask); - } - pcRefPic = xGetLongTermRefPic(rcListPic, ltrpPoc, pRPL0->getDeltaPocMSBPresentFlag(i), m_pcPic->layerId); - refPicPOC = pcRefPic->getPOC(); - } + const ReferencePictureList *rpl = l == REF_PIC_LIST_0 ? pRPL0 : pRPL1; + + const int numEntries = rpl->getNumRefEntries(); + const int numActiveEntries = getNumRefIdx(l); - if (pcRefPic) // the checks are for all reference picture, but we may not have an inactive reference picture, if starting with a CRA + for (int i = 0; i < numEntries; i++) { - refPicDecodingOrderNumber = pcRefPic->getDecodingOrderNumber(); + Picture *refPic; + int refPicPOC; - if (nalUnitType == NAL_UNIT_CODED_SLICE_CRA || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_W_RADL || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_N_LP) + if (rpl->isInterLayerRefPic(i)) { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture, with nuh_layer_id equal to a particular value " - "layerId and subpicture index equal to a particular value subpicIdx, is an IRAP subpicture, there shall be no picture referred to by an entry in RefPicList[0] that " - "precedes, in output order or decoding order,any preceding picture, in decoding order (when present), containing an IRAP subpicture with nuh_layer_id equal to " - "layerId and subpicture index equal to subpicIdx"); - } + const VPS *vps = m_pcPic->cs->vps; + const int layerIdx = vps->getGeneralLayerIdx(m_pcPic->layerId); + const int refLayerId = vps->getLayerId(vps->getDirectRefLayerIdx(layerIdx, rpl->getInterLayerRefPicIdx(i))); - if (prevIRAPSubpicPOC < getPOC() && !getSPS()->getFieldSeqFlag()) + refPic = xGetRefPic(rcListPic, getPOC(), refLayerId); + refPicPOC = refPic->getPOC(); + } + else if (!rpl->isRefPicLongterm(i)) { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture follows an IRAP subpicture having the same value " - "of nuh_layer_id and the same value of subpicture index in both decoding and output order, there shall be no picture referred to by an active entry in RefPicList[ 0 ] " - "that precedes the picture containing that IRAP subpicture in output order or decoding order"); + refPicPOC = getPOC() + rpl->getRefPicIdentifier(i); + refPic = xGetRefPic(rcListPic, refPicPOC, m_pcPic->layerId); } - - if (i < numActiveEntriesL0) + else { - if (prevIRAPSubpicPOC < getPOC()) - { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture follows an IRAP subpicture having the same value " - "of nuh_layer_id and the same value of subpicture index and the leading subpictures, if any, associated with that IRAP subpicture in both decoding and output order, " - "there shall be no picture referred to by an entry in RefPicList[ 0 ] that precedes the picture containing that IRAP subpicture in output order or decoding order"); - } - - if (nalUnitType == NAL_UNIT_CODED_SLICE_RADL) + int pocBits = getSPS()->getBitsForPOC(); + int pocMask = (1 << pocBits) - 1; + int ltrpPoc = pRPL0->getRefPicIdentifier(i) & pocMask; + if (rpl->getDeltaPocMSBPresentFlag(i)) { - CHECK(refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture, with nuh_layer_id equal to a particular value layerId and subpicture index equal " - "to a particular value subpicIdx, is a RADL subpicture, there shall be no active entry in RefPicList[ 0 ] that is a picture that precedes the picture containing the" - "associated IRAP subpicture in decoding order"); - - if (pcRefPic->layerId == m_nuhLayerId) - { - for (int i = 0; i < pcRefPic->numSlices; i++) - { - if (pcRefPic->sliceSubpicIdx[i] == curSubpicIdx) - { - CHECK(pcRefPic->slices[i]->getNalUnitType() == NAL_UNIT_CODED_SLICE_RASL, "When the current subpicture, with nuh_layer_id equal to a particular value layerId and " - "subpicture index equal to a particular value subpicIdx, is a RADL subpicture, there shall be no active entry in RefPicList[ 0 ] that is a picture with " - "nuh_layer_id equal to layerId containing a RASL subpicture with subpicture index equal to subpicIdx"); - } - } - } + ltrpPoc += getPOC() - pRPL0->getDeltaPocMSBCycleLT(i) * (pocMask + 1) - (getPOC() & pocMask); } + refPic = xGetLongTermRefPic(rcListPic, ltrpPoc, rpl->getDeltaPocMSBPresentFlag(i), m_pcPic->layerId); + refPicPOC = refPic->getPOC(); } - } - } - for (int i = 0; i < numEntriesL1; i++) - { - if (pRPL1->isInterLayerRefPic(i)) - { - int refLayerId = m_pcPic->cs->vps->getLayerId(m_pcPic->cs->vps->getDirectRefLayerIdx(layerIdx, pRPL1->getInterLayerRefPicIdx(i))); - pcRefPic = xGetRefPic(rcListPic, getPOC(), refLayerId); - refPicPOC = pcRefPic->getPOC(); - } - else if (!pRPL1->isRefPicLongterm(i)) - { - refPicPOC = getPOC() + pRPL1->getRefPicIdentifier(i); - pcRefPic = xGetRefPic(rcListPic, refPicPOC, m_pcPic->layerId); - } - else - { - int pocBits = getSPS()->getBitsForPOC(); - int pocMask = (1 << pocBits) - 1; - int ltrpPoc = pRPL1->getRefPicIdentifier(i) & pocMask; - if (pRPL1->getDeltaPocMSBPresentFlag(i)) + // checks are for all reference pictures, but inactive reference pictures may be missing if starting with a CRA + if (refPic != nullptr) { - ltrpPoc += getPOC() - pRPL1->getDeltaPocMSBCycleLT(i) * (pocMask + 1) - (getPOC() & pocMask); - } - pcRefPic = xGetLongTermRefPic(rcListPic, ltrpPoc, pRPL1->getDeltaPocMSBPresentFlag(i), m_pcPic->layerId); - refPicPOC = pcRefPic->getPOC(); - } - if (pcRefPic) // the checks are for all reference picture, but we may not have an inactive reference picture, if starting with a CRA - { - refPicDecodingOrderNumber = pcRefPic->getDecodingOrderNumber(); + const int refPicDecodingOrderNumber = refPic->getDecodingOrderNumber(); - if (nalUnitType == NAL_UNIT_CODED_SLICE_CRA || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_W_RADL || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_N_LP) - { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture, with nuh_layer_id equal to a particular value" - "layerId and subpicture index equal to a particular value subpicIdx, is an IRAP subpicture, there shall be no picture referred to by an entry in RefPicList[1] that" - "precedes, in output order or decoding order,any preceding picture, in decoding order (when present), containing an IRAP subpicture with nuh_layer_id equal to " - "layerId and subpicture index equal to subpicIdx"); - } + if (nalUnitType == NAL_UNIT_CODED_SLICE_CRA || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_W_RADL + || nalUnitType == NAL_UNIT_CODED_SLICE_IDR_N_LP) + { + CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, + "When the current subpicture, with nuh_layer_id equal to a particular value layerId and subpicture " + "index equal to a particular value subpicIdx, is an IRAP subpicture, there shall be no picture " + "referred to by an entry in RefPicList[i] that precedes, in output order or decoding order,any " + "preceding picture, in decoding order (when present), containing an IRAP subpicture with nuh_layer_id " + "equal to layerId and subpicture index equal to subpicIdx"); + } - if (prevIRAPSubpicPOC < getPOC() && !getSPS()->getFieldSeqFlag()) - { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture follows an IRAP subpicture having the same value " - "of nuh_layer_id and the same value of subpicture index in both decoding and output order, there shall be no picture referred to by an active entry in RefPicList[ 1 ] " - "that precedes the picture containing that IRAP subpicture in output order or decoding order"); - } - if (i < numActiveEntriesL1) - { - if (prevIRAPSubpicPOC < getPOC()) + if (prevIRAPSubpicPOC < getPOC() && !getSPS()->getFieldSeqFlag()) { - CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture follows an IRAP subpicture having the same value " - "of nuh_layer_id and the same value of subpicture index and the leading subpictures, if any, associated with that IRAP subpicture in both decoding and output order, " - "there shall be no picture referred to by an entry in RefPicList[ 1 ] that precedes the picture containing that IRAP subpicture in output order or decoding order"); + CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, + "When the current subpicture follows an IRAP subpicture having the same value of nuh_layer_id and the " + "same value of subpicture index in both decoding and output order, there shall be no picture referred " + "to by an active entry in RefPicList[ i ] that precedes the picture containing that IRAP subpicture in " + "output order or decoding order"); } - if (nalUnitType == NAL_UNIT_CODED_SLICE_RADL) + if (i < numActiveEntries) { - CHECK(refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, "When the current subpicture, with nuh_layer_id equal to a particular value layerId and subpicture index equal " - "to a particular value subpicIdx, is a RADL subpicture, there shall be no active entry in RefPicList[ 1 ] that is a picture that precedes the picture containing the" - "associated IRAP subpicture in decoding order"); + if (prevIRAPSubpicPOC < getPOC()) + { + CHECK(refPicPOC < prevIRAPSubpicPOC || refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, + "When the current subpicture follows an IRAP subpicture having the same value " + "of nuh_layer_id and the same value of subpicture index and the leading subpictures, if any, " + "associated with that IRAP subpicture in both decoding and output order, " + "there shall be no picture referred to by an entry in RefPicList[ i ] that precedes the picture " + "containing that IRAP subpicture in output order or decoding order"); + } - if (pcRefPic->layerId == m_nuhLayerId) + if (nalUnitType == NAL_UNIT_CODED_SLICE_RADL) { - for (int i = 0; i < pcRefPic->numSlices; i++) + CHECK(refPicDecodingOrderNumber < prevIRAPSubpicDecOrderNo, + "When the current subpicture, with nuh_layer_id equal to a particular value layerId and subpicture " + "index equal to a particular value subpicIdx, is a RADL subpicture, there shall be no active entry " + "in RefPicList[ i ] that is a picture that precedes the picture containing the associated IRAP " + "subpicture in decoding order"); + + if (refPic->layerId == m_nuhLayerId) { - if (pcRefPic->sliceSubpicIdx[i] == curSubpicIdx) + for (int i = 0; i < refPic->numSlices; i++) { - CHECK(pcRefPic->slices[i]->getNalUnitType() == NAL_UNIT_CODED_SLICE_RASL, "When the current subpicture, with nuh_layer_id equal to a particular value layerId and " - "subpicture index equal to a particular value subpicIdx, is a RADL subpicture, there shall be no active entry in RefPicList[ 1 ] that is a picture with " - "nuh_layer_id equal to layerId containing a RASL subpicture with subpicture index equal to subpicIdx"); + if (refPic->sliceSubpicIdx[i] == curSubpicIdx) + { + CHECK(refPic->slices[i]->getNalUnitType() == NAL_UNIT_CODED_SLICE_RASL, + "When the current subpicture, with nuh_layer_id equal to a particular value layerId and " + "subpicture index equal to a particular value subpicIdx, is a RADL subpicture, there shall be " + "no active entry in RefPicList[ i ] that is a picture with nuh_layer_id equal to layerId " + "containing a RASL subpicture with subpicture index equal to subpicIdx"); + } } } } @@ -1571,259 +1472,156 @@ void Slice::checkSubpicTypeConstraints(PicList& rcListPic, const ReferencePictur //Function for applying picture marking based on the Reference Picture List void Slice::applyReferencePictureListBasedMarking( PicList& rcListPic, const ReferencePictureList *pRPL0, const ReferencePictureList *pRPL1, const int layerId, const PPS& pps ) const { - int i, isReference; checkLeadingPictureRestrictions(rcListPic, pps); - bool isNeedToCheck = (this->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_N_LP || this->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_W_RADL) && !pps.getMixedNaluTypesInPicFlag() ? false : true; - // mark long-term reference pictures in List0 - for( i = 0; i < pRPL0->getNumberOfShorttermPictures() + pRPL0->getNumberOfLongtermPictures() + pRPL0->getNumberOfInterLayerPictures(); i++ ) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if( !pRPL0->isRefPicLongterm( i ) || pRPL0->isInterLayerRefPic( i ) ) - { - continue; - } + const ReferencePictureList *rpl = l == REF_PIC_LIST_0 ? pRPL0 : pRPL1; - int isAvailable = 0; - PicList::iterator iterPic = rcListPic.begin(); - while (iterPic != rcListPic.end()) + for (int i = 0; i < rpl->getNumRefEntries(); i++) { - Picture* rpcPic = *(iterPic++); - if (!rpcPic->referenced) + if (!rpl->isRefPicLongterm(i) || rpl->isInterLayerRefPic(i)) { continue; } - int pocCycle = 1 << (rpcPic->cs->sps->getBitsForPOC()); - int curPoc = rpcPic->getPOC(); - int refPoc = pRPL0->getRefPicIdentifier(i) & (pocCycle - 1); - if(pRPL0->getDeltaPocMSBPresentFlag(i)) - { - refPoc += getPOC() - pRPL0->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); - } - else - { - curPoc = curPoc & (pocCycle - 1); - } - if (rpcPic->longTerm && curPoc == refPoc && rpcPic->referenced) - { - isAvailable = 1; - break; - } - } - // if there was no such long-term check the short terms - if (!isAvailable) - { - iterPic = rcListPic.begin(); - while (iterPic != rcListPic.end()) - { - Picture* rpcPic = *(iterPic++); - if (!rpcPic->referenced) - { - continue; - } - int pocCycle = 1 << (rpcPic->cs->sps->getBitsForPOC()); - int curPoc = rpcPic->getPOC(); - int refPoc = pRPL0->getRefPicIdentifier(i) & (pocCycle - 1); - if(pRPL0->getDeltaPocMSBPresentFlag(i)) - { - refPoc += getPOC() - pRPL0->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); - } - else - { - curPoc = curPoc & (pocCycle - 1); - } - if (!rpcPic->longTerm && curPoc == refPoc && rpcPic->referenced) - { - isAvailable = 1; - rpcPic->longTerm = true; - break; - } - } - } - } - - // mark long-term reference pictures in List1 - for( i = 0; i < pRPL1->getNumberOfShorttermPictures() + pRPL1->getNumberOfLongtermPictures() + pRPL1->getNumberOfInterLayerPictures(); i++ ) - { - if( !pRPL1->isRefPicLongterm( i ) || pRPL1->isInterLayerRefPic( i ) ) - { - continue; - } - int isAvailable = 0; - PicList::iterator iterPic = rcListPic.begin(); - while (iterPic != rcListPic.end()) - { - Picture* rpcPic = *(iterPic++); - if (!rpcPic->referenced) - { - continue; - } - int pocCycle = 1 << (rpcPic->cs->sps->getBitsForPOC()); - int curPoc = rpcPic->getPOC(); - int refPoc = pRPL1->getRefPicIdentifier(i) & (pocCycle - 1); - if(pRPL1->getDeltaPocMSBPresentFlag(i)) - { - refPoc += getPOC() - pRPL1->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); - } - else - { - curPoc = curPoc & (pocCycle - 1); - } - if (rpcPic->longTerm && curPoc == refPoc && rpcPic->referenced && rpcPic->reconstructed && rpcPic->layerId == getNalUnitLayerId()) - { - isAvailable = 1; - break; - } - } - // if there was no such long-term check the short terms - if (!isAvailable) - { - iterPic = rcListPic.begin(); - while (iterPic != rcListPic.end()) + bool isAvailable = false; + for (const Picture *pic: rcListPic) { - Picture* rpcPic = *(iterPic++); - if (!rpcPic->referenced) + if (!pic->referenced) { continue; } - int pocCycle = 1 << (rpcPic->cs->sps->getBitsForPOC()); - int curPoc = rpcPic->getPOC(); - int refPoc = pRPL1->getRefPicIdentifier(i) & (pocCycle - 1); - if(pRPL1->getDeltaPocMSBPresentFlag(i)) + int pocCycle = 1 << (pic->cs->sps->getBitsForPOC()); + int curPoc = pic->getPOC(); + int refPoc = rpl->getRefPicIdentifier(i) & (pocCycle - 1); + if (rpl->getDeltaPocMSBPresentFlag(i)) { - refPoc += getPOC() - pRPL1->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); + refPoc += getPOC() - rpl->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); } else { curPoc = curPoc & (pocCycle - 1); } - if (!rpcPic->longTerm && curPoc == refPoc && rpcPic->referenced && rpcPic->reconstructed && rpcPic->layerId == getNalUnitLayerId()) + if (pic->longTerm && curPoc == refPoc && pic->referenced) { - isAvailable = 1; - rpcPic->longTerm = true; + isAvailable = true; break; } } - } - } - - // loop through all pictures in the reference picture buffer - PicList::iterator iterPic = rcListPic.begin(); - while (iterPic != rcListPic.end()) - { - Picture* pcPic = *(iterPic++); - - if (!pcPic->referenced) - { - continue; - } - - isReference = 0; - // loop through all pictures in the Reference Picture Set - // to see if the picture should be kept as reference picture - for( i = 0; isNeedToCheck && !isReference && i < pRPL0->getNumberOfShorttermPictures() + pRPL0->getNumberOfLongtermPictures() + pRPL0->getNumberOfInterLayerPictures(); i++ ) - { - if( pRPL0->isInterLayerRefPic( i ) ) - { - // Diagonal inter-layer prediction is not allowed - CHECK( pRPL0->getRefPicIdentifier( i ), "ILRP identifier should be 0" ); - - if (pcPic->poc == m_poc) - { - isReference = 1; - pcPic->longTerm = true; - } - } - else if (pcPic->layerId == layerId) + // if there was no such long-term check the short terms + if (!isAvailable) { - if (!(pRPL0->isRefPicLongterm(i))) + for (Picture *pic: rcListPic) { - if (pcPic->poc == this->getPOC() + pRPL0->getRefPicIdentifier(i)) + if (!pic->referenced) { - isReference = 1; - pcPic->longTerm = false; + continue; } - } - else - { - int pocCycle = 1 << (pcPic->cs->sps->getBitsForPOC()); - int curPoc = pcPic->poc; - int refPoc = pRPL0->getRefPicIdentifier(i) & (pocCycle - 1); - if (pRPL0->getDeltaPocMSBPresentFlag(i)) + int pocCycle = 1 << (pic->cs->sps->getBitsForPOC()); + int curPoc = pic->getPOC(); + int refPoc = rpl->getRefPicIdentifier(i) & (pocCycle - 1); + if (rpl->getDeltaPocMSBPresentFlag(i)) { - refPoc += getPOC() - pRPL0->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); + refPoc += getPOC() - rpl->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); } else { curPoc = curPoc & (pocCycle - 1); } - if (pcPic->longTerm && curPoc == refPoc) + if (!pic->longTerm && curPoc == refPoc && pic->referenced) { - isReference = 1; - pcPic->longTerm = true; + isAvailable = true; + pic->longTerm = true; + break; } } } } + } - for( i = 0; isNeedToCheck && !isReference && i < pRPL1->getNumberOfShorttermPictures() + pRPL1->getNumberOfLongtermPictures() + pRPL1->getNumberOfInterLayerPictures(); i++ ) + if (isIDRorBLA() && !pps.getMixedNaluTypesInPicFlag()) + { + return; + } + + // loop through all pictures in the reference picture buffer + for (Picture *pic: rcListPic) + { + if (!pic->referenced) { - if( pRPL1->isInterLayerRefPic( i ) ) - { - // Diagonal inter-layer prediction is not allowed - CHECK( pRPL1->getRefPicIdentifier( i ), "ILRP identifier should be 0" ); + continue; + } - if (pcPic->poc == m_poc) - { - isReference = 1; - pcPic->longTerm = true; - } - } - else if( pcPic->layerId == layerId ) + bool isReference = false; + + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + const ReferencePictureList *rpl = l == REF_PIC_LIST_0 ? pRPL0 : pRPL1; + + // loop through all pictures in the Reference Picture Set + // to see if the picture should be kept as reference picture + for (int i = 0; !isReference && i < rpl->getNumRefEntries(); i++) { - if (!(pRPL1->isRefPicLongterm(i))) + if (rpl->isInterLayerRefPic(i)) { - if (pcPic->poc == this->getPOC() + pRPL1->getRefPicIdentifier(i)) + // Diagonal inter-layer prediction is not allowed + CHECK(rpl->getRefPicIdentifier(i), "ILRP identifier should be 0"); + + if (pic->poc == m_poc) { - isReference = 1; - pcPic->longTerm = false; + isReference = true; + pic->longTerm = true; } } - else + else if (pic->layerId == layerId) { - int pocCycle = 1 << (pcPic->cs->sps->getBitsForPOC()); - int curPoc = pcPic->poc; - int refPoc = pRPL1->getRefPicIdentifier(i) & (pocCycle - 1); - if (pRPL1->getDeltaPocMSBPresentFlag(i)) + if (!rpl->isRefPicLongterm(i)) { - refPoc += getPOC() - pRPL1->getDeltaPocMSBCycleLT(i) * pocCycle - (getPOC() & (pocCycle - 1)); + if (pic->poc == getPOC() + rpl->getRefPicIdentifier(i)) + { + isReference = true; + pic->longTerm = false; + } } else { - curPoc = curPoc & (pocCycle - 1); - } - if (pcPic->longTerm && curPoc == refPoc) - { - isReference = 1; - pcPic->longTerm = true; + const int pocCycle = 1 << pic->cs->sps->getBitsForPOC(); + const int pocMask = pocCycle - 1; + int curPoc = pic->poc; + int refPoc = rpl->getRefPicIdentifier(i) & pocMask; + if (rpl->getDeltaPocMSBPresentFlag(i)) + { + refPoc += (getPOC() & ~pocMask) - rpl->getDeltaPocMSBCycleLT(i) * pocCycle; + } + else + { + curPoc &= pocMask; + } + if (pic->longTerm && curPoc == refPoc) + { + isReference = true; + pic->longTerm = true; + } } } } } + // mark the picture as "unused for reference" if it is not in // the Reference Picture List - if (pcPic->layerId == layerId && pcPic->poc != m_poc && isReference == 0) + if (pic->layerId == layerId && pic->poc != m_poc && !isReference) { - pcPic->referenced = false; - pcPic->longTerm = false; + pic->referenced = false; + pic->longTerm = false; } // sanity checks - if (pcPic->referenced) + if (pic->referenced) { //check that pictures of higher temporal layers are not used - CHECK(pcPic->usedByCurr && !(pcPic->temporalId <= this->getTLayer()), "Invalid state"); + CHECK(pic->usedByCurr && pic->temporalId > this->getTLayer(), "Invalid state"); } } } @@ -1839,7 +1637,7 @@ int Slice::checkThatAllRefPicsAreAvailable(PicList& rcListPic, const ReferencePi return 0; // Assume that all pic in the DPB will be flushed anyway so no need to check. } - int numberOfPictures = pRPL->getNumberOfLongtermPictures() + pRPL->getNumberOfShorttermPictures() + pRPL->getNumberOfInterLayerPictures(); + int numberOfPictures = pRPL->getNumRefEntries(); //Check long term ref pics for (int ii = 0; pRPL->getNumberOfLongtermPictures() > 0 && ii < numberOfPictures; ii++) { @@ -2058,7 +1856,7 @@ int Slice::checkThatAllRefPicsAreAvailable(PicList& rcListPic, const ReferencePi bool Slice::isPOCInRefPicList(const ReferencePictureList *rpl, int poc ) { - for( int i = 0; i < rpl->getNumberOfLongtermPictures() + rpl->getNumberOfShorttermPictures() + rpl->getNumberOfInterLayerPictures(); i++ ) + for (int i = 0; i < rpl->getNumRefEntries(); i++) { if( rpl->isInterLayerRefPic( i ) ) { @@ -2695,59 +2493,57 @@ uint32_t VPS::getMaxTidinTOls(int m_targetOlsIdx) // ------------------------------------------------------------------------------------------------ PicHeader::PicHeader() -: m_valid ( 0 ) -, m_nonReferencePictureFlag ( 0 ) -, m_gdrPicFlag ( 0 ) -, m_recoveryPocCnt ( -1 ) -, m_noOutputBeforeRecoveryFlag ( false ) -, m_handleCraAsCvsStartFlag ( false ) -, m_handleGdrAsCvsStartFlag ( false ) -, m_spsId ( -1 ) -, m_ppsId ( -1 ) -, m_pocMsbPresentFlag ( 0 ) -, m_pocMsbVal ( 0 ) -, m_virtualBoundariesEnabledFlag ( 0 ) -, m_virtualBoundariesPresentFlag ( 0 ) -, m_numVerVirtualBoundaries ( 0 ) -, m_numHorVirtualBoundaries ( 0 ) -, m_picOutputFlag ( true ) -, m_rpl0Idx ( 0 ) -, m_rpl1Idx ( 0 ) -, m_splitConsOverrideFlag ( 0 ) -, m_cuQpDeltaSubdivIntra ( 0 ) -, m_cuQpDeltaSubdivInter ( 0 ) -, m_cuChromaQpOffsetSubdivIntra ( 0 ) -, m_cuChromaQpOffsetSubdivInter ( 0 ) -, m_enableTMVPFlag ( true ) -, m_picColFromL0Flag ( true ) -, m_mvdL1ZeroFlag ( 0 ) -, m_maxNumAffineMergeCand ( AFFINE_MRG_MAX_NUM_CANDS ) -, m_disFracMMVD ( 0 ) -, m_bdofDisabledFlag ( 0 ) -, m_dmvrDisabledFlag ( 0 ) -, m_profDisabledFlag ( 0 ) -, m_jointCbCrSignFlag ( 0 ) -, m_qpDelta ( 0 ) -, m_numAlfApsIdsLuma ( 0 ) -, m_alfApsIdsLuma ( 0 ) -, m_alfApsIdChroma ( 0 ) -, m_deblockingFilterOverrideFlag ( 0 ) -, m_deblockingFilterDisable ( 0 ) -, m_deblockingFilterBetaOffsetDiv2 ( 0 ) -, m_deblockingFilterTcOffsetDiv2 ( 0 ) -, m_deblockingFilterCbBetaOffsetDiv2 ( 0 ) -, m_deblockingFilterCbTcOffsetDiv2 ( 0 ) -, m_deblockingFilterCrBetaOffsetDiv2 ( 0 ) -, m_deblockingFilterCrTcOffsetDiv2 ( 0 ) -, m_lmcsEnabledFlag ( 0 ) -, m_lmcsApsId ( -1 ) -, m_lmcsAps ( nullptr ) -, m_lmcsChromaResidualScaleFlag ( 0 ) -, m_explicitScalingListEnabledFlag ( 0 ) -, m_scalingListApsId ( -1 ) -, m_scalingListAps ( nullptr ) -, m_numL0Weights ( 0 ) -, m_numL1Weights ( 0 ) + : m_valid(0) + , m_nonReferencePictureFlag(0) + , m_gdrPicFlag(0) + , m_recoveryPocCnt(-1) + , m_noOutputBeforeRecoveryFlag(false) + , m_handleCraAsCvsStartFlag(false) + , m_handleGdrAsCvsStartFlag(false) + , m_spsId(-1) + , m_ppsId(-1) + , m_pocMsbPresentFlag(0) + , m_pocMsbVal(0) + , m_virtualBoundariesEnabledFlag(0) + , m_virtualBoundariesPresentFlag(0) + , m_numVerVirtualBoundaries(0) + , m_numHorVirtualBoundaries(0) + , m_picOutputFlag(true) + , m_rplIdx{ 0, 0 } + , m_splitConsOverrideFlag(0) + , m_cuQpDeltaSubdivIntra(0) + , m_cuQpDeltaSubdivInter(0) + , m_cuChromaQpOffsetSubdivIntra(0) + , m_cuChromaQpOffsetSubdivInter(0) + , m_enableTMVPFlag(true) + , m_picColFromL0Flag(true) + , m_mvdL1ZeroFlag(0) + , m_maxNumAffineMergeCand(AFFINE_MRG_MAX_NUM_CANDS) + , m_disFracMMVD(0) + , m_bdofDisabledFlag(0) + , m_dmvrDisabledFlag(0) + , m_profDisabledFlag(0) + , m_jointCbCrSignFlag(0) + , m_qpDelta(0) + , m_numAlfApsIdsLuma(0) + , m_alfApsIdsLuma(0) + , m_alfApsIdChroma(0) + , m_deblockingFilterOverrideFlag(0) + , m_deblockingFilterDisable(0) + , m_deblockingFilterBetaOffsetDiv2(0) + , m_deblockingFilterTcOffsetDiv2(0) + , m_deblockingFilterCbBetaOffsetDiv2(0) + , m_deblockingFilterCbTcOffsetDiv2(0) + , m_deblockingFilterCrBetaOffsetDiv2(0) + , m_deblockingFilterCrTcOffsetDiv2(0) + , m_lmcsEnabledFlag(0) + , m_lmcsApsId(-1) + , m_lmcsAps(nullptr) + , m_lmcsChromaResidualScaleFlag(0) + , m_explicitScalingListEnabledFlag(0) + , m_scalingListApsId(-1) + , m_scalingListAps(nullptr) + , m_numWeights{ 0, 0 } { memset(m_virtualBoundariesPosX, 0, sizeof(m_virtualBoundariesPosX)); memset(m_virtualBoundariesPosY, 0, sizeof(m_virtualBoundariesPosY)); @@ -2758,17 +2554,14 @@ PicHeader::PicHeader() memset(m_maxBTSize, 0, sizeof(m_maxBTSize)); memset(m_maxTTSize, 0, sizeof(m_maxTTSize)); - m_RPL0.setNumberOfActivePictures(0); - m_RPL0.setNumberOfShorttermPictures(0); - m_RPL0.setNumberOfLongtermPictures(0); - m_RPL0.setLtrpInSliceHeaderFlag(0); - m_RPL0.setNumberOfInterLayerPictures( 0 ); - - m_RPL1.setNumberOfActivePictures(0); - m_RPL1.setNumberOfShorttermPictures(0); - m_RPL1.setNumberOfLongtermPictures(0); - m_RPL1.setLtrpInSliceHeaderFlag(0); - m_RPL1.setNumberOfInterLayerPictures( 0 ); + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + m_rpl[l].setNumberOfActivePictures(0); + m_rpl[l].setNumberOfShorttermPictures(0); + m_rpl[l].setNumberOfLongtermPictures(0); + m_rpl[l].setLtrpInSliceHeaderFlag(0); + m_rpl[l].setNumberOfInterLayerPictures(0); + } m_alfApsIdsLuma.resize(0); @@ -2798,8 +2591,8 @@ void PicHeader::initPicHeader() m_numVerVirtualBoundaries = 0; m_numHorVirtualBoundaries = 0; m_picOutputFlag = true; - m_rpl0Idx = 0; - m_rpl1Idx = 0; + m_rplIdx[REF_PIC_LIST_0] = 0; + m_rplIdx[REF_PIC_LIST_1] = 0; m_splitConsOverrideFlag = 0; m_cuQpDeltaSubdivIntra = 0; m_cuQpDeltaSubdivInter = 0; @@ -2832,8 +2625,8 @@ void PicHeader::initPicHeader() m_explicitScalingListEnabledFlag = 0; m_scalingListApsId = -1; m_scalingListAps = nullptr; - m_numL0Weights = 0; - m_numL1Weights = 0; + m_numWeights[REF_PIC_LIST_0] = 0; + m_numWeights[REF_PIC_LIST_1] = 0; memset(m_virtualBoundariesPosX, 0, sizeof(m_virtualBoundariesPosX)); memset(m_virtualBoundariesPosY, 0, sizeof(m_virtualBoundariesPosY)); m_saoEnabledFlag.fill(false); @@ -2843,15 +2636,13 @@ void PicHeader::initPicHeader() memset(m_maxBTSize, 0, sizeof(m_maxBTSize)); memset(m_maxTTSize, 0, sizeof(m_maxTTSize)); - m_RPL0.setNumberOfActivePictures(0); - m_RPL0.setNumberOfShorttermPictures(0); - m_RPL0.setNumberOfLongtermPictures(0); - m_RPL0.setLtrpInSliceHeaderFlag(0); - - m_RPL1.setNumberOfActivePictures(0); - m_RPL1.setNumberOfShorttermPictures(0); - m_RPL1.setNumberOfLongtermPictures(0); - m_RPL1.setLtrpInSliceHeaderFlag(0); + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + m_rpl[l].setNumberOfActivePictures(0); + m_rpl[l].setNumberOfShorttermPictures(0); + m_rpl[l].setNumberOfLongtermPictures(0); + m_rpl[l].setLtrpInSliceHeaderFlag(0); + } m_alfApsIdsLuma.resize(0); #if GDR_ENABLED @@ -2951,8 +2742,7 @@ SPS::SPS() , m_maxTTSize{ 0, 0, 0 } , m_maxCuWidth(32) , m_maxCuHeight(32) - , m_numRPL0(0) - , m_numRPL1(0) + , m_numRpl{ 0, 0 } , m_rpl1CopyFromRpl0Flag(false) , m_rpl1IdxPresentFlag(false) , m_allRplEntriesHasSameSignFlag(true) @@ -3049,22 +2839,13 @@ SPS::~SPS() { } -void SPS::createRPLList0(int numRPL) +void SPS::createRplList(RefPicList l, int numRPL) { - m_RPLList0.destroy(); - m_RPLList0.create(numRPL); - m_numRPL0 = numRPL; - m_rpl1IdxPresentFlag = (m_numRPL0 != m_numRPL1) ? true : false; + m_rplList[l].destroy(); + m_rplList[l].create(numRPL); + m_numRpl[l] = numRPL; + m_rpl1IdxPresentFlag = m_numRpl[REF_PIC_LIST_0] != m_numRpl[REF_PIC_LIST_1]; } -void SPS::createRPLList1(int numRPL) -{ - m_RPLList1.destroy(); - m_RPLList1.create(numRPL); - m_numRPL1 = numRPL; - - m_rpl1IdxPresentFlag = (m_numRPL0 != m_numRPL1) ? true : false; -} - const int SPS::m_winUnitX[]={1,2,2,1}; const int SPS::m_winUnitY[]={1,2,1,1}; @@ -3188,8 +2969,7 @@ PPS::PPS() , m_chromaCrQpOffset(0) , m_chromaCbCrQpOffset(0) , m_chromaQpOffsetListLen(0) - , m_numRefIdxL0DefaultActive(1) - , m_numRefIdxL1DefaultActive(1) + , m_numRefIdxDefaultActive{ 1, 1 } , m_rpl1IdxPresentFlag(false) , m_numSubPics(1) , m_subPicIdMappingInPpsFlag(0) @@ -3821,26 +3601,6 @@ bool ReferencePictureList::isRefPicLongterm(int idx) const return m_isLongtermRefPic[idx]; } -void ReferencePictureList::setNumberOfShorttermPictures(int numberOfStrp) -{ - m_numberOfShorttermPictures = numberOfStrp; -} - -int ReferencePictureList::getNumberOfShorttermPictures() const -{ - return m_numberOfShorttermPictures; -} - -void ReferencePictureList::setNumberOfLongtermPictures(int numberOfLtrp) -{ - m_numberOfLongtermPictures = numberOfLtrp; -} - -int ReferencePictureList::getNumberOfLongtermPictures() const -{ - return m_numberOfLongtermPictures; -} - void ReferencePictureList::setPOC(int idx, int POC) { m_POC[idx] = POC; @@ -3865,7 +3625,7 @@ void ReferencePictureList::printRefPicInfo() const { //DTRACE(g_trace_ctx, D_RPSINFO, "RefPics = { "); printf("RefPics = { "); - int numRefPic = getNumberOfShorttermPictures() + getNumberOfLongtermPictures(); + int numRefPic = getNumRefEntries(); for (int ii = 0; ii < numRefPic; ii++) { //DTRACE(g_trace_ctx, D_RPSINFO, "%d%s ", m_refPicIdentifier[ii], (m_isLongtermRefPic[ii] == 1) ? "[LT]" : "[ST]"); diff --git a/source/Lib/CommonLib/Slice.h b/source/Lib/CommonLib/Slice.h index 2f78c2a32676cb5a7db435705741f6743eddab26..e6ea62824bf44f5898339c96809c917fea23edbd 100644 --- a/source/Lib/CommonLib/Slice.h +++ b/source/Lib/CommonLib/Slice.h @@ -84,11 +84,11 @@ public: int getRefPicIdentifier(int idx) const; bool isRefPicLongterm(int idx) const; - void setNumberOfShorttermPictures(int numberOfStrp); - int getNumberOfShorttermPictures() const; + void setNumberOfShorttermPictures(int n) { m_numberOfShorttermPictures = n; } + int getNumberOfShorttermPictures() const { return m_numberOfShorttermPictures; } - void setNumberOfLongtermPictures(int numberOfLtrp); - int getNumberOfLongtermPictures() const; + void setNumberOfLongtermPictures(int n) { m_numberOfLongtermPictures = n; } + int getNumberOfLongtermPictures() const { return m_numberOfLongtermPictures; } void setLtrpInSliceHeaderFlag(bool flag) { m_ltrpInSliceHeaderFlag = flag; } bool getLtrpInSliceHeaderFlag() const { return m_ltrpInSliceHeaderFlag; } @@ -1433,10 +1433,8 @@ private: uint32_t m_maxCuWidth; uint32_t m_maxCuHeight; - RPLList m_RPLList0; - RPLList m_RPLList1; - uint32_t m_numRPL0; - uint32_t m_numRPL1; + RPLList m_rplList[NUM_REF_PIC_LIST_01]; + uint32_t m_numRpl[NUM_REF_PIC_LIST_01]; bool m_rpl1CopyFromRpl0Flag; bool m_rpl1IdxPresentFlag; @@ -1723,17 +1721,10 @@ public: const std::vector<bool> getExtraSHBitPresentFlags() const { return m_extraSHBitPresentFlag; } void setMaxNumReorderPics(int i, uint32_t tlayer) { m_maxNumReorderPics[tlayer] = i; } int getMaxNumReorderPics(uint32_t tlayer) const { return m_maxNumReorderPics[tlayer]; } - void createRPLList0(int numRPL); - void createRPLList1(int numRPL); - const RPLList* getRPLList( bool b ) const { return b==1 ? &m_RPLList1 : &m_RPLList0; } - RPLList* getRPLList( bool b ) { return b==1 ? &m_RPLList1 : &m_RPLList0; } - uint32_t getNumRPL( bool b ) const { return b==1 ? m_numRPL1 : m_numRPL0; } - const RPLList* getRPLList0() const { return &m_RPLList0; } - RPLList* getRPLList0() { return &m_RPLList0; } - const RPLList* getRPLList1() const { return &m_RPLList1; } - RPLList* getRPLList1() { return &m_RPLList1; } - uint32_t getNumRPL0() const { return m_numRPL0; } - uint32_t getNumRPL1() const { return m_numRPL1; } + void createRplList(RefPicList l, int numRPL); + const RPLList *getRplList(RefPicList l) const { return &m_rplList[l]; } + RPLList *getRplList(RefPicList l) { return &m_rplList[l]; } + uint32_t getNumRpl(RefPicList l) const { return m_numRpl[l]; } void setRPL1CopyFromRPL0Flag(bool isCopy) { m_rpl1CopyFromRpl0Flag = isCopy; } bool getRPL1CopyFromRPL0Flag() const { return m_rpl1CopyFromRpl0Flag; } bool getRPL1IdxPresentFlag() const { return m_rpl1IdxPresentFlag; } @@ -2015,8 +2006,7 @@ private: // [cu_chroma_qp_offset_idx+1...] otherwis ChromaQpAdj m_chromaQpAdjTableIncludingNullEntry[1 + MAX_QP_OFFSET_LIST_SIZE]; - uint32_t m_numRefIdxL0DefaultActive; - uint32_t m_numRefIdxL1DefaultActive; + uint32_t m_numRefIdxDefaultActive[NUM_REF_PIC_LIST_01]; bool m_rpl1IdxPresentFlag; @@ -2167,10 +2157,8 @@ public: m_chromaQpOffsetListLen = std::max(m_chromaQpOffsetListLen, cuChromaQpOffsetIdxPlus1); } - void setNumRefIdxL0DefaultActive(uint32_t ui) { m_numRefIdxL0DefaultActive=ui; } - uint32_t getNumRefIdxL0DefaultActive() const { return m_numRefIdxL0DefaultActive; } - void setNumRefIdxL1DefaultActive(uint32_t ui) { m_numRefIdxL1DefaultActive=ui; } - uint32_t getNumRefIdxL1DefaultActive() const { return m_numRefIdxL1DefaultActive; } + void setNumRefIdxDefaultActive(RefPicList l, int n) { m_numRefIdxDefaultActive[l] = n; } + int getNumRefIdxDefaultActive(RefPicList l) const { return m_numRefIdxDefaultActive[l]; } void setRpl1IdxPresentFlag(bool isPresent) { m_rpl1IdxPresentFlag = isPresent; } uint32_t getRpl1IdxPresentFlag() const { return m_rpl1IdxPresentFlag; } @@ -2441,10 +2429,8 @@ private: unsigned m_virtualBoundariesPosX[3]; //!< horizontal virtual boundary positions unsigned m_virtualBoundariesPosY[3]; //!< vertical virtual boundary positions bool m_picOutputFlag; //!< picture output flag - ReferencePictureList m_RPL0; //!< RPL for L0 when present in picture header - ReferencePictureList m_RPL1; //!< RPL for L1 when present in picture header - int m_rpl0Idx; //!< index of used RPL in the SPS or -1 for local RPL in the picture header - int m_rpl1Idx; //!< index of used RPL in the SPS or -1 for local RPL in the picture header + ReferencePictureList m_rpl[NUM_REF_PIC_LIST_01]; + int m_rplIdx[NUM_REF_PIC_LIST_01]; // index of used RPL in the SPS or -1 for local RPL in the picture header bool m_picInterSliceAllowedFlag; //!< inter slice allowed flag in PH bool m_picIntraSliceAllowedFlag; //!< intra slice allowed flag in PH bool m_splitConsOverrideFlag; //!< partitioning constraint override flag @@ -2494,8 +2480,8 @@ private: unsigned m_maxTTSize[3]; //!< maximum TT size RefSetArray<WPScalingParam[MAX_NUM_COMPONENT]> m_weightPredTable; - int m_numL0Weights; //!< number of weights for L0 list - int m_numL1Weights; //!< number of weights for L1 list + + int m_numWeights[NUM_REF_PIC_LIST_01]; // number of weights for each list public: PicHeader(); @@ -2536,15 +2522,9 @@ public: unsigned getVirtualBoundariesPosY(unsigned idx) const { CHECK( idx >= 3, "boundary index exceeds valid range" ); return m_virtualBoundariesPosY[idx];} void setPicOutputFlag( bool b ) { m_picOutputFlag = b; } bool getPicOutputFlag() const { return m_picOutputFlag; } - ReferencePictureList* getRPL( bool b ) { return (b==1) ? getRPL1() : getRPL0(); } - void setRPLIdx( bool b, int rplIdx) { if(b==1) { m_rpl1Idx = rplIdx; } else { m_rpl0Idx = rplIdx; } } - int getRPLIdx( bool b ) const { return b==1 ? m_rpl1Idx : m_rpl0Idx; } - ReferencePictureList* getRPL0() { return &m_RPL0; } - ReferencePictureList* getRPL1() { return &m_RPL1; } - void setRPL0idx(int rplIdx) { m_rpl0Idx = rplIdx; } - void setRPL1idx(int rplIdx) { m_rpl1Idx = rplIdx; } - int getRPL0idx() const { return m_rpl0Idx; } - int getRPL1idx() const { return m_rpl1Idx; } + int getRplIdx(RefPicList l) const { return m_rplIdx[l]; } + ReferencePictureList *getRpl(RefPicList l) { return &m_rpl[l]; } + void setRplIdx(RefPicList l, int rplIdx) { m_rplIdx[l] = rplIdx; } void setPicInterSliceAllowedFlag(bool b) { m_picInterSliceAllowedFlag = b; } bool getPicInterSliceAllowedFlag() const { return m_picInterSliceAllowedFlag; } void setPicIntraSliceAllowedFlag(bool b) { m_picIntraSliceAllowedFlag = b; } @@ -2673,10 +2653,8 @@ public: WPScalingParam * getWpScaling(const RefPicList refPicList, const int refIdx); WPScalingParam* getWpScalingAll() { return (WPScalingParam *) m_weightPredTable; } void resetWpScaling(); - void setNumL0Weights(int b) { m_numL0Weights = b; } - int getNumL0Weights() { return m_numL0Weights; } - void setNumL1Weights(int b) { m_numL1Weights = b; } - int getNumL1Weights() { return m_numL1Weights; } + void setNumWeights(RefPicList l, int n) { m_numWeights[l] = n; } + int getNumWeights(RefPicList l) { return m_numWeights[l]; } void setNoOutputBeforeRecoveryFlag( bool val ) { m_noOutputBeforeRecoveryFlag = val; } bool getNoOutputBeforeRecoveryFlag() const { return m_noOutputBeforeRecoveryFlag; } @@ -2712,10 +2690,8 @@ private: std::vector<int> m_edrapRefRapIds; int m_latestEDRAPPOC; bool m_latestEdrapLeadingPicDecodableFlag; - ReferencePictureList m_RPL0; //< RPL for L0 when present in slice header - ReferencePictureList m_RPL1; //< RPL for L1 when present in slice header - int m_rpl0Idx; //< index of used RPL in the SPS or -1 for local RPL in the slice header - int m_rpl1Idx; //< index of used RPL in the SPS or -1 for local RPL in the slice header + ReferencePictureList m_rpl[NUM_REF_PIC_LIST_01]; + int m_rplIdx[NUM_REF_PIC_LIST_01]; //< index of used RPL in the SPS or -1 for local RPL in the slice header NalUnitType m_eNalUnitType; ///< Nal unit type for the slice bool m_pictureHeaderInSliceHeader; uint32_t m_nuhLayerId; ///< Nal unit layer id @@ -2843,14 +2819,11 @@ public: void setAlfAPSs(APS** apss) { memcpy(m_alfApss, apss, sizeof(m_alfApss)); } APS** getAlfAPSs() { return m_alfApss; } - void setSaoEnabledFlag(const ChannelType chType, bool s) { m_saoEnabledFlag[chType] = s; } - bool getSaoEnabledFlag(const ChannelType chType) const { return m_saoEnabledFlag[chType]; } - ReferencePictureList* getRPL0() { return &m_RPL0; } - ReferencePictureList* getRPL1() { return &m_RPL1; } - void setRPL0idx(int rplIdx) { m_rpl0Idx = rplIdx; } - void setRPL1idx(int rplIdx) { m_rpl1Idx = rplIdx; } - int getRPL0idx() const { return m_rpl0Idx; } - int getRPL1idx() const { return m_rpl1Idx; } + void setSaoEnabledFlag(ChannelType chType, bool s) { m_saoEnabledFlag[chType] = s; } + bool getSaoEnabledFlag(ChannelType chType) const { return m_saoEnabledFlag[chType]; } + ReferencePictureList *getRpl(RefPicList l) { return &m_rpl[l]; } + void setRplIdx(RefPicList l, int rplIdx) { m_rplIdx[l] = rplIdx; } + int getRplIdx(RefPicList l) const { return m_rplIdx[l]; } void setLastIDR(int iIDRPOC) { m_iLastIDR = iIDRPOC; } int getLastIDR() const { return m_iLastIDR; } void setPrevGDRInSameLayerPOC(int prevGDRInSameLayerPOC) { m_prevGDRInSameLayerPOC = prevGDRInSameLayerPOC; } @@ -2919,6 +2892,10 @@ public: // CLVSS PU is either an IRAP PU with NoOutputBeforeRecoveryFlag equal to 1 or a GDR PU with NoOutputBeforeRecoveryFlag equal to 1. bool isClvssPu() const { return m_eNalUnitType >= NAL_UNIT_CODED_SLICE_IDR_W_RADL && m_eNalUnitType <= NAL_UNIT_CODED_SLICE_GDR && !m_pcPPS->getMixedNaluTypesInPicFlag() && m_pcPicHeader->getNoOutputBeforeRecoveryFlag(); } bool isIDRorBLA() const { return (getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_W_RADL) || (getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_N_LP); } + bool isLeadingPic() const + { + return getNalUnitType() == NAL_UNIT_CODED_SLICE_RADL || getNalUnitType() == NAL_UNIT_CODED_SLICE_RASL; + } void checkCRA(const ReferencePictureList* pRPL0, const ReferencePictureList* pRPL1, const int pocCRA, CheckCRAFlags &flags, PicList& rcListPic); void checkSTSA(PicList& rcListPic); void checkRPL(const ReferencePictureList* pRPL0, const ReferencePictureList* pRPL1, const int associatedIRAPDecodingOrderNumber, PicList& rcListPic); diff --git a/source/Lib/DecoderLib/DecLib.cpp b/source/Lib/DecoderLib/DecLib.cpp index 6570c12ec8176673aba8b82cc3cf45594ad578e2..9916396ccf2b19f289fdc964fafdd07a899ef284 100644 --- a/source/Lib/DecoderLib/DecLib.cpp +++ b/source/Lib/DecoderLib/DecLib.cpp @@ -2010,7 +2010,8 @@ void DecLib::xActivateParameterSets( const InputNALUnit nalu ) } #endif - m_apcSlicePilot->applyReferencePictureListBasedMarking( m_cListPic, m_apcSlicePilot->getRPL0(), m_apcSlicePilot->getRPL1(), layerId, *pps); + m_apcSlicePilot->applyReferencePictureListBasedMarking(m_cListPic, m_apcSlicePilot->getRpl(REF_PIC_LIST_0), + m_apcSlicePilot->getRpl(REF_PIC_LIST_1), layerId, *pps); // Get a new picture buffer. This will also set up m_pcPic, and therefore give us a SPS and PPS pointer that we can use. m_pcPic = xGetNewPicBuffer( *sps, *pps, m_apcSlicePilot->getTLayer(), layerId ); @@ -3010,37 +3011,31 @@ bool DecLib::xDecodeSlice(InputNALUnit &nalu, int &iSkipFrame, int iPOCLastDispl { int lostPoc; int refPicIndex; - while ((lostPoc = m_apcSlicePilot->checkThatAllRefPicsAreAvailable(m_cListPic, m_apcSlicePilot->getRPL0(), 0, true, &refPicIndex, m_apcSlicePilot->getNumRefIdx(REF_PIC_LIST_0))) > 0) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if( !pps->getMixedNaluTypesInPicFlag() && ( - ( ( m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_W_RADL || m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_N_LP ) && ( sps->getIDRRefParamListPresent() || pps->getRplInfoInPhFlag() ) ) || - ( ( m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_GDR || m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_CRA ) && m_picHeader.getNoOutputBeforeRecoveryFlag() ) ) ) + const ReferencePictureList *rpl = m_apcSlicePilot->getRpl(l); + + while ((lostPoc = m_apcSlicePilot->checkThatAllRefPicsAreAvailable(m_cListPic, rpl, 0, true, &refPicIndex, + m_apcSlicePilot->getNumRefIdx(l))) + > 0) { - if (m_apcSlicePilot->getRPL0()->isInterLayerRefPic(refPicIndex) == 0) + if (!pps->getMixedNaluTypesInPicFlag() + && ((m_apcSlicePilot->isIDRorBLA() && (sps->getIDRRefParamListPresent() || pps->getRplInfoInPhFlag())) + || ((m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_GDR + || m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_CRA) + && m_picHeader.getNoOutputBeforeRecoveryFlag()))) { - xCreateUnavailablePicture( pps, lostPoc, m_apcSlicePilot->getRPL0()->isRefPicLongterm( refPicIndex ), m_apcSlicePilot->getTLayer(), m_apcSlicePilot->getNalUnitLayerId(), m_apcSlicePilot->getRPL0()->isInterLayerRefPic( refPicIndex ) ); + if (!rpl->isInterLayerRefPic(refPicIndex)) + { + xCreateUnavailablePicture(pps, lostPoc, rpl->isRefPicLongterm(refPicIndex), m_apcSlicePilot->getTLayer(), + m_apcSlicePilot->getNalUnitLayerId(), rpl->isInterLayerRefPic(refPicIndex)); + } } - } - else - { - xCreateLostPicture( lostPoc - 1, m_apcSlicePilot->getPic()->layerId ); - } - } - while ((lostPoc = m_apcSlicePilot->checkThatAllRefPicsAreAvailable(m_cListPic, m_apcSlicePilot->getRPL1(), 0, true, &refPicIndex, m_apcSlicePilot->getNumRefIdx(REF_PIC_LIST_1))) > 0) - { - if( !pps->getMixedNaluTypesInPicFlag() && ( - ( ( m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_W_RADL || m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_N_LP ) && ( sps->getIDRRefParamListPresent() || pps->getRplInfoInPhFlag() ) ) || - ( ( m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_GDR || m_apcSlicePilot->getNalUnitType() == NAL_UNIT_CODED_SLICE_CRA ) && m_picHeader.getNoOutputBeforeRecoveryFlag() ) ) ) - { - if (m_apcSlicePilot->getRPL1()->isInterLayerRefPic(refPicIndex) == 0) + else { - xCreateUnavailablePicture( pps, lostPoc, m_apcSlicePilot->getRPL1()->isRefPicLongterm( refPicIndex ), m_apcSlicePilot->getTLayer(), m_apcSlicePilot->getNalUnitLayerId(), m_apcSlicePilot->getRPL1()->isInterLayerRefPic( refPicIndex ) ); + xCreateLostPicture(lostPoc - 1, m_apcSlicePilot->getPic()->layerId); } } - else - { - xCreateLostPicture( lostPoc - 1, m_apcSlicePilot->getPic()->layerId ); - } } } @@ -3171,13 +3166,16 @@ bool DecLib::xDecodeSlice(InputNALUnit &nalu, int &iSkipFrame, int iPOCLastDispl #endif } pcSlice->getPic()->sliceSubpicIdx.push_back(pps->getSubPicIdxFromSubPicId(pcSlice->getSliceSubPicId())); - pcSlice->checkCRA(pcSlice->getRPL0(), pcSlice->getRPL1(), m_pocCRA[nalu.m_nuhLayerId], m_checkCRAFlags[nalu.m_nuhLayerId], m_cListPic); + pcSlice->checkCRA(pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getRpl(REF_PIC_LIST_1), m_pocCRA[nalu.m_nuhLayerId], + m_checkCRAFlags[nalu.m_nuhLayerId], m_cListPic); pcSlice->constructRefPicList(m_cListPic); pcSlice->setPrevGDRSubpicPOC(m_prevGDRSubpicPOC[nalu.m_nuhLayerId][currSubPicIdx]); pcSlice->setPrevIRAPSubpicPOC(m_prevIRAPSubpicPOC[nalu.m_nuhLayerId][currSubPicIdx]); pcSlice->setPrevIRAPSubpicType(m_prevIRAPSubpicType[nalu.m_nuhLayerId][currSubPicIdx]); - pcSlice->checkSubpicTypeConstraints(m_cListPic, pcSlice->getRPL0(), pcSlice->getRPL1(), m_prevIRAPSubpicDecOrderNo[nalu.m_nuhLayerId][currSubPicIdx]); - pcSlice->checkRPL(pcSlice->getRPL0(), pcSlice->getRPL1(), m_associatedIRAPDecodingOrderNumber[nalu.m_nuhLayerId], m_cListPic); + pcSlice->checkSubpicTypeConstraints(m_cListPic, pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getRpl(REF_PIC_LIST_1), + m_prevIRAPSubpicDecOrderNo[nalu.m_nuhLayerId][currSubPicIdx]); + pcSlice->checkRPL(pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getRpl(REF_PIC_LIST_1), + m_associatedIRAPDecodingOrderNumber[nalu.m_nuhLayerId], m_cListPic); pcSlice->checkSTSA(m_cListPic); if (m_pcPic->cs->vps && !m_pcPic->cs->vps->getIndependentLayerFlag(m_pcPic->cs->vps->getGeneralLayerIdx(nalu.m_nuhLayerId)) && m_pcPic->cs->pps->getNumSubPics() > 1) { diff --git a/source/Lib/DecoderLib/VLCReader.cpp b/source/Lib/DecoderLib/VLCReader.cpp index 555af014c8171b1d47a3ca7a94d1bbbadad13955..266651eac58661c01031c7087f948a843a761012 100644 --- a/source/Lib/DecoderLib/VLCReader.cpp +++ b/source/Lib/DecoderLib/VLCReader.cpp @@ -310,7 +310,7 @@ void HLSyntaxReader::copyRefPicList(SPS* sps, ReferencePictureList* source_rpl, dest_rp->setNumberOfLongtermPictures(0); } - uint32_t numRefPic = dest_rp->getNumberOfShorttermPictures() + dest_rp->getNumberOfLongtermPictures() + dest_rp->getNumberOfInterLayerPictures(); + uint32_t numRefPic = dest_rp->getNumRefEntries(); for( int ii = 0; ii < numRefPic; ii++ ) { @@ -368,10 +368,6 @@ void HLSyntaxReader::parseRefPicList(SPS* sps, ReferencePictureList* rpl, int rp xReadFlag(code, "st_ref_pic_flag[ listIdx ][ rplsIdx ][ i ]"); isLongTerm = (code == 1) ? false : true; } - else - { - isLongTerm = false; - } if (!isLongTerm) { @@ -685,12 +681,12 @@ void HLSyntaxReader::parsePPS( PPS* pcPPS ) xReadUvlc(uiCode, "pps_num_ref_idx_default_active_minus1[0]"); CHECK(uiCode >= MAX_NUM_ACTIVE_REF, "The value of pps_num_ref_idx_default_active_minus1[0] shall be in the range of 0 to 14, inclusive"); - pcPPS->setNumRefIdxL0DefaultActive(uiCode+1); + pcPPS->setNumRefIdxDefaultActive(REF_PIC_LIST_0, uiCode + 1); xReadUvlc(uiCode, "pps_num_ref_idx_default_active_minus1[1]"); CHECK(uiCode >= MAX_NUM_ACTIVE_REF, "The value of pps_num_ref_idx_default_active_minus1[1] shall be in the range of 0 to 14, inclusive"); - pcPPS->setNumRefIdxL1DefaultActive(uiCode+1); + pcPPS->setNumRefIdxDefaultActive(REF_PIC_LIST_1, uiCode + 1); xReadFlag(uiCode, "pps_rpl1_idx_present_flag"); pcPPS->setRpl1IdxPresentFlag(uiCode); @@ -1774,8 +1770,8 @@ void HLSyntaxReader::parseSPS(SPS* pcSPS) //Read candidate for List0 xReadUvlc(uiCode, "sps_num_ref_pic_lists[0]"); uint32_t numberOfRPL = uiCode; - pcSPS->createRPLList0(numberOfRPL); - RPLList* rplList = pcSPS->getRPLList0(); + pcSPS->createRplList(REF_PIC_LIST_0, numberOfRPL); + RPLList *rplList = pcSPS->getRplList(REF_PIC_LIST_0); ReferencePictureList* rpl; for (uint32_t ii = 0; ii < numberOfRPL; ii++) { @@ -1788,8 +1784,8 @@ void HLSyntaxReader::parseSPS(SPS* pcSPS) { xReadUvlc(uiCode, "sps_num_ref_pic_lists[1]"); numberOfRPL = uiCode; - pcSPS->createRPLList1(numberOfRPL); - rplList = pcSPS->getRPLList1(); + pcSPS->createRplList(REF_PIC_LIST_1, numberOfRPL); + rplList = pcSPS->getRplList(REF_PIC_LIST_1); for (uint32_t ii = 0; ii < numberOfRPL; ii++) { rpl = rplList->getReferencePictureList(ii); @@ -1798,10 +1794,10 @@ void HLSyntaxReader::parseSPS(SPS* pcSPS) } else { - numberOfRPL = pcSPS->getNumRPL0(); - pcSPS->createRPLList1(numberOfRPL); - RPLList* rplListSource = pcSPS->getRPLList0(); - RPLList* rplListDest = pcSPS->getRPLList1(); + numberOfRPL = pcSPS->getNumRpl(REF_PIC_LIST_0); + pcSPS->createRplList(REF_PIC_LIST_1, numberOfRPL); + RPLList *rplListSource = pcSPS->getRplList(REF_PIC_LIST_0); + RPLList *rplListDest = pcSPS->getRplList(REF_PIC_LIST_1); for (uint32_t ii = 0; ii < numberOfRPL; ii++) { copyRefPicList(pcSPS, rplListSource->getReferencePictureList(ii), rplListDest->getReferencePictureList(ii)); @@ -2944,74 +2940,67 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag // reference picture lists if (pps->getRplInfoInPhFlag()) { - bool rplSpsFlag0 = 0; + bool rplSpsFlag = false; - // List0 and List1 - for(int listIdx = 0; listIdx < 2; listIdx++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if (sps->getNumRPL(listIdx) > 0 && - (listIdx == 0 || (listIdx == 1 && pps->getRpl1IdxPresentFlag()))) + int numRplsInSps = sps->getNumRpl(l); + if (numRplsInSps == 0) { - xReadFlag(uiCode, "rpl_sps_flag[i]"); + rplSpsFlag = false; } - else if (sps->getNumRPL(listIdx) == 0) + else if (l == REF_PIC_LIST_0 || pps->getRpl1IdxPresentFlag()) { - uiCode = 0; - } - else - { - uiCode = rplSpsFlag0; - } - - if (listIdx == 0) - { - rplSpsFlag0 = uiCode; + xReadFlag(uiCode, "rpl_sps_flag[i]"); + rplSpsFlag = uiCode != 0; } - // explicit RPL in picture header - auto const rpl = picHeader->getRPL( listIdx ); - if (!uiCode) + ReferencePictureList *rpl = picHeader->getRpl(l); + if (!rplSpsFlag) { - (*rpl) = ReferencePictureList(); + // explicit RPL in picture header + *rpl = ReferencePictureList(); parseRefPicList(sps, rpl, -1); - picHeader->setRPLIdx(listIdx, -1); + picHeader->setRplIdx(l, -1); } - // use list from SPS else { - if (sps->getNumRPL(listIdx) > 1 && - (listIdx == 0 || (listIdx == 1 && pps->getRpl1IdxPresentFlag()))) - { - int numBits = ceilLog2(sps->getNumRPL( listIdx )); - xReadCode(numBits, uiCode, "rpl_idx[i]"); - picHeader->setRPLIdx( listIdx, uiCode ); - *rpl = *sps->getRPLList( listIdx )->getReferencePictureList(uiCode); - } - else if (sps->getNumRPL(listIdx) == 1) + // use list from SPS + int rplIdx = 0; + + if (l == REF_PIC_LIST_0 || pps->getRpl1IdxPresentFlag()) { - picHeader->setRPLIdx( listIdx, 0 ); - *rpl = *sps->getRPLList( listIdx )->getReferencePictureList(0); + if (numRplsInSps > 1) + { + int numBits = ceilLog2(numRplsInSps); + xReadCode(numBits, uiCode, "rpl_idx[i]"); + rplIdx = uiCode; + } } else { - CHECK(picHeader->getRPLIdx(0) == -1, "Invalid reference picture index"); - picHeader->setRPLIdx( listIdx, picHeader->getRPLIdx(0)); - *rpl = *sps->getRPLList( listIdx )->getReferencePictureList(picHeader->getRPLIdx( listIdx )); + rplIdx = picHeader->getRplIdx(REF_PIC_LIST_0); + CHECK(rplIdx == -1, "There should be a list 0 RPL"); } + + picHeader->setRplIdx(l, rplIdx); + *rpl = *sps->getRplList(l)->getReferencePictureList(rplIdx); } - if (picHeader->getPicInterSliceAllowedFlag() && listIdx == 0) + if (picHeader->getPicInterSliceAllowedFlag() && l == REF_PIC_LIST_0) { - CHECK(picHeader->getRPL(0)->getNumRefEntries() <= 0, "When pps_rpl_info_in_ph_flag is equal to 1 and ph_inter_slice_allowed_flag is equal to 1, the value of num_ref_entries[ 0 ][ RplsIdx[ 0 ] ] shall be greater than 0"); + CHECK(picHeader->getRpl(REF_PIC_LIST_0)->getNumRefEntries() <= 0, + "When pps_rpl_info_in_ph_flag is equal to 1 and ph_inter_slice_allowed_flag is equal to 1, the value of " + "num_ref_entries[ 0 ][ RplsIdx[ 0 ] ] shall be greater than 0"); } // POC MSB cycle signalling for LTRP - for (int i = 0; i < rpl->getNumberOfLongtermPictures() + rpl->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl->getNumRefEntries(); i++) { rpl->setDeltaPocMSBPresentFlag(i, false); rpl->setDeltaPocMSBCycleLT(i, 0); } if (rpl->getNumberOfLongtermPictures()) { - for (int i = 0; i < rpl->getNumberOfLongtermPictures() + rpl->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl->getNumRefEntries(); i++) { if (rpl->isRefPicLongterm(i)) { @@ -3181,7 +3170,7 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag if (picHeader->getEnableTMVPFlag() && pps->getRplInfoInPhFlag()) { - if (picHeader->getRPL(1)->getNumRefEntries() > 0) + if (picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0) { xReadCode(1, uiCode, "ph_collocated_from_l0_flag"); picHeader->setPicColFromL0Flag(uiCode); @@ -3190,8 +3179,7 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag { picHeader->setPicColFromL0Flag(true); } - if ((picHeader->getPicColFromL0Flag() == 1 && picHeader->getRPL(0)->getNumRefEntries() > 1) || - (picHeader->getPicColFromL0Flag() == 0 && picHeader->getRPL(1)->getNumRefEntries() > 1)) + if (picHeader->getRpl(picHeader->getPicColFromL0Flag() ? REF_PIC_LIST_0 : REF_PIC_LIST_1)->getNumRefEntries() > 1) { xReadUvlc(uiCode, "ph_collocated_ref_idx"); picHeader->setColRefIdx(uiCode); @@ -3230,7 +3218,7 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag } // mvd L1 zero flag - if (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0) + if (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0) { xReadFlag(uiCode, "ph_mvd_l1_zero_flag"); } @@ -3241,7 +3229,8 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag picHeader->setMvdL1ZeroFlag(uiCode != 0); // picture level BDOF disable flags - if (sps->getBdofControlPresentInPhFlag() && (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0)) + if (sps->getBdofControlPresentInPhFlag() + && (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0)) { xReadFlag(uiCode, "ph_bdof_disabled_flag"); picHeader->setBdofDisabledFlag(uiCode != 0); } @@ -3258,7 +3247,8 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag } // picture level DMVR disable flags - if (sps->getDmvrControlPresentInPhFlag() && (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0)) + if (sps->getDmvrControlPresentInPhFlag() + && (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0)) { xReadFlag(uiCode, "ph_dmvr_disabled_flag"); picHeader->setDmvrDisabledFlag(uiCode != 0); } @@ -3842,63 +3832,56 @@ void HLSyntaxReader::parseSliceHeader (Slice* pcSlice, PicHeader* picHeader, Par if (pps->getRplInfoInPhFlag()) { - *pcSlice->getRPL0() = *picHeader->getRPL0(); - *pcSlice->getRPL1() = *picHeader->getRPL1(); + *pcSlice->getRpl(REF_PIC_LIST_0) = *picHeader->getRpl(REF_PIC_LIST_0); + *pcSlice->getRpl(REF_PIC_LIST_1) = *picHeader->getRpl(REF_PIC_LIST_1); } else if (pcSlice->getIdrPicFlag() && !(sps->getIDRRefParamListPresent())) { - ReferencePictureList *rpl0 = pcSlice->getRPL0(); + ReferencePictureList *rpl0 = pcSlice->getRpl(REF_PIC_LIST_0); (*rpl0) = ReferencePictureList(); - ReferencePictureList *rpl1 = pcSlice->getRPL1(); + ReferencePictureList *rpl1 = pcSlice->getRpl(REF_PIC_LIST_1); (*rpl1) = ReferencePictureList(); } else { // Read L0 related syntax elements - bool rplSpsFlag0 = 0; + bool rplSpsFlag0 = false; - if (sps->getNumRPL0() > 0) + if (sps->getNumRpl(REF_PIC_LIST_0) > 0) { xReadFlag(uiCode, "ref_pic_list_sps_flag[0]"); - } - else - { - uiCode = 0; + rplSpsFlag0 = uiCode != 0; } - rplSpsFlag0 = uiCode; - - auto const rpl0 = pcSlice->getRPL0(); - if (!uiCode) // explicitly carried in this SH + auto const rpl0 = pcSlice->getRpl(REF_PIC_LIST_0); + if (!rplSpsFlag0) // explicitly carried in this SH { - (*rpl0) = ReferencePictureList(); + *rpl0 = ReferencePictureList(); parseRefPicList(sps, rpl0, -1); - pcSlice->setRPL0idx(-1); + pcSlice->setRplIdx(REF_PIC_LIST_0, -1); } else // Refer to list in SPS { - if (sps->getNumRPL0() > 1) + int rpsIdx = 0; + if (sps->getNumRpl(REF_PIC_LIST_0) > 1) { - int numBits = ceilLog2(sps->getNumRPL0()); + int numBits = ceilLog2(sps->getNumRpl(REF_PIC_LIST_0)); xReadCode(numBits, uiCode, "ref_pic_list_idx[0]"); - pcSlice->setRPL0idx(uiCode); - *rpl0 = *sps->getRPLList0()->getReferencePictureList(uiCode); - } - else - { - pcSlice->setRPL0idx(0); - *rpl0 = *sps->getRPLList0()->getReferencePictureList(0); + rpsIdx = uiCode; } + + pcSlice->setRplIdx(REF_PIC_LIST_0, rpsIdx); + *rpl0 = *sps->getRplList(REF_PIC_LIST_0)->getReferencePictureList(rpsIdx); } // Deal POC Msb cycle signalling for LTRP - for (int i = 0; i < rpl0->getNumberOfLongtermPictures() + rpl0->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl0->getNumRefEntries(); i++) { rpl0->setDeltaPocMSBPresentFlag(i, false); rpl0->setDeltaPocMSBCycleLT(i, 0); } if (rpl0->getNumberOfLongtermPictures()) { - for (int i = 0; i < rpl0->getNumberOfLongtermPictures() + rpl0->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl0->getNumRefEntries(); i++) { if (rpl0->isRefPicLongterm(i)) { @@ -3939,57 +3922,51 @@ void HLSyntaxReader::parseSliceHeader (Slice* pcSlice, PicHeader* picHeader, Par } // Read L1 related syntax elements - if (sps->getNumRPL(1) > 0 && pps->getRpl1IdxPresentFlag()) + bool rplSpsFlag1 = sps->getNumRpl(REF_PIC_LIST_1) == 0 ? false : rplSpsFlag0; + if (sps->getNumRpl(REF_PIC_LIST_1) > 0 && pps->getRpl1IdxPresentFlag()) { xReadFlag(uiCode, "ref_pic_list_sps_flag[1]"); - } - else if (sps->getNumRPL(1) == 0) - { - uiCode = 0; - } - else - { - uiCode = rplSpsFlag0; + rplSpsFlag1 = uiCode != 0; } - auto const rpl1 = pcSlice->getRPL1(); - if (uiCode == 1) + auto const rpl1 = pcSlice->getRpl(REF_PIC_LIST_1); + if (rplSpsFlag1) { - if (sps->getNumRPL(1) > 1 && pps->getRpl1IdxPresentFlag()) + if (sps->getNumRpl(REF_PIC_LIST_1) > 1 && pps->getRpl1IdxPresentFlag()) { - int numBits = ceilLog2(sps->getNumRPL1()); + int numBits = ceilLog2(sps->getNumRpl(REF_PIC_LIST_1)); xReadCode(numBits, uiCode, "ref_pic_list_idx[1]"); - pcSlice->setRPL1idx(uiCode); - *rpl1 = *sps->getRPLList1()->getReferencePictureList(uiCode); + pcSlice->setRplIdx(REF_PIC_LIST_1, uiCode); + *rpl1 = *sps->getRplList(REF_PIC_LIST_1)->getReferencePictureList(uiCode); } - else if (sps->getNumRPL(1) == 1) + else if (sps->getNumRpl(REF_PIC_LIST_1) == 1) { - pcSlice->setRPL1idx(0); - *rpl1 = *sps->getRPLList1()->getReferencePictureList(0); + pcSlice->setRplIdx(REF_PIC_LIST_1, 0); + *rpl1 = *sps->getRplList(REF_PIC_LIST_1)->getReferencePictureList(0); } else { - CHECK(pcSlice->getRPL0idx() == -1, "Invalid reference picture index"); - pcSlice->setRPL1idx(pcSlice->getRPL0idx()); - *rpl1 = *sps->getRPLList1()->getReferencePictureList(pcSlice->getRPL0idx()); + assert(pcSlice->getRplIdx(REF_PIC_LIST_0) != -1); + pcSlice->setRplIdx(REF_PIC_LIST_1, pcSlice->getRplIdx(REF_PIC_LIST_0)); + *rpl1 = *sps->getRplList(REF_PIC_LIST_1)->getReferencePictureList(pcSlice->getRplIdx(REF_PIC_LIST_0)); } } else { (*rpl1) = ReferencePictureList(); parseRefPicList(sps, rpl1, -1); - pcSlice->setRPL1idx(-1); + pcSlice->setRplIdx(REF_PIC_LIST_1, -1); } // Deal POC Msb cycle signalling for LTRP - for (int i = 0; i < rpl1->getNumberOfLongtermPictures() + rpl1->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl1->getNumRefEntries(); i++) { rpl1->setDeltaPocMSBPresentFlag(i, false); rpl1->setDeltaPocMSBCycleLT(i, 0); } if (rpl1->getNumberOfLongtermPictures()) { - for (int i = 0; i < rpl1->getNumberOfLongtermPictures() + rpl1->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl1->getNumRefEntries(); i++) { if (rpl1->isRefPicLongterm(i)) { @@ -4032,20 +4009,20 @@ void HLSyntaxReader::parseSliceHeader (Slice* pcSlice, PicHeader* picHeader, Par uint32_t numActiveRefs[NUM_REF_PIC_LIST_01] = { pcSlice->isIntra() ? 0u : 1u, pcSlice->isInterB() ? 1u : 0u }; - if ((!pcSlice->isIntra() && pcSlice->getRPL0()->getNumRefEntries() > 1) - || (pcSlice->isInterB() && pcSlice->getRPL1()->getNumRefEntries() > 1)) + if ((!pcSlice->isIntra() && pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries() > 1) + || (pcSlice->isInterB() && pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 1)) { xReadFlag(uiCode, "sh_num_ref_idx_active_override_flag"); if (uiCode) { - if (pcSlice->getRPL0()->getNumRefEntries() > 1) + if (pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries() > 1) { xReadUvlc(uiCode, "sh_num_ref_idx_active_minus1[0]"); CHECK(uiCode >= MAX_NUM_ACTIVE_REF, "The value of sh_num_ref_idx_active_minus1[0] shall be in the range of 0 to 14, inclusive"); numActiveRefs[REF_PIC_LIST_0] = uiCode + 1; } - if (pcSlice->isInterB() && pcSlice->getRPL1()->getNumRefEntries() > 1) + if (pcSlice->isInterB() && pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 1) { xReadUvlc(uiCode, "sh_num_ref_idx_active_minus1[1]"); CHECK(uiCode >= MAX_NUM_ACTIVE_REF, @@ -4055,13 +4032,13 @@ void HLSyntaxReader::parseSliceHeader (Slice* pcSlice, PicHeader* picHeader, Par } else { - numActiveRefs[REF_PIC_LIST_0] = - std::min<int>(pcSlice->getRPL0()->getNumRefEntries(), pps->getNumRefIdxL0DefaultActive()); + numActiveRefs[REF_PIC_LIST_0] = std::min<int>(pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries(), + pps->getNumRefIdxDefaultActive(REF_PIC_LIST_0)); if (pcSlice->isInterB()) { - numActiveRefs[REF_PIC_LIST_1] = - std::min<int>(pcSlice->getRPL1()->getNumRefEntries(), pps->getNumRefIdxL1DefaultActive()); + numActiveRefs[REF_PIC_LIST_1] = std::min<int>(pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries(), + pps->getNumRefIdxDefaultActive(REF_PIC_LIST_1)); } } } @@ -4130,10 +4107,10 @@ void HLSyntaxReader::parseSliceHeader (Slice* pcSlice, PicHeader* picHeader, Par { if (pps->getWpInfoInPhFlag()) { - CHECK(pcSlice->getNumRefIdx(REF_PIC_LIST_0) > picHeader->getNumL0Weights(), + CHECK(pcSlice->getNumRefIdx(REF_PIC_LIST_0) > picHeader->getNumWeights(REF_PIC_LIST_0), "ERROR: Number of active reference picture L0 is greater than the number of weighted prediction signalled " "in Picture Header"); - CHECK(pcSlice->getNumRefIdx(REF_PIC_LIST_1) > picHeader->getNumL1Weights(), + CHECK(pcSlice->getNumRefIdx(REF_PIC_LIST_1) > picHeader->getNumWeights(REF_PIC_LIST_1), "ERROR: Number of active reference picture L1 is greater than the number of weighted prediction signalled " "in Picture Header"); pcSlice->setWpScaling(picHeader->getWpScalingAll()); @@ -4774,8 +4751,6 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) const ChromaFormat chFmt = sps->getChromaFormatIdc(); const int numValidComp = int(getNumberValidComponents(chFmt)); const bool hasChroma = (chFmt != CHROMA_400); - const SliceType eSliceType = pcSlice->getSliceType(); - const int numLists = (eSliceType == B_SLICE) ? 2 : 1; uint32_t log2WeightDenomLuma = 0; uint32_t log2WeightDenomChroma = 0; @@ -4795,12 +4770,18 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) log2WeightDenomChroma = (uint32_t) (deltaDenom + log2WeightDenomLuma); } - for (int listIdx = 0; listIdx < numLists; listIdx++) // loop over l0 and l1 syntax elements + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - RefPicList eRefPicList = listIdx ? REF_PIC_LIST_1 : REF_PIC_LIST_0; - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) + const bool l0 = l == REF_PIC_LIST_0; + + if (!l0 && !pcSlice->isInterB()) { - WPScalingParam *wp = pcSlice->getWpScaling(eRefPicList, refIdx); + continue; + } + + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) + { + WPScalingParam *wp = pcSlice->getWpScaling(l, refIdx); wp[COMPONENT_Y].log2WeightDenom = log2WeightDenomLuma; for(int j=1; j<numValidComp; j++) @@ -4809,54 +4790,54 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) } uint32_t uiCode; - xReadFlag(uiCode, listIdx == 0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]"); - wp[COMPONENT_Y].presentFlag = (uiCode == 1); - totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag; + xReadFlag(uiCode, (l0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]")); + wp[COMPONENT_Y].presentFlag = uiCode != 0; + totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag ? 1 : 0; } if (hasChroma) { - uint32_t uiCode; - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) { - WPScalingParam *wp = pcSlice->getWpScaling(eRefPicList, refIdx); - xReadFlag(uiCode, listIdx == 0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]"); + WPScalingParam *wp = pcSlice->getWpScaling(l, refIdx); + uint32_t uiCode; + xReadFlag(uiCode, (l0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]")); for(int j=1; j<numValidComp; j++) { - wp[j].presentFlag = (uiCode == 1); + wp[j].presentFlag = uiCode != 0; + totalSignalledWeightFlags += wp[COMPONENT_Cb].presentFlag ? 1 : 0; } - totalSignalledWeightFlags += 2 * wp[COMPONENT_Cb].presentFlag; } } else { for (int refIdx = 0; refIdx < MAX_NUM_REF; refIdx++) { - WPScalingParam *wp = pcSlice->getWpScaling(eRefPicList, refIdx); + WPScalingParam *wp = pcSlice->getWpScaling(l, refIdx); wp[COMPONENT_Cb].presentFlag = false; wp[COMPONENT_Cr].presentFlag = false; } } - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) { - WPScalingParam *wp = pcSlice->getWpScaling(eRefPicList, refIdx); + WPScalingParam *wp = pcSlice->getWpScaling(l, refIdx); if (wp[COMPONENT_Y].presentFlag) { int deltaWeight; - xReadSvlc(deltaWeight, listIdx == 0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]"); + xReadSvlc(deltaWeight, (l0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]")); CHECK(deltaWeight < -128, "delta_luma_weight_lx shall be in the rage of -128 to 127"); CHECK(deltaWeight > 127, "delta_luma_weight_lx shall be in the rage of -128 to 127"); wp[COMPONENT_Y].codedWeight = (deltaWeight + (1 << wp[COMPONENT_Y].log2WeightDenom)); - xReadSvlc(wp[COMPONENT_Y].codedOffset, listIdx == 0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]"); + xReadSvlc(wp[COMPONENT_Y].codedOffset, (l0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]")); const int range = sps->getSpsRangeExtension().getHighPrecisionOffsetsEnabledFlag() ? (1 << sps->getBitDepth(ChannelType::LUMA)) / 2 : 128; - CHECK(wp[0].codedOffset < -range, "luma_offset_lx shall be in the rage of -128 to 127"); - CHECK(wp[0].codedOffset >= range, "luma_offset_lx shall be in the rage of -128 to 127"); + CHECK(wp[COMPONENT_Y].codedOffset < -range, "luma_offset_lx shall be in the rage of -128 to 127"); + CHECK(wp[COMPONENT_Y].codedOffset >= range, "luma_offset_lx shall be in the rage of -128 to 127"); } else { - wp[COMPONENT_Y].codedWeight = (1 << wp[COMPONENT_Y].log2WeightDenom); + wp[COMPONENT_Y].codedWeight = 1 << wp[COMPONENT_Y].log2WeightDenom; wp[COMPONENT_Y].codedOffset = 0; } if (hasChroma) @@ -4869,13 +4850,13 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) for ( int j=1 ; j<numValidComp ; j++ ) { int deltaWeight; - xReadSvlc(deltaWeight, listIdx == 0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]"); + xReadSvlc(deltaWeight, (l0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]")); CHECK(deltaWeight < -128, "delta_chroma_weight_lx shall be in the rage of -128 to 127"); CHECK(deltaWeight > 127, "delta_chroma_weight_lx shall be in the rage of -128 to 127"); wp[j].codedWeight = (deltaWeight + (1 << wp[j].log2WeightDenom)); int deltaChroma; - xReadSvlc(deltaChroma, listIdx == 0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]"); + xReadSvlc(deltaChroma, (l0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]")); CHECK(deltaChroma < -4 * range, "delta_chroma_offset_lx shall be in the range of -4 * 128 to 4 * 127"); CHECK(deltaChroma > 4 * (range - 1), "delta_chroma_offset_lx shall be in the range of -4 * 128 to 4 * 127"); int pred = (range - ((range * wp[j].codedWeight) >> (wp[j].log2WeightDenom))); @@ -4886,16 +4867,16 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) { for ( int j=1 ; j<numValidComp ; j++ ) { - wp[j].codedWeight = (1 << wp[j].log2WeightDenom); + wp[j].codedWeight = 1 << wp[j].log2WeightDenom; wp[j].codedOffset = 0; } } } } - for (int refIdx = pcSlice->getNumRefIdx(eRefPicList); refIdx < MAX_NUM_REF; refIdx++) + for (int refIdx = pcSlice->getNumRefIdx(l); refIdx < MAX_NUM_REF; refIdx++) { - WPScalingParam *wp = pcSlice->getWpScaling(eRefPicList, refIdx); + WPScalingParam *wp = pcSlice->getWpScaling(l, refIdx); wp[COMPONENT_Y].presentFlag = false; wp[COMPONENT_Cb].presentFlag = false; @@ -4907,37 +4888,40 @@ void HLSyntaxReader::parsePredWeightTable( Slice* pcSlice, const SPS *sps ) void HLSyntaxReader::parsePredWeightTable(PicHeader *picHeader, const PPS *pps, const SPS *sps) { - WPScalingParam * wp; - const ChromaFormat chFmt = sps->getChromaFormatIdc(); - const int numValidComp = int(getNumberValidComponents(chFmt)); - const bool chroma = (chFmt != CHROMA_400); - uint32_t log2WeightDenomLuma = 0; - uint32_t log2WeightDenomChroma = 0; - uint32_t totalSignalledWeightFlags = 0; + const ChromaFormat chFmt = sps->getChromaFormatIdc(); + const int numValidComp = getNumberValidComponents(chFmt); + const bool chroma = isChromaEnabled(chFmt); - int deltaDenom; + uint32_t log2WeightDenomLuma = 0; + uint32_t log2WeightDenomChroma = 0; + uint32_t totalSignalledWeightFlags = 0; xReadUvlc(log2WeightDenomLuma, "luma_log2_weight_denom"); CHECK(log2WeightDenomLuma > 7, "The value of luma_log2_weight_denom shall be in the range of 0 to 7"); if (chroma) { + int deltaDenom; xReadSvlc(deltaDenom, "delta_chroma_log2_weight_denom"); - CHECK((deltaDenom + (int) log2WeightDenomLuma) < 0, "luma_log2_weight_denom + delta_chroma_log2_weight_denom shall be in the range of 0 to 7"); - CHECK((deltaDenom + (int) log2WeightDenomLuma) > 7, "luma_log2_weight_denom + delta_chroma_log2_weight_denom shall be in the range of 0 to 7"); - log2WeightDenomChroma = (uint32_t)(deltaDenom + log2WeightDenomLuma); + log2WeightDenomChroma = deltaDenom + log2WeightDenomLuma; + CHECK(log2WeightDenomChroma > 7, + "luma_log2_weight_denom + delta_chroma_log2_weight_denom shall be in the range of 0 to 7"); } - uint32_t numLxWeights; - xReadUvlc(numLxWeights, "num_l0_weights"); - picHeader->setNumL0Weights(numLxWeights); - picHeader->setNumL1Weights(0); - - bool moreSyntaxToBeParsed = true; - for (int numRef = 0; numRef < NUM_REF_PIC_LIST_01 && moreSyntaxToBeParsed; numRef++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - RefPicList refPicList = (numRef ? REF_PIC_LIST_1 : REF_PIC_LIST_0); + const bool l0 = l == REF_PIC_LIST_0; + + WPScalingParam *wp; + + uint32_t numLxWeights = 0; + if (l0 || (pps->getWPBiPred() && picHeader->getRpl(l)->getNumRefEntries() > 0)) + { + xReadUvlc(numLxWeights, (l0 ? "num_l0_weights" : "num_l1_weights")); + } + picHeader->setNumWeights(l, numLxWeights); + for (int refIdx = 0; refIdx < numLxWeights; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); + wp = picHeader->getWpScaling(l, refIdx); wp[COMPONENT_Y].log2WeightDenom = log2WeightDenomLuma; for (int j = 1; j < numValidComp; j++) @@ -4946,44 +4930,45 @@ void HLSyntaxReader::parsePredWeightTable(PicHeader *picHeader, const PPS *pps, } uint32_t uiCode; - xReadFlag(uiCode, numRef == 0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]"); - wp[COMPONENT_Y].presentFlag = (uiCode == 1); - totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag; + xReadFlag(uiCode, (l0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]")); + wp[COMPONENT_Y].presentFlag = uiCode != 0; + totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag ? 1 : 0; } if (chroma) { uint32_t uiCode; for (int refIdx = 0; refIdx < numLxWeights; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); - xReadFlag(uiCode, numRef == 0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]"); + wp = picHeader->getWpScaling(l, refIdx); + xReadFlag(uiCode, (l0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]")); for (int j = 1; j < numValidComp; j++) { - wp[j].presentFlag = (uiCode == 1); + wp[j].presentFlag = uiCode != 0; + totalSignalledWeightFlags += wp[COMPONENT_Cb].presentFlag ? 1 : 0; } - totalSignalledWeightFlags += 2 * wp[COMPONENT_Cb].presentFlag; } } else { for ( int refIdx=0; refIdx<MAX_NUM_REF; refIdx++ ) { - wp = picHeader->getWpScaling(refPicList, refIdx); + wp = picHeader->getWpScaling(l, refIdx); + wp[1].presentFlag = false; wp[2].presentFlag = false; } } for (int refIdx = 0; refIdx < numLxWeights; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); + wp = picHeader->getWpScaling(l, refIdx); if (wp[COMPONENT_Y].presentFlag) { int deltaWeight; - xReadSvlc(deltaWeight, numRef == 0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]"); + xReadSvlc(deltaWeight, (l0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]")); CHECK(deltaWeight < -128, "delta_luma_weight_lx shall be in the rage of -128 to 127"); CHECK(deltaWeight > 127, "delta_luma_weight_lx shall be in the rage of -128 to 127"); wp[COMPONENT_Y].codedWeight = (deltaWeight + (1 << wp[COMPONENT_Y].log2WeightDenom)); - xReadSvlc(wp[COMPONENT_Y].codedOffset, numRef == 0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]"); + xReadSvlc(wp[COMPONENT_Y].codedOffset, (l0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]")); const int range = sps->getSpsRangeExtension().getHighPrecisionOffsetsEnabledFlag() ? (1 << sps->getBitDepth(ChannelType::LUMA)) / 2 : 128; @@ -5005,13 +4990,13 @@ void HLSyntaxReader::parsePredWeightTable(PicHeader *picHeader, const PPS *pps, for (int j = 1; j < numValidComp; j++) { int deltaWeight; - xReadSvlc(deltaWeight, numRef == 0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]"); + xReadSvlc(deltaWeight, (l0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]")); CHECK( deltaWeight < -128, "delta_chroma_weight_lx shall be in the rage of -128 to 127" ); CHECK( deltaWeight > 127, "delta_chroma_weight_lx shall be in the rage of -128 to 127" ); wp[j].codedWeight = (deltaWeight + (1 << wp[j].log2WeightDenom)); int deltaChroma; - xReadSvlc(deltaChroma, numRef == 0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]"); + xReadSvlc(deltaChroma, (l0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]")); CHECK( deltaChroma < -4*range, "delta_chroma_offset_lx shall be in the range of -4 * 128 to 4 * 127" ); CHECK( deltaChroma >= 4*range, "delta_chroma_offset_lx shall be in the range of -4 * 128 to 4 * 127" ); int pred = (range - ((range * wp[j].codedWeight) >> (wp[j].log2WeightDenom))); @@ -5031,25 +5016,11 @@ void HLSyntaxReader::parsePredWeightTable(PicHeader *picHeader, const PPS *pps, for (int refIdx = numLxWeights; refIdx < MAX_NUM_REF; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); - - wp[0].presentFlag = false; - wp[1].presentFlag = false; - wp[2].presentFlag = false; - } + wp = picHeader->getWpScaling(l, refIdx); - if (numRef == 0) - { - if (pps->getWPBiPred() && picHeader->getRPL(1)->getNumRefEntries() > 0) - { - xReadUvlc(numLxWeights, "num_l1_weights"); - } - else - { - numLxWeights = 0; - } - moreSyntaxToBeParsed = (numLxWeights == 0) ? false : true; - picHeader->setNumL1Weights(numLxWeights); + wp[COMPONENT_Y].presentFlag = false; + wp[COMPONENT_Cb].presentFlag = false; + wp[COMPONENT_Cr].presentFlag = false; } } CHECK(totalSignalledWeightFlags > 24, "Too many weight flag signalled"); diff --git a/source/Lib/EncoderLib/EncGOP.cpp b/source/Lib/EncoderLib/EncGOP.cpp index b0d105531225b44d5efc6a955a6b753f2b00ad4a..fbf02e705bf8c5ce8c9d673e6bad8baf87db873d 100644 --- a/source/Lib/EncoderLib/EncGOP.cpp +++ b/source/Lib/EncoderLib/EncGOP.cpp @@ -2637,73 +2637,65 @@ void EncGOP::compressGOP(int pocLast, int numPicRcvd, PicList &rcListPic, std::l } } - if (pcSlice->checkThatAllRefPicsAreAvailable(rcListPic, pcSlice->getRPL0(), 0, false) != 0 || pcSlice->checkThatAllRefPicsAreAvailable(rcListPic, pcSlice->getRPL1(), 1, false) != 0 || - (m_pcEncLib->getDependentRAPIndicationSEIEnabled() && !pcSlice->isIRAP() && ( pcSlice->isDRAP() || !pcSlice->isPOCInRefPicList(pcSlice->getRPL0(), pcSlice->getAssociatedIRAPPOC())) ) || - (m_pcEncLib->getEdrapIndicationSEIEnabled() && !pcSlice->isIRAP() && ( pcSlice->getEdrapRapId() > 0 || !pcSlice->isPOCInRefPicList(pcSlice->getRPL0(), pcSlice->getAssociatedIRAPPOC()) ) ) - || (((pcSlice->isIRAP() && m_pcEncLib->getAvoidIntraInDepLayer()) || (!pcSlice->isIRAP() && m_pcEncLib->getRplOfDepLayerInSh())) && pcSlice->getPic()->cs->vps && m_pcEncLib->getNumRefLayers(pcSlice->getPic()->cs->vps->getGeneralLayerIdx(m_pcEncLib->getLayerId()))) - ) + if (pcSlice->checkThatAllRefPicsAreAvailable(rcListPic, pcSlice->getRpl(REF_PIC_LIST_0), 0, false) != 0 + || pcSlice->checkThatAllRefPicsAreAvailable(rcListPic, pcSlice->getRpl(REF_PIC_LIST_1), 1, false) != 0 + || (m_pcEncLib->getDependentRAPIndicationSEIEnabled() && !pcSlice->isIRAP() + && (pcSlice->isDRAP() + || !pcSlice->isPOCInRefPicList(pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getAssociatedIRAPPOC()))) + || (m_pcEncLib->getEdrapIndicationSEIEnabled() && !pcSlice->isIRAP() + && (pcSlice->getEdrapRapId() > 0 + || !pcSlice->isPOCInRefPicList(pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getAssociatedIRAPPOC()))) + || (((pcSlice->isIRAP() && m_pcEncLib->getAvoidIntraInDepLayer()) + || (!pcSlice->isIRAP() && m_pcEncLib->getRplOfDepLayerInSh())) + && pcSlice->getPic()->cs->vps + && m_pcEncLib->getNumRefLayers(pcSlice->getPic()->cs->vps->getGeneralLayerIdx(m_pcEncLib->getLayerId())))) { - xCreateExplicitReferencePictureSetFromReference( pcSlice, rcListPic, pcSlice->getRPL0(), pcSlice->getRPL1() ); + xCreateExplicitReferencePictureSetFromReference(pcSlice, rcListPic, pcSlice->getRpl(REF_PIC_LIST_0), + pcSlice->getRpl(REF_PIC_LIST_1)); } - pcSlice->applyReferencePictureListBasedMarking( rcListPic, pcSlice->getRPL0(), pcSlice->getRPL1(), pcSlice->getPic()->layerId, *(pcSlice->getPPS())); + pcSlice->applyReferencePictureListBasedMarking(rcListPic, pcSlice->getRpl(REF_PIC_LIST_0), + pcSlice->getRpl(REF_PIC_LIST_1), pcSlice->getPic()->layerId, + *(pcSlice->getPPS())); - if(pcSlice->getTLayer() > 0 - && !(pcSlice->getNalUnitType() == NAL_UNIT_CODED_SLICE_RADL // Check if not a leading picture - || pcSlice->getNalUnitType() == NAL_UNIT_CODED_SLICE_RASL) - ) + if (pcSlice->getTLayer() > 0 && !pcSlice->isLeadingPic()) { if (pcSlice->isStepwiseTemporalLayerSwitchingPointCandidate(rcListPic)) { bool isSTSA=true; - for(int ii=0;(ii<m_pcCfg->getGOPSize() && isSTSA==true);ii++) + for (int ii = 0; ii < m_pcCfg->getGOPSize() && isSTSA; ii++) { int lTid = m_pcCfg->getRPLEntry(0, ii).m_temporalId; if (lTid == pcSlice->getTLayer()) { - const ReferencePictureList* rpl0 = m_pcEncLib->getRplOfDepLayerInSh()? m_pcEncLib->getRPLList(0)->getReferencePictureList(ii): pcSlice->getSPS()->getRPLList0()->getReferencePictureList(ii); - for (int jj = 0; jj < pcSlice->getRPL0()->getNumberOfActivePictures(); jj++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - int tPoc = pcSlice->getPOC() + rpl0->getRefPicIdentifier(jj); - int kk = 0; - for (kk = 0; kk<m_pcCfg->getGOPSize(); kk++) + const ReferencePictureList *rpl = m_pcEncLib->getRplOfDepLayerInSh() + ? m_pcEncLib->getRplList(l)->getReferencePictureList(ii) + : pcSlice->getSPS()->getRplList(l)->getReferencePictureList(ii); + for (int jj = 0; jj < pcSlice->getRpl(l)->getNumberOfActivePictures(); jj++) { - if (m_pcCfg->getRPLEntry(0, kk).m_POC == tPoc) + // What about long-term and inter-layer? + int tPoc = pcSlice->getPOC() + rpl->getRefPicIdentifier(jj); + for (int kk = 0; kk < m_pcCfg->getGOPSize(); kk++) { - break; - } - } - int tTid = m_pcCfg->getRPLEntry(0, kk).m_temporalId; - if (tTid >= pcSlice->getTLayer()) - { - isSTSA = false; - break; - } - } - const ReferencePictureList* rpl1 = m_pcEncLib->getRplOfDepLayerInSh()? m_pcEncLib->getRPLList(1)->getReferencePictureList(ii): pcSlice->getSPS()->getRPLList1()->getReferencePictureList(ii); - for (int jj = 0; jj < pcSlice->getRPL1()->getNumberOfActivePictures(); jj++) - { - int tPoc = pcSlice->getPOC() + rpl1->getRefPicIdentifier(jj); - int kk = 0; - for (kk = 0; kk<m_pcCfg->getGOPSize(); kk++) - { - if (m_pcCfg->getRPLEntry(1, kk).m_POC == tPoc) - { - break; + if (m_pcCfg->getRPLEntry(0, kk).m_POC == tPoc) + { + int tTid = m_pcCfg->getRPLEntry(0, kk).m_temporalId; + if (tTid >= pcSlice->getTLayer()) + { + isSTSA = false; + break; + } + } } } - int tTid = m_pcCfg->getRPLEntry(1, kk).m_temporalId; - if (tTid >= pcSlice->getTLayer()) - { - isSTSA = false; - break; - } } } } - if(isSTSA==true) + if (isSTSA) { pcSlice->setNalUnitType(NAL_UNIT_CODED_SLICE_STSA); } @@ -2715,16 +2707,18 @@ void EncGOP::compressGOP(int pocLast, int numPicRcvd, PicList &rcListPic, std::l pcSlice->setNumRefIdx(REF_PIC_LIST_0, (pcSlice->isIntra()) ? 0 : min(m_pcCfg->getRPLEntry(0, gopId).m_numRefPicsActive + 1, - pcSlice->getRPL0()->getNumberOfActivePictures())); + pcSlice->getRpl(REF_PIC_LIST_0)->getNumberOfActivePictures())); pcSlice->setNumRefIdx(REF_PIC_LIST_1, (!pcSlice->isInterB()) ? 0 : min(m_pcCfg->getRPLEntry(1, gopId).m_numRefPicsActive + 1, - pcSlice->getRPL1()->getNumberOfActivePictures())); + pcSlice->getRpl(REF_PIC_LIST_1)->getNumberOfActivePictures())); } else { - pcSlice->setNumRefIdx(REF_PIC_LIST_0, (pcSlice->isIntra()) ? 0 : pcSlice->getRPL0()->getNumberOfActivePictures()); - pcSlice->setNumRefIdx(REF_PIC_LIST_1, (!pcSlice->isInterB()) ? 0 : pcSlice->getRPL1()->getNumberOfActivePictures()); + pcSlice->setNumRefIdx(REF_PIC_LIST_0, + (pcSlice->isIntra()) ? 0 : pcSlice->getRpl(REF_PIC_LIST_0)->getNumberOfActivePictures()); + pcSlice->setNumRefIdx(REF_PIC_LIST_1, + (!pcSlice->isInterB()) ? 0 : pcSlice->getRpl(REF_PIC_LIST_1)->getNumberOfActivePictures()); } if (m_pcCfg->getUseCompositeRef() && getPrepareLTRef()) { @@ -3938,10 +3932,10 @@ void EncGOP::compressGOP(int pocLast, int numPicRcvd, PicList &rcListPic, std::l } m_pcSliceEncoder->setSliceSegmentIdx(sliceSegmentIdxCount); - *pcSlice->getRPL0() = *pcPic->slices[0]->getRPL0(); - *pcSlice->getRPL1() = *pcPic->slices[0]->getRPL1(); - pcSlice->setRPL0idx(pcPic->slices[0]->getRPL0idx()); - pcSlice->setRPL1idx(pcPic->slices[0]->getRPL1idx()); + *pcSlice->getRpl(REF_PIC_LIST_0) = *pcPic->slices[0]->getRpl(REF_PIC_LIST_0); + *pcSlice->getRpl(REF_PIC_LIST_1) = *pcPic->slices[0]->getRpl(REF_PIC_LIST_1); + pcSlice->setRplIdx(REF_PIC_LIST_0, pcPic->slices[0]->getRplIdx(REF_PIC_LIST_0)); + pcSlice->setRplIdx(REF_PIC_LIST_1, pcPic->slices[0]->getRplIdx(REF_PIC_LIST_1)); picHeader->setNoOutputBeforeRecoveryFlag( false ); if (pcSlice->isIRAP()) @@ -3968,10 +3962,10 @@ void EncGOP::compressGOP(int pocLast, int numPicRcvd, PicList &rcListPic, std::l // code RPL in picture header or slice headers if( !m_pcCfg->getSliceLevelRpl() && (!pcSlice->getIdrPicFlag() || pcSlice->getSPS()->getIDRRefParamListPresent()) ) { - picHeader->setRPL0idx(pcSlice->getRPL0idx()); - picHeader->setRPL1idx(pcSlice->getRPL1idx()); - *picHeader->getRPL0() = *pcSlice->getRPL0(); - *picHeader->getRPL1() = *pcSlice->getRPL1(); + picHeader->setRplIdx(REF_PIC_LIST_0, pcSlice->getRplIdx(REF_PIC_LIST_0)); + picHeader->setRplIdx(REF_PIC_LIST_1, pcSlice->getRplIdx(REF_PIC_LIST_1)); + *picHeader->getRpl(REF_PIC_LIST_0) = *pcSlice->getRpl(REF_PIC_LIST_0); + *picHeader->getRpl(REF_PIC_LIST_1) = *pcSlice->getRpl(REF_PIC_LIST_1); } // code DBLK in picture header or slice headers @@ -4018,8 +4012,8 @@ void EncGOP::compressGOP(int pocLast, int numPicRcvd, PicList &rcListPic, std::l if (!m_pcCfg->getSliceLevelWp()) { picHeader->setWpScaling(pcSlice->getWpScalingAll()); - picHeader->setNumL0Weights(pcSlice->getNumRefIdx(REF_PIC_LIST_0)); - picHeader->setNumL0Weights(pcSlice->getNumRefIdx(REF_PIC_LIST_1)); + picHeader->setNumWeights(REF_PIC_LIST_0, pcSlice->getNumRefIdx(REF_PIC_LIST_0)); + picHeader->setNumWeights(REF_PIC_LIST_1, pcSlice->getNumRefIdx(REF_PIC_LIST_1)); } pcPic->cs->picHeader->setPic(pcPic); @@ -6600,410 +6594,241 @@ bool EncGOP::xCheckMaxTidILRefPics(int layerIdx, Picture* refPic, bool currentPi void EncGOP::xCreateExplicitReferencePictureSetFromReference( Slice* slice, PicList& rcListPic, const ReferencePictureList *rpl0, const ReferencePictureList *rpl1 ) { - Picture* rpcPic; - int pocCycle = 0; + const int pocCycle = 1 << slice->getSPS()->getBitsForPOC(); - Picture* pic = slice->getPic(); - const VPS* vps = slice->getPic()->cs->vps; - int layerIdx = vps == nullptr ? 0 : vps->getGeneralLayerIdx( pic->layerId ); - bool isIntraLayerPredAllowed = (vps->getIndependentLayerFlag(layerIdx) || (vps->getPredDirection(slice->getTLayer()) != 1)) - && (!slice->isIRAP() || (m_pcEncLib->getAvoidIntraInDepLayer() && layerIdx)); - bool isInterLayerPredAllowed = !vps->getIndependentLayerFlag(layerIdx) && (vps->getPredDirection(slice->getTLayer()) != 2); + const bool interLayerPresent = slice->getSPS()->getInterLayerPresentFlag(); - ReferencePictureList localRPL0(slice->getSPS()->getInterLayerPresentFlag()); - ReferencePictureList *const pLocalRPL0 = &localRPL0; + Picture *curPic = slice->getPic(); + const VPS *vps = curPic->cs->vps; + int layerIdx = vps->getGeneralLayerIdx(curPic->layerId); - uint32_t numOfSTRPL0 = 0; - uint32_t numOfLTRPL0 = 0; - uint32_t numOfILRPL0 = 0; - uint32_t numOfRefPic = rpl0->getNumberOfShorttermPictures() + rpl0->getNumberOfLongtermPictures() + rpl0->getNumberOfInterLayerPictures(); - uint32_t refPicIdxL0 = 0; + const bool isIntraLayerPredAllowed = + (vps->getIndependentLayerFlag(layerIdx) || vps->getPredDirection(slice->getTLayer()) != 1) + && (!slice->isIRAP() || (m_pcEncLib->getAvoidIntraInDepLayer() && layerIdx != 0)); + const bool isInterLayerPredAllowed = + !vps->getIndependentLayerFlag(layerIdx) && vps->getPredDirection(slice->getTLayer()) != 2; - static_vector<int, MAX_NUM_REF_PICS> higherTLayerRefs; + ReferencePictureList localRpl[NUM_REF_PIC_LIST_01] = { ReferencePictureList(interLayerPresent), + ReferencePictureList(interLayerPresent) }; - higherTLayerRefs.resize(0); - static_vector<int, MAX_NUM_REF_PICS> inactiveRefs; - inactiveRefs.resize(0); - if (isIntraLayerPredAllowed) + uint32_t numStrp[NUM_REF_PIC_LIST_01] = { 0, 0 }; + uint32_t numLtrp[NUM_REF_PIC_LIST_01] = { 0, 0 }; + uint32_t numIlrp[NUM_REF_PIC_LIST_01] = { 0, 0 }; + uint32_t num[NUM_REF_PIC_LIST_01] = { 0, 0 }; + + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - for (int ii = 0; ii < numOfRefPic; ii++) - { - // loop through all pictures in the reference picture buffer - PicList::iterator iterPic = rcListPic.begin(); + static_vector<int, MAX_NUM_REF_PICS> higherTLayerRefs; + static_vector<int, MAX_NUM_REF_PICS> inactiveRefs; - bool isAvailable = false; - bool hasHigherTId = false; + const ReferencePictureList *rpl = l == REF_PIC_LIST_0 ? rpl0 : rpl1; - if (!rpl0->isInterLayerRefPic(ii)) + if (isIntraLayerPredAllowed) + { + for (int ii = 0; ii < rpl->getNumRefEntries(); ii++) { - pocCycle = 1 << (slice->getSPS()->getBitsForPOC()); - while (iterPic != rcListPic.end()) + if (!rpl->isInterLayerRefPic(ii)) { - rpcPic = *(iterPic++); - - if (rpcPic->layerId == pic->layerId) + for (const auto &pic: rcListPic) { - hasHigherTId = rpcPic->temporalId > pic->temporalId; - if (!rpl0->isRefPicLongterm(ii) && rpcPic->referenced - && rpcPic->getPOC() == slice->getPOC() + rpl0->getRefPicIdentifier(ii) - && !slice->isPocRestrictedByDRAP(rpcPic->getPOC(), rpcPic->precedingDRAP) - && !slice->isPocRestrictedByEdrap(rpcPic->getPOC())) + if (pic->layerId == curPic->layerId && pic->referenced + && !slice->isPocRestrictedByDRAP(pic->getPOC(), pic->precedingDRAP) + && !slice->isPocRestrictedByEdrap(pic->getPOC())) { - isAvailable = true; - break; - } - else if (rpl0->isRefPicLongterm(ii) && rpcPic->referenced && (rpcPic->getPOC() & (pocCycle - 1)) == rpl0->getRefPicIdentifier(ii) && !slice->isPocRestrictedByDRAP(rpcPic->getPOC(), rpcPic->precedingDRAP) - && !slice->isPocRestrictedByEdrap(rpcPic->getPOC())) - { - isAvailable = true; - break; + const bool isAvailable = !rpl->isRefPicLongterm(ii) + ? pic->getPOC() == slice->getPOC() + rpl->getRefPicIdentifier(ii) + : (pic->getPOC() & (pocCycle - 1)) == rpl->getRefPicIdentifier(ii); + if (isAvailable) + { + if (slice->isIRAP()) + { + inactiveRefs.push_back(ii); + } + else if (pic->temporalId > curPic->temporalId) + { + higherTLayerRefs.push_back(ii); + } + else if (num[l] >= rpl->getNumberOfActivePictures() - rpl->getNumberOfInterLayerPictures() + && layerIdx != 0 && vps != nullptr && !vps->getAllIndependentLayersFlag() + && isInterLayerPredAllowed) + { + inactiveRefs.push_back(ii); + } + else + { + localRpl[l].setRefPicIdentifier(num[l], rpl->getRefPicIdentifier(ii), rpl->isRefPicLongterm(ii), + false, NOT_VALID); + num[l]++; + numStrp[l] += rpl->isRefPicLongterm(ii) ? 0 : 1; + numLtrp[l] += rpl->isRefPicLongterm(ii) && !rpl->isInterLayerRefPic(ii) ? 1 : 0; + } + break; + } } } } - - if (isAvailable) - { - if (slice->isIRAP()) - { - inactiveRefs.push_back(ii); - } - else if (hasHigherTId) - { - higherTLayerRefs.push_back(ii); - } - else if (refPicIdxL0 >= rpl0->getNumberOfActivePictures() - rpl0->getNumberOfInterLayerPictures() && layerIdx && vps && !vps->getAllIndependentLayersFlag() && isInterLayerPredAllowed) - { - inactiveRefs.push_back(ii); - } - else - { - pLocalRPL0->setRefPicIdentifier(refPicIdxL0, rpl0->getRefPicIdentifier(ii), rpl0->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL0++; - numOfSTRPL0 = numOfSTRPL0 + ((rpl0->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL0 += (rpl0->isRefPicLongterm(ii) && !rpl0->isInterLayerRefPic(ii)) ? 1 : 0; - } - } } } - } - // inter-layer reference pictures are added to the end of the reference picture list - if (layerIdx && vps && !vps->getAllIndependentLayersFlag() && isInterLayerPredAllowed) - { - numOfRefPic = rpl0->getNumberOfInterLayerPictures() ? rpl0->getNumberOfInterLayerPictures() : m_pcEncLib->getNumRefLayers( layerIdx ); - - for( int ii = 0; ii < numOfRefPic; ii++ ) + // inter-layer reference pictures are added to the end of the reference picture list + if (layerIdx != 0 && vps != nullptr && !vps->getAllIndependentLayersFlag() && isInterLayerPredAllowed) { - // loop through all pictures in the reference picture buffer - PicList::iterator iterPic = rcListPic.begin(); - - while( iterPic != rcListPic.end() && ii < numOfRefPic ) + for (const auto &pic: rcListPic) { - rpcPic = *( iterPic++ ); - int refLayerIdx = vps->getGeneralLayerIdx( rpcPic->layerId ); - if (rpcPic->referenced && rpcPic->getPOC() == pic->getPOC() && vps->getDirectRefLayerFlag(layerIdx, refLayerIdx) - && xCheckMaxTidILRefPics(layerIdx, rpcPic, slice->isIRAP())) + int refLayerIdx = vps->getGeneralLayerIdx(pic->layerId); + if (pic->referenced && pic->getPOC() == curPic->getPOC() && vps->getDirectRefLayerFlag(layerIdx, refLayerIdx) + && xCheckMaxTidILRefPics(layerIdx, pic, slice->isIRAP())) { - pLocalRPL0->setRefPicIdentifier( refPicIdxL0, 0, true, true, vps->getInterLayerRefIdc( layerIdx, refLayerIdx ) ); - refPicIdxL0++; - numOfILRPL0++; - ii++; + localRpl[l].setRefPicIdentifier(num[l], 0, true, true, vps->getInterLayerRefIdc(layerIdx, refLayerIdx)); + num[l]++; + numIlrp[l]++; } } } - } - // now add inactive refs - for (int i = 0; i < inactiveRefs.size(); i++) - { - const int ii = inactiveRefs[i]; - pLocalRPL0->setRefPicIdentifier(refPicIdxL0, rpl0->getRefPicIdentifier(ii), rpl0->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL0++; - numOfSTRPL0 = numOfSTRPL0 + ((rpl0->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL0 += (rpl0->isRefPicLongterm(ii) && !rpl0->isInterLayerRefPic(ii)) ? 1 : 0; - } - if( slice->getEnableDRAPSEI() ) - { - pLocalRPL0->setNumberOfShorttermPictures( numOfSTRPL0 ); - pLocalRPL0->setNumberOfLongtermPictures( numOfLTRPL0 ); - pLocalRPL0->setNumberOfInterLayerPictures( numOfILRPL0 ); - - if( !slice->isIRAP() && !slice->isPOCInRefPicList( pLocalRPL0, slice->getAssociatedIRAPPOC() ) ) + // now add inactive refs + for (const int i: inactiveRefs) { - if( slice->getUseLTforDRAP() && !slice->isPOCInRefPicList( rpl1, slice->getAssociatedIRAPPOC() ) ) - { - // Adding associated IRAP as longterm picture - pLocalRPL0->setRefPicIdentifier( refPicIdxL0, slice->getAssociatedIRAPPOC(), true, false, 0 ); - refPicIdxL0++; - numOfLTRPL0++; - } - else - { - // Adding associated IRAP as shortterm picture - pLocalRPL0->setRefPicIdentifier(refPicIdxL0, slice->getAssociatedIRAPPOC() - slice->getPOC(), false, false, 0); - refPicIdxL0++; - numOfSTRPL0++; - } + localRpl[l].setRefPicIdentifier(num[l], rpl->getRefPicIdentifier(i), rpl->isRefPicLongterm(i), false, NOT_VALID); + num[l]++; + numStrp[l] += rpl->isRefPicLongterm(i) ? 0 : 1; + numLtrp[l] += rpl->isRefPicLongterm(i) && !rpl->isInterLayerRefPic(i) ? 1 : 0; } - } - if( slice->getEnableEdrapSEI() ) - { - pLocalRPL0->setNumberOfShorttermPictures( numOfSTRPL0 ); - pLocalRPL0->setNumberOfLongtermPictures( numOfLTRPL0 ); - pLocalRPL0->setNumberOfInterLayerPictures( numOfILRPL0 ); - for (int i = 0; i < slice->getEdrapNumRefRapPics(); i++) + if (slice->getEnableDRAPSEI() && l == REF_PIC_LIST_0) { - int refPoc = slice->getEdrapRefRapId(i) == 0 ? slice->getAssociatedIRAPPOC() : slice->getEdrapRefRapId(i) * m_pcEncLib->getEdrapPeriod(); - if( slice->isPOCInRefPicList( pLocalRPL0, refPoc ) ) - { - continue; - } - if( slice->getUseLTforEdrap() && !slice->isPOCInRefPicList( rpl1, refPoc ) ) - { - // Added as longterm picture - pLocalRPL0->setRefPicIdentifier( refPicIdxL0, refPoc, true, false, 0 ); - refPicIdxL0++; - numOfLTRPL0++; - } - else - { - // Added as shortterm picture - pLocalRPL0->setRefPicIdentifier(refPicIdxL0, refPoc - slice->getPOC(), false, false, 0); - refPicIdxL0++; - numOfSTRPL0++; - } - } - } - - // now add higher TId refs - for (int i = 0; i < higherTLayerRefs.size(); i++) - { - const int ii = higherTLayerRefs[i]; - pLocalRPL0->setRefPicIdentifier(refPicIdxL0, rpl0->getRefPicIdentifier(ii), rpl0->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL0++; - numOfSTRPL0 = numOfSTRPL0 + ((rpl0->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL0 += (rpl0->isRefPicLongterm(ii) && !rpl0->isInterLayerRefPic(ii)) ? 1 : 0; - } - - ReferencePictureList localRPL1(slice->getSPS()->getInterLayerPresentFlag()); - ReferencePictureList *const pLocalRPL1 = &localRPL1; + localRpl[l].setNumberOfShorttermPictures(numStrp[l]); + localRpl[l].setNumberOfLongtermPictures(numLtrp[l]); + localRpl[l].setNumberOfInterLayerPictures(numIlrp[l]); - uint32_t numOfSTRPL1 = 0; - uint32_t numOfLTRPL1 = 0; - uint32_t numOfILRPL1 = 0; - numOfRefPic = rpl1->getNumberOfShorttermPictures() + rpl1->getNumberOfLongtermPictures() + rpl1->getNumberOfInterLayerPictures(); - uint32_t refPicIdxL1 = 0; - - higherTLayerRefs.resize(0); - inactiveRefs.resize(0); - if (isIntraLayerPredAllowed) - { - for (int ii = 0; ii < numOfRefPic; ii++) - { - // loop through all pictures in the reference picture buffer - if (!rpl1->isInterLayerRefPic(ii)) + if (!slice->isIRAP() && !slice->isPOCInRefPicList(&localRpl[l], slice->getAssociatedIRAPPOC())) { - PicList::iterator iterPic = rcListPic.begin(); - - bool isAvailable = false; - bool hasHigherTId = false; - pocCycle = 1 << (slice->getSPS()->getBitsForPOC()); - while (iterPic != rcListPic.end()) + if (slice->getUseLTforDRAP() && !slice->isPOCInRefPicList(rpl1, slice->getAssociatedIRAPPOC())) { - rpcPic = *(iterPic++); - if (rpcPic->layerId == pic->layerId) - { - hasHigherTId = rpcPic->temporalId > pic->temporalId; - if (!rpl1->isRefPicLongterm(ii) && rpcPic->referenced - && rpcPic->getPOC() == slice->getPOC() + rpl1->getRefPicIdentifier(ii) - && !slice->isPocRestrictedByDRAP(rpcPic->getPOC(), rpcPic->precedingDRAP) - && !slice->isPocRestrictedByEdrap(rpcPic->getPOC())) - { - isAvailable = true; - break; - } - else if (rpl1->isRefPicLongterm(ii) && rpcPic->referenced && (rpcPic->getPOC() & (pocCycle - 1)) == rpl1->getRefPicIdentifier(ii) && !slice->isPocRestrictedByDRAP(rpcPic->getPOC(), rpcPic->precedingDRAP) && !slice->isPocRestrictedByEdrap(rpcPic->getPOC())) - { - isAvailable = true; - break; - } - } + // Adding associated IRAP as longterm picture + localRpl[l].setRefPicIdentifier(num[l], slice->getAssociatedIRAPPOC(), true, false, 0); + num[l]++; + numLtrp[l]++; } - - if (isAvailable) + else { - if (slice->isIRAP()) - { - inactiveRefs.push_back(ii); - } - else if (hasHigherTId) - { - higherTLayerRefs.push_back(ii); - } - else if (refPicIdxL1 >= rpl1->getNumberOfActivePictures() - rpl1->getNumberOfInterLayerPictures() && layerIdx && vps && !vps->getAllIndependentLayersFlag() && isInterLayerPredAllowed) - { - inactiveRefs.push_back(ii); - } - else - { - pLocalRPL1->setRefPicIdentifier(refPicIdxL1, rpl1->getRefPicIdentifier(ii), rpl1->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL1++; - numOfSTRPL1 = numOfSTRPL1 + ((rpl1->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL1 += (rpl1->isRefPicLongterm(ii) && !rpl1->isInterLayerRefPic(ii)) ? 1 : 0; - } + // Adding associated IRAP as shortterm picture + localRpl[l].setRefPicIdentifier(num[l], slice->getAssociatedIRAPPOC() - slice->getPOC(), false, false, 0); + num[l]++; + numStrp[l]++; } } } - } - - - // inter-layer reference pictures are added to the end of the reference picture list - if (layerIdx && vps && !vps->getAllIndependentLayersFlag() && isInterLayerPredAllowed) - { - numOfRefPic = rpl1->getNumberOfInterLayerPictures() ? rpl1->getNumberOfInterLayerPictures() : m_pcEncLib->getNumRefLayers( layerIdx ); - - for( int ii = 0; ii < numOfRefPic; ii++ ) + if (slice->getEnableEdrapSEI() && l == REF_PIC_LIST_0) { - // loop through all pictures in the reference picture buffer - PicList::iterator iterPic = rcListPic.begin(); + localRpl[l].setNumberOfShorttermPictures(numStrp[l]); + localRpl[l].setNumberOfLongtermPictures(numLtrp[l]); + localRpl[l].setNumberOfInterLayerPictures(numIlrp[l]); - while( iterPic != rcListPic.end() && ii < numOfRefPic ) + for (int i = 0; i < slice->getEdrapNumRefRapPics(); i++) { - rpcPic = *( iterPic++ ); - int refLayerIdx = vps->getGeneralLayerIdx( rpcPic->layerId ); - if (rpcPic->referenced && rpcPic->getPOC() == pic->getPOC() && vps->getDirectRefLayerFlag(layerIdx, refLayerIdx) - && xCheckMaxTidILRefPics( layerIdx, rpcPic, slice->isIRAP())) + int refPoc = slice->getEdrapRefRapId(i) == 0 ? slice->getAssociatedIRAPPOC() + : slice->getEdrapRefRapId(i) * m_pcEncLib->getEdrapPeriod(); + if (slice->isPOCInRefPicList(&localRpl[l], refPoc)) { - pLocalRPL1->setRefPicIdentifier( refPicIdxL1, 0, true, true, vps->getInterLayerRefIdc( layerIdx, refLayerIdx ) ); - refPicIdxL1++; - numOfILRPL1++; - ii++; + continue; } - } - } - } - - for (int i = 0; i < inactiveRefs.size(); i++) - { - const int ii = inactiveRefs[i]; - pLocalRPL1->setRefPicIdentifier(refPicIdxL1, rpl1->getRefPicIdentifier(ii), rpl1->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL1++; - numOfSTRPL1 = numOfSTRPL1 + ((rpl1->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL1 += (rpl1->isRefPicLongterm(ii) && !rpl1->isInterLayerRefPic(ii)) ? 1 : 0; - } - // now add higher TId refs - for (int i = 0; i < higherTLayerRefs.size(); i++) - { - const int ii = higherTLayerRefs[i]; - pLocalRPL1->setRefPicIdentifier(refPicIdxL1, rpl1->getRefPicIdentifier(ii), rpl1->isRefPicLongterm(ii), false, - NOT_VALID); - refPicIdxL1++; - numOfSTRPL1 = numOfSTRPL1 + ((rpl1->isRefPicLongterm(ii)) ? 0 : 1); - numOfLTRPL1 += (rpl1->isRefPicLongterm(ii) && !rpl1->isInterLayerRefPic(ii)) ? 1 : 0; - } - - //Copy from L1 if we have less than active ref pic - int numOfNeedToFill = rpl0->getNumberOfActivePictures() - rpl0->getNumberOfInterLayerPictures() - (numOfLTRPL0 + numOfSTRPL0); - bool isDisallowMixedRefPic = ( slice->getSPS()->getAllActiveRplEntriesHasSameSignFlag() ) ? true : false; - int originalL0StrpNum = numOfSTRPL0; - int originalL0LtrpNum = numOfLTRPL0; - int originalL0IlrpNum = numOfILRPL0; - - for( int ii = 0; numOfNeedToFill > 0 && ii < ( numOfLTRPL1 + numOfSTRPL1 + numOfILRPL1 ); ii++ ) - { - if( ii <= ( numOfLTRPL1 + numOfSTRPL1 + numOfILRPL1 - 1 ) ) - { - //Make sure this copy is not already in L0 - bool canIncludeThis = true; - for( int jj = 0; jj < refPicIdxL0; jj++ ) - { - if( ( pLocalRPL1->getRefPicIdentifier( ii ) == pLocalRPL0->getRefPicIdentifier( jj ) ) && ( pLocalRPL1->isRefPicLongterm( ii ) == pLocalRPL0->isRefPicLongterm( jj ) ) && pLocalRPL1->getInterLayerRefPicIdx( ii ) == pLocalRPL0->getInterLayerRefPicIdx( jj ) ) + if (slice->getUseLTforEdrap() && !slice->isPOCInRefPicList(rpl1, refPoc)) { - canIncludeThis = false; + // Added as longterm picture + localRpl[l].setRefPicIdentifier(num[l], refPoc, true, false, 0); + num[l]++; + numLtrp[l]++; } - - bool sameSign = ( pLocalRPL1->getRefPicIdentifier( ii ) > 0 ) == ( pLocalRPL0->getRefPicIdentifier( 0 ) > 0 ); - - if( isDisallowMixedRefPic && canIncludeThis && !pLocalRPL1->isRefPicLongterm( ii ) && !sameSign ) + else { - canIncludeThis = false; + // Added as shortterm picture + localRpl[l].setRefPicIdentifier(num[l], refPoc - slice->getPOC(), false, false, 0); + num[l]++; + numStrp[l]++; } } - if( canIncludeThis ) - { - pLocalRPL0->setRefPicIdentifier( refPicIdxL0, pLocalRPL1->getRefPicIdentifier( ii ), pLocalRPL1->isRefPicLongterm( ii ), pLocalRPL1->isInterLayerRefPic( ii ), pLocalRPL1->getInterLayerRefPicIdx( ii ) ); - refPicIdxL0++; - numOfSTRPL0 = numOfSTRPL0 + ( ( pLocalRPL1->isRefPicLongterm( ii ) ) ? 0 : 1 ); - numOfLTRPL0 += ( pLocalRPL1->isRefPicLongterm( ii ) && !pLocalRPL1->isInterLayerRefPic( ii ) ) ? 1 : 0; - numOfILRPL0 += pLocalRPL1->isInterLayerRefPic( ii ) ? 1 : 0; - numOfNeedToFill--; - } + } + + // now add higher TId refs + for (const int i: higherTLayerRefs) + { + localRpl[l].setRefPicIdentifier(num[l], rpl->getRefPicIdentifier(i), rpl->isRefPicLongterm(i), false, NOT_VALID); + num[l]++; + numStrp[l] += rpl->isRefPicLongterm(i) ? 0 : 1; + numLtrp[l] += rpl->isRefPicLongterm(i) && !rpl->isInterLayerRefPic(i) ? 1 : 0; } } - pLocalRPL0->setNumberOfLongtermPictures( numOfLTRPL0 ); - pLocalRPL0->setNumberOfShorttermPictures( numOfSTRPL0 ); - pLocalRPL0->setNumberOfInterLayerPictures( numOfILRPL0 ); - int numPics = (slice->isIRAP()) ? 0 : numOfLTRPL0 + numOfSTRPL0; - pLocalRPL0->setNumberOfActivePictures((numPics < (rpl0->getNumberOfActivePictures() - rpl0->getNumberOfInterLayerPictures()) ? numPics : (rpl0->getNumberOfActivePictures() - rpl0->getNumberOfInterLayerPictures())) + numOfILRPL0); - pLocalRPL0->setLtrpInSliceHeaderFlag( 1 ); - slice->setRPL0idx( -1 ); - *slice->getRPL0() = localRPL0; + uint32_t numPrev[NUM_REF_PIC_LIST_01] = { num[REF_PIC_LIST_0], num[REF_PIC_LIST_1] }; + + // Copy from other list if we have fewer than active ref pics - //Copy from L0 if we have less than active ref pic - numOfNeedToFill = rpl1->getNumberOfActivePictures() - rpl1->getNumberOfInterLayerPictures() - (numOfLTRPL1 + numOfSTRPL1); + bool isDisallowMixedRefPic = slice->getSPS()->getAllActiveRplEntriesHasSameSignFlag(); - for( int ii = 0; numOfNeedToFill > 0 && ii < ( pLocalRPL0->getNumberOfLongtermPictures() + pLocalRPL0->getNumberOfShorttermPictures() + pLocalRPL0->getNumberOfInterLayerPictures() ); ii++ ) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if( ii <= ( originalL0StrpNum + originalL0LtrpNum + originalL0IlrpNum - 1 ) ) + const ReferencePictureList *rpl = l == REF_PIC_LIST_0 ? rpl0 : rpl1; + const auto k = l == REF_PIC_LIST_0 ? REF_PIC_LIST_1 : REF_PIC_LIST_0; + + int numOfNeedToFill = rpl->getNumberOfActivePictures() - num[l]; + + for (int ii = 0; numOfNeedToFill > 0 && ii < numPrev[k]; ii++) { - //Make sure this copy is not already in L0 + const int identifier = localRpl[k].getRefPicIdentifier(ii); + const bool isLongTerm = localRpl[k].isRefPicLongterm(ii); + const bool isInterLayer = localRpl[k].isInterLayerRefPic(ii); + + // Make sure this copy is not already present bool canIncludeThis = true; - for( int jj = 0; jj < refPicIdxL1; jj++ ) + for (int jj = 0; jj < num[l]; jj++) { - if( ( pLocalRPL0->getRefPicIdentifier( ii ) == pLocalRPL1->getRefPicIdentifier( jj ) ) && ( pLocalRPL0->isRefPicLongterm( ii ) == pLocalRPL1->isRefPicLongterm( jj ) ) && pLocalRPL0->getInterLayerRefPicIdx( ii ) == pLocalRPL1->getInterLayerRefPicIdx( jj ) ) + if (identifier == localRpl[l].getRefPicIdentifier(jj) && isLongTerm == localRpl[l].isRefPicLongterm(jj) + && isInterLayer == localRpl[l].isInterLayerRefPic(jj)) { canIncludeThis = false; + break; } - bool sameSign = ( pLocalRPL0->getRefPicIdentifier( ii ) > 0 ) == ( pLocalRPL1->getRefPicIdentifier( 0 ) > 0 ); - - if( isDisallowMixedRefPic && canIncludeThis && !pLocalRPL0->isRefPicLongterm( ii ) && !sameSign ) + if (isDisallowMixedRefPic && !isLongTerm && !localRpl[l].isRefPicLongterm(jj)) { - canIncludeThis = false; + const bool sameSign = (identifier ^ localRpl[l].getRefPicIdentifier(jj)) >= 0; + if (!sameSign) + { + canIncludeThis = false; + break; + } } } if( canIncludeThis ) { - pLocalRPL1->setRefPicIdentifier( refPicIdxL1, pLocalRPL0->getRefPicIdentifier( ii ), pLocalRPL0->isRefPicLongterm( ii ), pLocalRPL0->isInterLayerRefPic( ii ), pLocalRPL0->getInterLayerRefPicIdx( ii ) ); - refPicIdxL1++; - numOfSTRPL1 = numOfSTRPL1 + ( ( pLocalRPL0->isRefPicLongterm( ii ) ) ? 0 : 1 ); - numOfLTRPL1 += ( pLocalRPL0->isRefPicLongterm( ii ) && !pLocalRPL0->isInterLayerRefPic( ii ) ) ? 1 : 0; - numOfILRPL1 += pLocalRPL0->isInterLayerRefPic( ii ) ? 1 : 0; + localRpl[l].setRefPicIdentifier(num[l], identifier, isLongTerm, isInterLayer, + localRpl[k].getInterLayerRefPicIdx(ii)); + num[l]++; + numStrp[l] += isLongTerm ? 0 : 1; + numLtrp[l] += isLongTerm && !isInterLayer ? 1 : 0; + numIlrp[l] += isInterLayer ? 1 : 0; numOfNeedToFill--; } } + localRpl[l].setNumberOfLongtermPictures(numLtrp[l]); + localRpl[l].setNumberOfShorttermPictures(numStrp[l]); + localRpl[l].setNumberOfInterLayerPictures(numIlrp[l]); + const int numPics = slice->isIRAP() ? 0 : numLtrp[l] + numStrp[l]; + + localRpl[l].setNumberOfActivePictures( + std::min<int>(numPics, rpl->getNumberOfActivePictures() - rpl->getNumberOfInterLayerPictures()) + numIlrp[l]); + localRpl[l].setLtrpInSliceHeaderFlag(1); + slice->setRplIdx(l, -1); + *slice->getRpl(l) = localRpl[l]; } - pLocalRPL1->setNumberOfLongtermPictures( numOfLTRPL1 ); - pLocalRPL1->setNumberOfShorttermPictures( numOfSTRPL1 ); - pLocalRPL1->setNumberOfInterLayerPictures( numOfILRPL1 ); - numPics = (slice->isIRAP()) ? 0 : numOfLTRPL1 + numOfSTRPL1; - pLocalRPL1->setNumberOfActivePictures((numPics < (rpl1->getNumberOfActivePictures() - rpl1->getNumberOfInterLayerPictures()) ? numPics : (rpl1->getNumberOfActivePictures() - rpl1->getNumberOfInterLayerPictures())) + numOfILRPL1); - pLocalRPL1->setLtrpInSliceHeaderFlag( 1 ); - slice->setRPL1idx( -1 ); - *slice->getRPL1() = localRPL1; - // To ensure that any picture in the RefRapIds has been included in the refrence list. + // Ensure that all pictures in the RefRapIds are included in a reference list. for (int i = 0; i < slice->getEdrapNumRefRapPics(); i++) { int refPoc = slice->getEdrapRefRapId(i) == 0 ? slice->getAssociatedIRAPPOC() : slice->getEdrapRefRapId(i) * m_pcEncLib->getEdrapPeriod(); - if (!slice->isPOCInRefPicList( pLocalRPL0, refPoc ) && !slice->isPOCInRefPicList( pLocalRPL1, refPoc )) + if (!slice->isPOCInRefPicList(&localRpl[REF_PIC_LIST_0], refPoc) + && !slice->isPOCInRefPicList(&localRpl[REF_PIC_LIST_1], refPoc)) { slice->deleteEdrapRefRapIds(i); } diff --git a/source/Lib/EncoderLib/EncLib.cpp b/source/Lib/EncoderLib/EncLib.cpp index db2a832c9b4f98c78dae32f7391f238721b18b70..6b77221167d51d691a860da93ee49cf877943a55 100644 --- a/source/Lib/EncoderLib/EncLib.cpp +++ b/source/Lib/EncoderLib/EncLib.cpp @@ -2037,9 +2037,9 @@ void EncLib::xInitPPS(PPS &pps, const SPS &sps) bestPos=i; } } - CHECK(!(bestPos <= 15), "Unspecified error"); - pps.setNumRefIdxL0DefaultActive(bestPos); - pps.setNumRefIdxL1DefaultActive(bestPos); + CHECK(bestPos > 15, "Unspecified error"); + pps.setNumRefIdxDefaultActive(REF_PIC_LIST_0, bestPos); + pps.setNumRefIdxDefaultActive(REF_PIC_LIST_1, bestPos); pps.setPictureHeaderExtensionPresentFlag(false); pps.setRplInfoInPhFlag(getSliceLevelRpl() ? false : true); @@ -2163,24 +2163,24 @@ void EncLib::xInitRPL(SPS &sps) setRplOfDepLayerInSh(codeRplInSH); if (codeRplInSH) { - sps.createRPLList0(0); - sps.createRPLList1(0); - getRPLList(0)->destroy(); - getRPLList(0)->create(numRPLCandidates + (isFieldCoding ? 1 : 0)); - getRPLList(1)->destroy(); - getRPLList(1)->create(numRPLCandidates + (isFieldCoding ? 1 : 0)); - rplLists[0] = getRPLList(0); - rplLists[1] = getRPLList(1); + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + sps.createRplList(l, 0); + getRplList(l)->destroy(); + getRplList(l)->create(numRPLCandidates + (isFieldCoding ? 1 : 0)); + rplLists[l] = getRplList(l); + } } else { - getRPLList(0)->create(0); - getRPLList(1)->create(0); - sps.createRPLList0(numRPLCandidates + (isFieldCoding ? 1 : 0)); - sps.createRPLList1(numRPLCandidates + (isFieldCoding ? 1 : 0)); - rplLists[0] = sps.getRPLList(0); - rplLists[1] = sps.getRPLList(1); + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + getRplList(l)->create(0); + sps.createRplList(l, numRPLCandidates + (isFieldCoding ? 1 : 0)); + rplLists[l] = sps.getRplList(l); + } } + static_vector<int, MAX_VPS_LAYERS> refLayersIdx; if (layerIdx > 0 && !getRplOfDepLayerInSh()) { @@ -2267,24 +2267,27 @@ void EncLib::xInitRPL(SPS &sps) } } - bool isRpl1CopiedFromRpl0 = true; - for(int i = 0; isRpl1CopiedFromRpl0 && i < sps.getNumRPL0(); i++) + const int numRplsL0 = sps.getNumRpl(REF_PIC_LIST_0); + const int numRplsL1 = sps.getNumRpl(REF_PIC_LIST_1); + + bool isRpl1CopiedFromRpl0 = numRplsL0 == numRplsL1; + + for (int i = 0; isRpl1CopiedFromRpl0 && i < numRplsL0; i++) { - if( sps.getRPLList0()->getReferencePictureList(i)->getNumRefEntries() == sps.getRPLList1()->getReferencePictureList(i)->getNumRefEntries() ) - { - for( int j = 0; isRpl1CopiedFromRpl0 && j < sps.getRPLList0()->getReferencePictureList(i)->getNumRefEntries(); j++ ) - { - if( sps.getRPLList0()->getReferencePictureList(i)->getRefPicIdentifier(j) != sps.getRPLList1()->getReferencePictureList(i)->getRefPicIdentifier(j) ) - { - isRpl1CopiedFromRpl0 = false; - } - } - } - else + const int numEntriesL0 = sps.getRplList(REF_PIC_LIST_0)->getReferencePictureList(i)->getNumRefEntries(); + const int numEntriesL1 = sps.getRplList(REF_PIC_LIST_1)->getReferencePictureList(i)->getNumRefEntries(); + + isRpl1CopiedFromRpl0 = numEntriesL0 == numEntriesL1; + + for (int j = 0; isRpl1CopiedFromRpl0 && j < numEntriesL0; j++) { - isRpl1CopiedFromRpl0 = false; + const int entryL0 = sps.getRplList(REF_PIC_LIST_0)->getReferencePictureList(i)->getRefPicIdentifier(j); + const int entryL1 = sps.getRplList(REF_PIC_LIST_1)->getReferencePictureList(i)->getRefPicIdentifier(j); + + isRpl1CopiedFromRpl0 = entryL0 == entryL1; } } + sps.setRPL1CopyFromRPL0Flag(isRpl1CopiedFromRpl0); //Check if all delta POC of STRP in each RPL has the same sign @@ -2296,25 +2299,26 @@ void EncLib::xInitRPL(SPS &sps) for (uint32_t ii = 0; isAllEntriesinRPLHasSameSignFlag && ii < rplList0->getNumberOfReferencePictureLists(); ii++) { bool isFirstEntry = true; - bool lastSign = true; + bool prevSign = true; + int prevIdentifier = 0; const ReferencePictureList* rpl = rplList0->getReferencePictureList(ii); for (uint32_t jj = 0; isAllEntriesinRPLHasSameSignFlag && jj < rpl->getNumberOfActivePictures(); jj++) { if (!rpl->isRefPicLongterm(jj)) { - if (isFirstEntry) + const int identifier = rpl->getRefPicIdentifier(jj); + const int delta = identifier - prevIdentifier; + if (delta != 0) { - lastSign = rpl->getRefPicIdentifier(jj) >= 0; - isFirstEntry = false; - } - else - { - const bool currentSign = rpl->getRefPicIdentifier(jj) - rpl->getRefPicIdentifier(jj - 1) >= 0; - if (currentSign != lastSign) + const bool currentSign = delta >= 0; + if (!isFirstEntry && currentSign != prevSign) { isAllEntriesinRPLHasSameSignFlag = false; } + prevIdentifier = identifier; + prevSign = currentSign; + isFirstEntry = false; } } } @@ -2357,20 +2361,20 @@ void EncLib::selectReferencePictureList(Slice *slice, int pocCurr, int gopId, in pocCurr++; } - const RPLList* rplLists[2]; + const RPLList *rplLists[NUM_REF_PIC_LIST_01]; bool codeRplInSH = getRplOfDepLayerInSh(); int RPLIdx = gopId; - if (codeRplInSH) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - rplLists[0] = getRPLList(0); - rplLists[1] = getRPLList(1); - slice->setRPL0idx(-1); - slice->setRPL1idx(-1); - } - else - { - rplLists[0] = slice->getSPS()->getRPLList(0); - rplLists[1] = slice->getSPS()->getRPLList(1); + if (codeRplInSH) + { + rplLists[l] = getRplList(l); + slice->setRplIdx(l, -1); + } + else + { + rplLists[l] = slice->getSPS()->getRplList(l); + } } int fullListNum = m_gopSize; @@ -2424,8 +2428,8 @@ void EncLib::selectReferencePictureList(Slice *slice, int pocCurr, int gopId, in // To set RPL index of POC1 (first bottom field) if (pocCurr == 1) { - slice->setRPL0idx(getRPLCandidateSize(0)); - slice->setRPL1idx(getRPLCandidateSize(0)); + slice->setRplIdx(REF_PIC_LIST_0, getRPLCandidateSize(0)); + slice->setRplIdx(REF_PIC_LIST_1, getRPLCandidateSize(0)); } else if( rplPeriod < 0 ) { @@ -2453,13 +2457,13 @@ void EncLib::selectReferencePictureList(Slice *slice, int pocCurr, int gopId, in } } - * slice->getRPL0() = *rplLists[0]->getReferencePictureList(RPLIdx); - *slice->getRPL1() = *rplLists[1]->getReferencePictureList(RPLIdx); + *slice->getRpl(REF_PIC_LIST_0) = *rplLists[0]->getReferencePictureList(RPLIdx); + *slice->getRpl(REF_PIC_LIST_1) = *rplLists[1]->getReferencePictureList(RPLIdx); if (!codeRplInSH) { - slice->setRPL0idx(RPLIdx); - slice->setRPL1idx(RPLIdx); + slice->setRplIdx(REF_PIC_LIST_0, RPLIdx); + slice->setRplIdx(REF_PIC_LIST_1, RPLIdx); } } diff --git a/source/Lib/EncoderLib/EncLib.h b/source/Lib/EncoderLib/EncLib.h index 777aaadccd7bc3d19793be6331a2af5ffc93b911..acce2aefff6dbd31a8b17478e49aeaa02cc54d95 100644 --- a/source/Lib/EncoderLib/EncLib.h +++ b/source/Lib/EncoderLib/EncLib.h @@ -139,9 +139,9 @@ public: APS** getApss() { return m_apss; } Ctx m_entropyCodingSyncContextState; ///< leave in addition to vector for compatibility PLTBuf m_palettePredictorSyncState; - const RPLList* getRPLList(bool b) const { return &m_rplLists[b]; } - RPLList* getRPLList(bool b) { return &m_rplLists[b]; } - uint32_t getNumRPL(bool b) const { return m_rplLists[b].getNumberOfReferencePictureLists(); } + const RPLList *getRplList(RefPicList l) const { return &m_rplLists[l]; } + RPLList *getRplList(RefPicList l) { return &m_rplLists[l]; } + uint32_t getNumRpl(RefPicList l) const { return m_rplLists[l].getNumberOfReferencePictureLists(); } int m_gopRprPpsId; protected: void xGetNewPicBuffer ( std::list<PelUnitBuf*>& rcListPicYuvRecOut, Picture*& rpcPic, int ppsId ); ///< get picture buffer which will be processed. If ppsId<0, then the ppsMap will be queried for the first match. diff --git a/source/Lib/EncoderLib/VLCWriter.cpp b/source/Lib/EncoderLib/VLCWriter.cpp index bacfd3575d1001fe36cec756fb6a268836f826c5..4d2222293650a4173ba05ac4a44dcfc5534ba964 100644 --- a/source/Lib/EncoderLib/VLCWriter.cpp +++ b/source/Lib/EncoderLib/VLCWriter.cpp @@ -227,7 +227,7 @@ void FDWriter::codeFD(OutputBitstream& bs, uint32_t &fdSize) void HLSWriter::xCodeRefPicList( const ReferencePictureList* rpl, bool isLongTermPresent, uint32_t ltLsbBitsCount, const bool isForbiddenZeroDeltaPoc, int rplIdx) { - uint32_t numRefPic = rpl->getNumberOfShorttermPictures() + rpl->getNumberOfLongtermPictures() + rpl->getNumberOfInterLayerPictures(); + uint32_t numRefPic = rpl->getNumRefEntries(); xWriteUvlc( numRefPic, "num_ref_entries[ listIdx ][ rplsIdx ]" ); if (isLongTermPresent && numRefPic > 0 && rplIdx != -1) @@ -444,8 +444,8 @@ void HLSWriter::codePPS( const PPS* pcPPS ) } xWriteFlag( pcPPS->getCabacInitPresentFlag() ? 1 : 0, "pps_cabac_init_present_flag" ); - xWriteUvlc( pcPPS->getNumRefIdxL0DefaultActive()-1, "pps_num_ref_idx_default_active_minus1[0]"); - xWriteUvlc( pcPPS->getNumRefIdxL1DefaultActive()-1, "pps_num_ref_idx_default_active_minus1[1]"); + xWriteUvlc(pcPPS->getNumRefIdxDefaultActive(REF_PIC_LIST_0) - 1, "pps_num_ref_idx_default_active_minus1[0]"); + xWriteUvlc(pcPPS->getNumRefIdxDefaultActive(REF_PIC_LIST_1) - 1, "pps_num_ref_idx_default_active_minus1[1]"); xWriteFlag( pcPPS->getRpl1IdxPresentFlag() ? 1 : 0, "pps_rpl1_idx_present_flag"); xWriteFlag( pcPPS->getUseWP() ? 1 : 0, "pps_weighted_pred_flag" ); // Use of Weighting Prediction (P_SLICE) xWriteFlag( pcPPS->getWPBiPred() ? 1 : 0, "pps_weighted_bipred_flag" ); // Use of Weighting Bi-Prediction (B_SLICE) @@ -1052,27 +1052,21 @@ void HLSWriter::codeSPS( const SPS* pcSPS ) xWriteFlag(pcSPS->getIDRRefParamListPresent() ? 1 : 0, "sps_idr_rpl_present_flag" ); xWriteFlag(pcSPS->getRPL1CopyFromRPL0Flag() ? 1 : 0, "sps_rpl1_same_as_rpl0_flag"); - const RPLList* rplList0 = pcSPS->getRPLList0(); - const RPLList* rplList1 = pcSPS->getRPLList1(); - - //Write candidate for List0 - uint32_t numberOfRPL = pcSPS->getNumRPL0(); - xWriteUvlc(numberOfRPL, "sps_num_ref_pic_lists[0]"); - for (int ii = 0; ii < numberOfRPL; ii++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - const ReferencePictureList* rpl = rplList0->getReferencePictureList(ii); - xCodeRefPicList(rpl, pcSPS->getLongTermRefsPresent(), pcSPS->getBitsForPOC(), !pcSPS->getUseWP() && !pcSPS->getUseWPBiPred(), ii); - } + if (l == REF_PIC_LIST_1 && pcSPS->getRPL1CopyFromRPL0Flag()) + { + continue; + } + const RPLList *rplList = pcSPS->getRplList(l); + const int numRpl = pcSPS->getNumRpl(l); + xWriteUvlc(numRpl, l == REF_PIC_LIST_0 ? "sps_num_ref_pic_lists[0]" : "sps_num_ref_pic_lists[1]"); - //Write candidate for List1 - if (!pcSPS->getRPL1CopyFromRPL0Flag()) - { - numberOfRPL = pcSPS->getNumRPL1(); - xWriteUvlc(numberOfRPL, "sps_num_ref_pic_lists[1]"); - for (int ii = 0; ii < numberOfRPL; ii++) + for (int rplIdx = 0; rplIdx < numRpl; rplIdx++) { - const ReferencePictureList* rpl = rplList1->getReferencePictureList(ii); - xCodeRefPicList(rpl, pcSPS->getLongTermRefsPresent(), pcSPS->getBitsForPOC(), !pcSPS->getUseWP() && !pcSPS->getUseWPBiPred(), ii); + const ReferencePictureList *rpl = rplList->getReferencePictureList(rplIdx); + xCodeRefPicList(rpl, pcSPS->getLongTermRefsPresent(), pcSPS->getBitsForPOC(), + !pcSPS->getUseWP() && !pcSPS->getUseWPBiPred(), rplIdx); } } @@ -1863,63 +1857,68 @@ void HLSWriter::codePictureHeader( PicHeader* picHeader, bool writeRbspTrailingB if (pps->getRplInfoInPhFlag()) { // List0 and List1 - for(int listIdx = 0; listIdx < 2; listIdx++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - if(sps->getNumRPL(listIdx) > 0 && - (listIdx == 0 || (listIdx == 1 && pps->getRpl1IdxPresentFlag()))) + const int numRplsInSps = sps->getNumRpl(l); + const int rplIdx = picHeader->getRplIdx(l); + const bool rplSpsFlag = rplIdx != -1; + + if (numRplsInSps == 0) { - xWriteFlag(picHeader->getRPLIdx(listIdx) != -1 ? 1 : 0, "rpl_sps_flag[i]"); + CHECK(rplSpsFlag, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); } - else if(sps->getNumRPL(listIdx) == 0) + else if (l == REF_PIC_LIST_0 || pps->getRpl1IdxPresentFlag()) { - CHECK(picHeader->getRPLIdx(listIdx) != -1, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); + xWriteFlag(rplSpsFlag ? 1 : 0, "rpl_sps_flag[i]"); } - else if(listIdx == 1) + else { - auto rplsSpsFlag0 = picHeader->getRPLIdx(0) != -1 ? 1 : 0; - auto rplsSpsFlag1 = picHeader->getRPLIdx(1) != -1 ? 1 : 0; - CHECK(rplsSpsFlag1 != rplsSpsFlag0, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); + bool rplSpsFlag0 = picHeader->getRplIdx(REF_PIC_LIST_0) != -1; + CHECK(rplSpsFlag != rplSpsFlag0, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); } - if(picHeader->getRPLIdx(listIdx) != -1) + if (rplSpsFlag) { - if(sps->getNumRPL(listIdx) > 1 && - (listIdx == 0 || (listIdx == 1 && pps->getRpl1IdxPresentFlag()))) - { - int numBits = ceilLog2(sps->getNumRPL( listIdx )); - xWriteCode(picHeader->getRPLIdx(listIdx), numBits, "rpl_idx[i]"); - } - else if(sps->getNumRPL(listIdx) == 1) + CHECK(rplIdx >= numRplsInSps, "rpl_idx is too large"); + + if (l == REF_PIC_LIST_0 || pps->getRpl1IdxPresentFlag()) { - CHECK(picHeader->getRPLIdx(listIdx) != 0, "RPL1Idx is not signalled but it is not equal to 0"); + if (numRplsInSps > 1) + { + const int numBits = ceilLog2(numRplsInSps); + xWriteCode(rplIdx, numBits, "rpl_idx[i]"); + } } else { - CHECK(picHeader->getRPL1idx() != picHeader->getRPL0idx(), "RPL1Idx is not signalled but it is not the same as RPL0Idx"); + CHECK(rplIdx != picHeader->getRplIdx(REF_PIC_LIST_0), + "RPL1Idx is not signalled but it is not the same as RPL0Idx"); } } // explicit RPL in picture header else { - xCodeRefPicList( picHeader->getRPL(listIdx), sps->getLongTermRefsPresent(), sps->getBitsForPOC(), !sps->getUseWP() && !sps->getUseWPBiPred(), -1); + xCodeRefPicList(picHeader->getRpl(l), sps->getLongTermRefsPresent(), sps->getBitsForPOC(), + !sps->getUseWP() && !sps->getUseWPBiPred(), -1); } // POC MSB cycle signalling for LTRP - if (picHeader->getRPL(listIdx) && picHeader->getRPL(listIdx)->getNumberOfLongtermPictures()) + const ReferencePictureList *rpl = picHeader->getRpl(l); + + if (rpl != nullptr && rpl->getNumberOfLongtermPictures() > 0) { - for (int i = 0; i < picHeader->getRPL(listIdx)->getNumberOfLongtermPictures() + picHeader->getRPL(listIdx)->getNumberOfShorttermPictures(); i++) + for (int i = 0; i < rpl->getNumRefEntries(); i++) { - if (picHeader->getRPL(listIdx)->isRefPicLongterm(i)) + if (rpl->isRefPicLongterm(i)) { - if (picHeader->getRPL(listIdx)->getLtrpInSliceHeaderFlag()) + if (rpl->getLtrpInSliceHeaderFlag()) { - xWriteCode(picHeader->getRPL(listIdx)->getRefPicIdentifier(i), sps->getBitsForPOC(), - "poc_lsb_lt[listIdx][rplsIdx][j]"); + xWriteCode(rpl->getRefPicIdentifier(i), sps->getBitsForPOC(), "poc_lsb_lt[listIdx][rplsIdx][j]"); } - xWriteFlag(picHeader->getRPL(listIdx)->getDeltaPocMSBPresentFlag(i) ? 1 : 0, "delta_poc_msb_present_flag[i][j]"); - if (picHeader->getRPL(listIdx)->getDeltaPocMSBPresentFlag(i)) + xWriteFlag(rpl->getDeltaPocMSBPresentFlag(i) ? 1 : 0, "delta_poc_msb_present_flag[i][j]"); + if (rpl->getDeltaPocMSBPresentFlag(i)) { - xWriteUvlc(picHeader->getRPL(listIdx)->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); + xWriteUvlc(rpl->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); } } } @@ -2018,12 +2017,12 @@ void HLSWriter::codePictureHeader( PicHeader* picHeader, bool writeRbspTrailingB xWriteFlag( picHeader->getEnableTMVPFlag(), "ph_temporal_mvp_enabled_flag" ); if (picHeader->getEnableTMVPFlag() && pps->getRplInfoInPhFlag()) { - if (picHeader->getRPL(1)->getNumRefEntries() > 0) + if (picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0) { xWriteCode(picHeader->getPicColFromL0Flag(), 1, "ph_collocated_from_l0_flag"); } - if ((picHeader->getPicColFromL0Flag() && picHeader->getRPL(0)->getNumRefEntries() > 1) || - (!picHeader->getPicColFromL0Flag() && picHeader->getRPL(1)->getNumRefEntries() > 1)) + if ((picHeader->getPicColFromL0Flag() && picHeader->getRpl(REF_PIC_LIST_0)->getNumRefEntries() > 1) + || (!picHeader->getPicColFromL0Flag() && picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 1)) { xWriteUvlc(picHeader->getColRefIdx(), "ph_collocated_ref_idx"); } @@ -2056,13 +2055,14 @@ void HLSWriter::codePictureHeader( PicHeader* picHeader, bool writeRbspTrailingB } // mvd L1 zero flag - if (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0) + if (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0) { xWriteFlag(picHeader->getMvdL1ZeroFlag(), "ph_mvd_l1_zero_flag"); } // picture level BDOF disable flags - if (sps->getBdofControlPresentInPhFlag() && (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0)) + if (sps->getBdofControlPresentInPhFlag() + && (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0)) { xWriteFlag(picHeader->getBdofDisabledFlag(), "ph_bdof_disabled_flag"); } @@ -2072,7 +2072,8 @@ void HLSWriter::codePictureHeader( PicHeader* picHeader, bool writeRbspTrailingB } // picture level DMVR disable flags - if (sps->getDmvrControlPresentInPhFlag() && (!pps->getRplInfoInPhFlag() || picHeader->getRPL(1)->getNumRefEntries() > 0)) + if (sps->getDmvrControlPresentInPhFlag() + && (!pps->getRplInfoInPhFlag() || picHeader->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 0)) { xWriteFlag(picHeader->getDmvrDisabledFlag(), "ph_dmvr_disabled_flag"); } @@ -2341,112 +2342,106 @@ void HLSWriter::codeSliceHeader ( Slice* pcSlice, PicHeader *picHeader ) if( !pcSlice->getPPS()->getRplInfoInPhFlag() && (!pcSlice->getIdrPicFlag() || pcSlice->getSPS()->getIDRRefParamListPresent())) { // Write L0 related syntax elements - if (pcSlice->getSPS()->getNumRPL0() > 0) + const int numRplsInSps = pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_0); + const int rplIdx = pcSlice->getRplIdx(REF_PIC_LIST_0); + + if (numRplsInSps > 0) { - xWriteFlag(pcSlice->getRPL0idx() != -1 ? 1 : 0, "ref_pic_list_sps_flag[0]"); + xWriteFlag(rplIdx != -1 ? 1 : 0, "ref_pic_list_sps_flag[0]"); } - if (pcSlice->getRPL0idx() != -1) + if (rplIdx != -1) { - if (pcSlice->getSPS()->getNumRPL0() > 1) + if (numRplsInSps > 1) { - int numBits = 0; - while ((1 << numBits) < pcSlice->getSPS()->getNumRPL0()) - { - numBits++; - } - xWriteCode(pcSlice->getRPL0idx(), numBits, "ref_pic_list_idx[0]"); + int numBits = ceilLog2(numRplsInSps); + xWriteCode(rplIdx, numBits, "ref_pic_list_idx[0]"); } } else { // write local RPL0 - xCodeRefPicList(pcSlice->getRPL0(), pcSlice->getSPS()->getLongTermRefsPresent(), + xCodeRefPicList(pcSlice->getRpl(REF_PIC_LIST_0), pcSlice->getSPS()->getLongTermRefsPresent(), pcSlice->getSPS()->getBitsForPOC(), !pcSlice->getSPS()->getUseWP() && !pcSlice->getSPS()->getUseWPBiPred(), -1); } // Deal POC Msb cycle signalling for LTRP - if (pcSlice->getRPL0()->getNumberOfLongtermPictures()) + if (pcSlice->getRpl(REF_PIC_LIST_0)->getNumberOfLongtermPictures()) { - for (int i = 0; - i < pcSlice->getRPL0()->getNumberOfLongtermPictures() + pcSlice->getRPL0()->getNumberOfShorttermPictures(); - i++) + for (int i = 0; i < pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries(); i++) { - if (pcSlice->getRPL0()->isRefPicLongterm(i)) + if (pcSlice->getRpl(REF_PIC_LIST_0)->isRefPicLongterm(i)) { - if (pcSlice->getRPL0()->getLtrpInSliceHeaderFlag()) + if (pcSlice->getRpl(REF_PIC_LIST_0)->getLtrpInSliceHeaderFlag()) { - xWriteCode(pcSlice->getRPL0()->getRefPicIdentifier(i), pcSlice->getSPS()->getBitsForPOC(), + xWriteCode(pcSlice->getRpl(REF_PIC_LIST_0)->getRefPicIdentifier(i), pcSlice->getSPS()->getBitsForPOC(), "slice_poc_lsb_lt[listIdx][rplsIdx][j]"); } - xWriteFlag(pcSlice->getRPL0()->getDeltaPocMSBPresentFlag(i) ? 1 : 0, "delta_poc_msb_present_flag[i][j]"); - if (pcSlice->getRPL0()->getDeltaPocMSBPresentFlag(i)) + xWriteFlag(pcSlice->getRpl(REF_PIC_LIST_0)->getDeltaPocMSBPresentFlag(i) ? 1 : 0, + "delta_poc_msb_present_flag[i][j]"); + if (pcSlice->getRpl(REF_PIC_LIST_0)->getDeltaPocMSBPresentFlag(i)) { - xWriteUvlc(pcSlice->getRPL0()->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); + xWriteUvlc(pcSlice->getRpl(REF_PIC_LIST_0)->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); } } } } // Write L1 related syntax elements - if (pcSlice->getSPS()->getNumRPL1() > 0 && pcSlice->getPPS()->getRpl1IdxPresentFlag()) + if (pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_1) > 0 && pcSlice->getPPS()->getRpl1IdxPresentFlag()) { - xWriteFlag(pcSlice->getRPL1idx() != -1 ? 1 : 0, "ref_pic_list_sps_flag[1]"); + xWriteFlag(pcSlice->getRplIdx(REF_PIC_LIST_1) != -1 ? 1 : 0, "ref_pic_list_sps_flag[1]"); } - else if (pcSlice->getSPS()->getNumRPL1() == 0) + else if (pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_1) == 0) { - CHECK(pcSlice->getRPL1idx() != -1, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); + CHECK(pcSlice->getRplIdx(REF_PIC_LIST_1) != -1, + "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); } else { - auto rplsSpsFlag0 = pcSlice->getRPL0idx() != -1 ? 1 : 0; - auto rplsSpsFlag1 = pcSlice->getRPL1idx() != -1 ? 1 : 0; + auto rplsSpsFlag0 = pcSlice->getRplIdx(REF_PIC_LIST_0) != -1 ? 1 : 0; + auto rplsSpsFlag1 = pcSlice->getRplIdx(REF_PIC_LIST_1) != -1 ? 1 : 0; CHECK(rplsSpsFlag1 != rplsSpsFlag0, "rpl_sps_flag[1] will be infer to 0 and this is not what was expected"); } - if (pcSlice->getRPL1idx() != -1) + if (pcSlice->getRplIdx(REF_PIC_LIST_1) != -1) { - if (pcSlice->getSPS()->getNumRPL1() > 1 && pcSlice->getPPS()->getRpl1IdxPresentFlag()) + if (pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_1) > 1 && pcSlice->getPPS()->getRpl1IdxPresentFlag()) { - int numBits = 0; - while ((1 << numBits) < pcSlice->getSPS()->getNumRPL1()) - { - numBits++; - } - xWriteCode(pcSlice->getRPL1idx(), numBits, "ref_pic_list_idx[1]"); + int numBits = ceilLog2(pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_1)); + xWriteCode(pcSlice->getRplIdx(REF_PIC_LIST_1), numBits, "ref_pic_list_idx[1]"); } - else if (pcSlice->getSPS()->getNumRPL1() == 1) + else if (pcSlice->getSPS()->getNumRpl(REF_PIC_LIST_1) == 1) { - CHECK(pcSlice->getRPL1idx() != 0, "RPL1Idx is not signalled but it is not equal to 0"); + CHECK(pcSlice->getRplIdx(REF_PIC_LIST_1) != 0, "RPL1Idx is not signalled but it is not equal to 0"); } else { - CHECK(pcSlice->getRPL1idx() != pcSlice->getRPL0idx(), + CHECK(pcSlice->getRplIdx(REF_PIC_LIST_1) != pcSlice->getRplIdx(REF_PIC_LIST_0), "RPL1Idx is not signalled but it is not the same as RPL0Idx"); } } else { // write local RPL1 - xCodeRefPicList(pcSlice->getRPL1(), pcSlice->getSPS()->getLongTermRefsPresent(), + xCodeRefPicList(pcSlice->getRpl(REF_PIC_LIST_1), pcSlice->getSPS()->getLongTermRefsPresent(), pcSlice->getSPS()->getBitsForPOC(), !pcSlice->getSPS()->getUseWP() && !pcSlice->getSPS()->getUseWPBiPred(), -1); } // Deal POC Msb cycle signalling for LTRP - if (pcSlice->getRPL1()->getNumberOfLongtermPictures()) + if (pcSlice->getRpl(REF_PIC_LIST_1)->getNumberOfLongtermPictures()) { - for (int i = 0; - i < pcSlice->getRPL1()->getNumberOfLongtermPictures() + pcSlice->getRPL1()->getNumberOfShorttermPictures(); - i++) + for (int i = 0; i < pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries(); i++) { - if (pcSlice->getRPL1()->isRefPicLongterm(i)) + if (pcSlice->getRpl(REF_PIC_LIST_1)->isRefPicLongterm(i)) { - if (pcSlice->getRPL1()->getLtrpInSliceHeaderFlag()) + if (pcSlice->getRpl(REF_PIC_LIST_1)->getLtrpInSliceHeaderFlag()) { - xWriteCode(pcSlice->getRPL1()->getRefPicIdentifier(i), pcSlice->getSPS()->getBitsForPOC(), + xWriteCode(pcSlice->getRpl(REF_PIC_LIST_1)->getRefPicIdentifier(i), pcSlice->getSPS()->getBitsForPOC(), "slice_poc_lsb_lt[listIdx][rplsIdx][j]"); } - xWriteFlag(pcSlice->getRPL1()->getDeltaPocMSBPresentFlag(i) ? 1 : 0, "delta_poc_msb_present_flag[i][j]"); - if (pcSlice->getRPL1()->getDeltaPocMSBPresentFlag(i)) + xWriteFlag(pcSlice->getRpl(REF_PIC_LIST_1)->getDeltaPocMSBPresentFlag(i) ? 1 : 0, + "delta_poc_msb_present_flag[i][j]"); + if (pcSlice->getRpl(REF_PIC_LIST_1)->getDeltaPocMSBPresentFlag(i)) { - xWriteUvlc(pcSlice->getRPL1()->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); + xWriteUvlc(pcSlice->getRpl(REF_PIC_LIST_1)->getDeltaPocMSBCycleLT(i), "delta_poc_msb_cycle_lt[i][j]"); } } } @@ -2458,18 +2453,18 @@ void HLSWriter::codeSliceHeader ( Slice* pcSlice, PicHeader *picHeader ) CHECK(pcSlice->isIntra() && pcSlice->getNumRefIdx(REF_PIC_LIST_0) > 0, "Bad number of refs"); CHECK(!pcSlice->isInterB() && pcSlice->getNumRefIdx(REF_PIC_LIST_1) > 0, "Bad number of refs"); - if ((!pcSlice->isIntra() && pcSlice->getRPL0()->getNumRefEntries() > 1) - || (pcSlice->isInterB() && pcSlice->getRPL1()->getNumRefEntries() > 1)) + if ((!pcSlice->isIntra() && pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries() > 1) + || (pcSlice->isInterB() && pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 1)) { - const int defaultL0 = - std::min<int>(pcSlice->getRPL0()->getNumRefEntries(), pcSlice->getPPS()->getNumRefIdxL0DefaultActive()); + const int defaultL0 = std::min(pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries(), + pcSlice->getPPS()->getNumRefIdxDefaultActive(REF_PIC_LIST_0)); bool overrideFlag = pcSlice->getNumRefIdx(REF_PIC_LIST_0) != defaultL0; if (!overrideFlag && pcSlice->isInterB()) { - const int defaultL1 = - std::min<int>(pcSlice->getRPL1()->getNumRefEntries(), pcSlice->getPPS()->getNumRefIdxL1DefaultActive()); + const int defaultL1 = std::min(pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries(), + pcSlice->getPPS()->getNumRefIdxDefaultActive(REF_PIC_LIST_1)); overrideFlag = pcSlice->getNumRefIdx(REF_PIC_LIST_1) != defaultL1; } @@ -2477,12 +2472,12 @@ void HLSWriter::codeSliceHeader ( Slice* pcSlice, PicHeader *picHeader ) xWriteFlag(overrideFlag ? 1 : 0, "sh_num_ref_idx_active_override_flag"); if (overrideFlag) { - if (pcSlice->getRPL0()->getNumRefEntries() > 1) + if (pcSlice->getRpl(REF_PIC_LIST_0)->getNumRefEntries() > 1) { xWriteUvlc(pcSlice->getNumRefIdx(REF_PIC_LIST_0) - 1, "sh_num_ref_idx_active_minus1[0]"); } - if (pcSlice->isInterB() && pcSlice->getRPL1()->getNumRefEntries() > 1) + if (pcSlice->isInterB() && pcSlice->getRpl(REF_PIC_LIST_1)->getNumRefEntries() > 1) { xWriteUvlc(pcSlice->getNumRefIdx(REF_PIC_LIST_1) - 1, "sh_num_ref_idx_active_minus1[1]"); } @@ -2867,85 +2862,82 @@ void HLSWriter::xCodePredWeightTable( Slice* pcSlice ) const ChromaFormat format = pcSlice->getSPS()->getChromaFormatIdc(); const uint32_t numberValidComponents = getNumberValidComponents(format); const bool hasChroma = isChromaEnabled(format); - const int numLists = (pcSlice->getSliceType() == B_SLICE) ? 2 : 1; - bool denomCoded = false; uint32_t totalSignalledWeightFlags = 0; - if ( (pcSlice->getSliceType()==P_SLICE && pcSlice->getPPS()->getUseWP()) || (pcSlice->getSliceType()==B_SLICE && pcSlice->getPPS()->getWPBiPred()) ) + wp = pcSlice->getWpScaling(REF_PIC_LIST_0, 0); + + xWriteUvlc(wp[COMPONENT_Y].log2WeightDenom, "luma_log2_weight_denom"); + + if (hasChroma) + { + CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, + "Chroma blocks of different size not supported"); + const int deltaDenom = (wp[COMPONENT_Cb].log2WeightDenom - wp[COMPONENT_Y].log2WeightDenom); + xWriteSvlc(deltaDenom, "delta_chroma_log2_weight_denom"); + } + + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) { - for (int listIdx = 0; listIdx < numLists; listIdx++) // loop over l0 and l1 syntax elements + const bool l0 = l == REF_PIC_LIST_0; + + if (!l0 && !pcSlice->isInterB()) { - RefPicList eRefPicList = listIdx ? REF_PIC_LIST_1 : REF_PIC_LIST_0; + continue; + } - // NOTE: wp[].log2WeightDenom and wp[].presentFlag are actually per-channel-type settings. + // NOTE: wp[].log2WeightDenom and wp[].presentFlag are actually per-channel-type settings. - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) + { + wp = pcSlice->getWpScaling(l, refIdx); + xWriteFlag(wp[COMPONENT_Y].presentFlag, (l0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]")); + totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag; + } + if (hasChroma) + { + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) { - wp = pcSlice->getWpScaling(eRefPicList, refIdx); - if (!denomCoded) - { - int deltaDenom; - xWriteUvlc(wp[COMPONENT_Y].log2WeightDenom, "luma_log2_weight_denom"); - - if (hasChroma) - { - CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, - "Chroma blocks of different size not supported"); - deltaDenom = (wp[COMPONENT_Cb].log2WeightDenom - wp[COMPONENT_Y].log2WeightDenom); - xWriteSvlc(deltaDenom, "delta_chroma_log2_weight_denom"); - } - denomCoded = true; - } - xWriteFlag(wp[COMPONENT_Y].presentFlag, listIdx == 0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]"); - totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag; + wp = pcSlice->getWpScaling(l, refIdx); + CHECK(wp[COMPONENT_Cb].presentFlag != wp[COMPONENT_Cr].presentFlag, + "Inconsistent settings for chroma channels"); + xWriteFlag(wp[COMPONENT_Cb].presentFlag, (l0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]")); + totalSignalledWeightFlags += 2 * wp[COMPONENT_Cb].presentFlag; } - if (hasChroma) + } + + for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(l); refIdx++) + { + wp = pcSlice->getWpScaling(l, refIdx); + if (wp[COMPONENT_Y].presentFlag) { - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) - { - wp = pcSlice->getWpScaling(eRefPicList, refIdx); - CHECK(wp[COMPONENT_Cb].presentFlag != wp[COMPONENT_Cr].presentFlag, - "Inconsistent settings for chroma channels"); - xWriteFlag(wp[COMPONENT_Cb].presentFlag, - listIdx == 0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]"); - totalSignalledWeightFlags += 2 * wp[COMPONENT_Cb].presentFlag; - } + int deltaWeight = (wp[COMPONENT_Y].codedWeight - (1 << wp[COMPONENT_Y].log2WeightDenom)); + xWriteSvlc(deltaWeight, (l0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]")); + xWriteSvlc(wp[COMPONENT_Y].codedOffset, (l0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]")); } - for (int refIdx = 0; refIdx < pcSlice->getNumRefIdx(eRefPicList); refIdx++) + if (hasChroma) { - wp = pcSlice->getWpScaling(eRefPicList, refIdx); - if (wp[COMPONENT_Y].presentFlag) - { - int deltaWeight = (wp[COMPONENT_Y].codedWeight - (1 << wp[COMPONENT_Y].log2WeightDenom)); - xWriteSvlc(deltaWeight, listIdx == 0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]"); - xWriteSvlc(wp[COMPONENT_Y].codedOffset, listIdx == 0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]"); - } - - if (hasChroma) + if (wp[COMPONENT_Cb].presentFlag) { - if (wp[COMPONENT_Cb].presentFlag) + for (int j = COMPONENT_Cb; j < numberValidComponents; j++) { - for ( int j = COMPONENT_Cb ; j < numberValidComponents ; j++ ) - { - CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, - "Chroma blocks of different size not supported"); - int deltaWeight = (wp[j].codedWeight - (1 << wp[COMPONENT_Cb].log2WeightDenom)); - xWriteSvlc(deltaWeight, listIdx == 0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]"); - - int range = pcSlice->getSPS()->getSpsRangeExtension().getHighPrecisionOffsetsEnabledFlag() - ? (1 << pcSlice->getSPS()->getBitDepth(ChannelType::CHROMA)) / 2 - : 128; - int pred = (range - ((range * wp[j].codedWeight) >> (wp[j].log2WeightDenom))); - int deltaChroma = (wp[j].codedOffset - pred); - xWriteSvlc(deltaChroma, listIdx == 0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]"); - } + CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, + "Chroma blocks of different size not supported"); + int deltaWeight = (wp[j].codedWeight - (1 << wp[COMPONENT_Cb].log2WeightDenom)); + xWriteSvlc(deltaWeight, (l0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]")); + + int range = pcSlice->getSPS()->getSpsRangeExtension().getHighPrecisionOffsetsEnabledFlag() + ? (1 << pcSlice->getSPS()->getBitDepth(ChannelType::CHROMA)) / 2 + : 128; + int pred = (range - ((range * wp[j].codedWeight) >> (wp[j].log2WeightDenom))); + int deltaChroma = (wp[j].codedOffset - pred); + xWriteSvlc(deltaChroma, (l0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]")); } } } } - CHECK(totalSignalledWeightFlags > 24, "Too many signalled weight flags"); } + CHECK(totalSignalledWeightFlags > 24, "Too many signalled weight flags"); } void HLSWriter::xCodePredWeightTable(PicHeader *picHeader, const PPS *pps, const SPS *sps) @@ -2954,56 +2946,57 @@ void HLSWriter::xCodePredWeightTable(PicHeader *picHeader, const PPS *pps, const const ChromaFormat format = sps->getChromaFormatIdc(); const uint32_t numberValidComponents = getNumberValidComponents(format); const bool chroma = isChromaEnabled(format); - bool denomCoded = false; uint32_t totalSignalledWeightFlags = 0; - uint32_t numLxWeights = picHeader->getNumL0Weights(); - bool moreSyntaxToBeParsed = true; - for (int numRef = 0; numRef < NUM_REF_PIC_LIST_01 && moreSyntaxToBeParsed; numRef++) // loop over l0 and l1 syntax elements + wp = picHeader->getWpScaling(REF_PIC_LIST_0, 0); + xWriteUvlc(wp[COMPONENT_Y].log2WeightDenom, "luma_log2_weight_denom"); + + if (chroma) { - RefPicList refPicList = (numRef ? REF_PIC_LIST_1 : REF_PIC_LIST_0); - // NOTE: wp[].log2WeightDenom and wp[].presentFlag are actually per-channel-type settings. + CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, + "Chroma blocks of different size not supported"); + const int deltaDenom = (wp[COMPONENT_Cb].log2WeightDenom - wp[COMPONENT_Y].log2WeightDenom); + xWriteSvlc(deltaDenom, "delta_chroma_log2_weight_denom"); + } - for (int refIdx = 0; refIdx < numLxWeights; refIdx++) + for (const auto l: { REF_PIC_LIST_0, REF_PIC_LIST_1 }) + { + const bool l0 = l == REF_PIC_LIST_0; + + int numLxWeights = 0; + if (l0 || pps->getWPBiPred()) { - wp = picHeader->getWpScaling(refPicList, refIdx); - if (!denomCoded) - { - int deltaDenom; - xWriteUvlc(wp[COMPONENT_Y].log2WeightDenom, "luma_log2_weight_denom"); + numLxWeights = picHeader->getNumWeights(l); + xWriteUvlc(numLxWeights, (l0 ? "num_l0_weights" : "num_l1_weights")); + } - if (chroma) - { - CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, - "Chroma blocks of different size not supported"); - deltaDenom = (wp[COMPONENT_Cb].log2WeightDenom - wp[COMPONENT_Y].log2WeightDenom); - xWriteSvlc(deltaDenom, "delta_chroma_log2_weight_denom"); - } - denomCoded = true; - } - xWriteFlag(wp[COMPONENT_Y].presentFlag, numRef == 0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]"); + for (int refIdx = 0; refIdx < numLxWeights; refIdx++) + { + wp = picHeader->getWpScaling(l, refIdx); + xWriteFlag(wp[COMPONENT_Y].presentFlag, (l0 ? "luma_weight_l0_flag[i]" : "luma_weight_l1_flag[i]")); totalSignalledWeightFlags += wp[COMPONENT_Y].presentFlag; } + if (chroma) { for (int refIdx = 0; refIdx < numLxWeights; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); + wp = picHeader->getWpScaling(l, refIdx); CHECK(wp[COMPONENT_Cb].presentFlag != wp[COMPONENT_Cr].presentFlag, "Inconsistent settings for chroma channels"); - xWriteFlag(wp[COMPONENT_Cb].presentFlag, numRef == 0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]"); + xWriteFlag(wp[COMPONENT_Cb].presentFlag, (l0 ? "chroma_weight_l0_flag[i]" : "chroma_weight_l1_flag[i]")); totalSignalledWeightFlags += 2 * wp[COMPONENT_Cb].presentFlag; } } for (int refIdx = 0; refIdx < numLxWeights; refIdx++) { - wp = picHeader->getWpScaling(refPicList, refIdx); + wp = picHeader->getWpScaling(l, refIdx); if (wp[COMPONENT_Y].presentFlag) { int deltaWeight = (wp[COMPONENT_Y].codedWeight - (1 << wp[COMPONENT_Y].log2WeightDenom)); - xWriteSvlc(deltaWeight, numRef == 0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]"); - xWriteSvlc(wp[COMPONENT_Y].codedOffset, numRef == 0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]"); + xWriteSvlc(deltaWeight, (l0 ? "delta_luma_weight_l0[i]" : "delta_luma_weight_l1[i]")); + xWriteSvlc(wp[COMPONENT_Y].codedOffset, (l0 ? "luma_offset_l0[i]" : "luma_offset_l1[i]")); } if (chroma) @@ -3015,32 +3008,20 @@ void HLSWriter::xCodePredWeightTable(PicHeader *picHeader, const PPS *pps, const CHECK(wp[COMPONENT_Cb].log2WeightDenom != wp[COMPONENT_Cr].log2WeightDenom, "Chroma blocks of different size not supported"); int deltaWeight = (wp[j].codedWeight - (1 << wp[COMPONENT_Cb].log2WeightDenom)); - xWriteSvlc(deltaWeight, numRef == 0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]"); + xWriteSvlc(deltaWeight, (l0 ? "delta_chroma_weight_l0[i]" : "delta_chroma_weight_l1[i]")); int range = sps->getSpsRangeExtension().getHighPrecisionOffsetsEnabledFlag() ? (1 << sps->getBitDepth(ChannelType::CHROMA)) / 2 : 128; int pred = (range - ((range * wp[j].codedWeight) >> (wp[j].log2WeightDenom))); int deltaChroma = (wp[j].codedOffset - pred); - xWriteSvlc(deltaChroma, numRef == 0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]"); + xWriteSvlc(deltaChroma, (l0 ? "delta_chroma_offset_l0[i]" : "delta_chroma_offset_l1[i]")); } } } } - if (numRef == 0) - { - numLxWeights = picHeader->getNumL1Weights(); - if (pps->getWPBiPred() == 0) - { - numLxWeights = 0; - } - else if (picHeader->getRPL(1)->getNumRefEntries() > 0) - { - xWriteUvlc(numLxWeights, "num_l1_weights"); - } - moreSyntaxToBeParsed = (numLxWeights == 0) ? false : true; - } } + CHECK(totalSignalledWeightFlags > 24, "Too many signalled weight flags"); }