History

add freely setoption for EC_idc and UT

huili2 committed 12 years ago

Commit f6fb4591 parent 25b723c4 files · +655 −9Browse files

Showing the changes to test/api/encode_decode_api_test.cpp (1 of 4 files). Show all

Unified · Split

test/api/encode_decode_api_test.cpp+627−0
@@ -62,6 +62,14 @@ class EncodeDecodeTestBase : public ::testing::TestWithParam<EncodeDecodeFilePar · 61 unmodified lines
6262 }
6363 }
6464
65+ virtual void encToDecSliceData (const int iLayerNum, const int iSliceNum, const SFrameBSInfo& info, int& len) {
66+ ASSERT_TRUE (iLayerNum < MAX_LAYER_NUM_OF_FRAME);
67+ len = 0;
68+ const SLayerBSInfo& layerInfo = info.sLayerInfo[iLayerNum];
69+ if (iSliceNum < layerInfo.iNalCount)
70+ len = layerInfo.pNalLengthInByte[iSliceNum];
71+ }
72+
6573 protected:
6674 SEncParamExt param_;
6775 BufferedData buf_;
@@ -739,3 +747,622 @@ TEST_P (EncodeDecodeTestAPI, SetOptionECFlag_ERROR_CON_SLICE_COPY) { · 671 unmodified lines
739747
740748 INSTANTIATE_TEST_CASE_P (EncodeDecodeTestBase, EncodeDecodeTestAPI,
741749 ::testing::ValuesIn (kFileParamArray));
750+
751+TEST_P (EncodeDecodeTestAPI, SetOptionECIDC_GeneralSliceChange) {
752+ uint32_t uiEcIdc;
753+ uint32_t uiGet;
754+ EncodeDecodeFileParamBase p = GetParam();
755+ prepareParam (p.width, p.height, p.frameRate);
756+ param_.sSpatialLayers[0].sSliceCfg.uiSliceMode = SM_FIXEDSLCNUM_SLICE;
757+ param_.sSpatialLayers[0].sSliceCfg.sSliceArgument.uiSliceNum = p.slicenum;
758+ encoder_->Uninitialize();
759+ int rv = encoder_->InitializeExt (&param_);
760+ ASSERT_TRUE (rv == cmResultSuccess);
761+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
762+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
763+
764+ uiEcIdc = 0;
765+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
766+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
767+ EXPECT_EQ (uiGet, uiEcIdc);
768+
769+ //Start for enc/dec
770+ int frameSize = p.width * p.height * 3 / 2;
771+ buf_.SetLength (frameSize);
772+ ASSERT_TRUE (buf_.Length() == (size_t)frameSize);
773+ SFrameBSInfo info;
774+ memset (&info, 0, sizeof (SFrameBSInfo));
775+
776+ SSourcePicture pic;
777+ memset (&pic, 0, sizeof (SSourcePicture));
778+ pic.iPicWidth = p.width;
779+ pic.iPicHeight = p.height;
780+ pic.iColorFormat = videoFormatI420;
781+ pic.iStride[0] = pic.iPicWidth;
782+ pic.iStride[1] = pic.iStride[2] = pic.iPicWidth >> 1;
783+ pic.pData[0] = buf_.data();
784+ pic.pData[1] = pic.pData[0] + p.width * p.height;
785+ pic.pData[2] = pic.pData[1] + (p.width * p.height >> 2);
786+ int32_t iTraceLevel = WELS_LOG_QUIET;
787+ encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
788+ decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
789+ int iIdx = 0;
790+ bool bVCLLoss = false;
791+ int iPacketNum;
792+ int len;
793+ int iTotalSliceSize;
794+
795+ //enc/dec pictures
796+ while (iIdx <= p.numframes) {
797+ memset (buf_.data(), rand() % 256, frameSize);
798+ rv = encoder_->EncodeFrame (&pic, &info);
799+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
800+ //decoding after each encoding frame
801+ len = 0;
802+ iPacketNum = 0;
803+ iTotalSliceSize = 0;
804+ unsigned char* pData[3] = { NULL };
805+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
806+ while (iPacketNum < info.sLayerInfo[0].iNalCount) {
807+ encToDecSliceData (0, iPacketNum, info, len);
808+ uiEcIdc = (ERROR_CON_IDC) (rand() % 2);
809+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
810+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
811+ EXPECT_EQ (uiGet, uiEcIdc);
812+
813+ bVCLLoss = rand() & 1; //loss or not
814+ if (!bVCLLoss) { //not loss
815+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize,
816+ info.sLayerInfo[0].pNalLengthInByte[iPacketNum], pData, &dstBufInfo_);
817+ if (uiEcIdc == ERROR_CON_DISABLE)
818+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
819+ }
820+ //EC_IDC should not change till now
821+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
822+ EXPECT_EQ (uiGet, uiEcIdc);
823+ //Set again inside
824+ uiEcIdc = (ERROR_CON_IDC) (rand() % 2);
825+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
826+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
827+ EXPECT_EQ (uiGet, uiEcIdc);
828+
829+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
830+ //EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
831+ if (uiEcIdc == ERROR_CON_DISABLE && rv != 0)
832+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
833+
834+ //deal with next slice
835+ iTotalSliceSize += len;
836+ iPacketNum++;
837+ } //while slice
838+ iIdx++;
839+ } //while frame
840+}
841+
842+//This case contain 1 slice per picture
843+//coding order: 0 1 2 3 4 5 6 7
844+//frame type: IDR P P P P P P P
845+//EC_IDC: 0 0 0 2 0 0 1 1
846+//loss: N Y N N N Y Y N
847+
848+TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificFrameChange) {
849+ uint32_t uiEcIdc;
850+ uint32_t uiGet;
851+ EncodeDecodeFileParamBase p = kFileParamArray[0];
852+ prepareParam (p.width, p.height, p.frameRate);
853+ param_.sSpatialLayers[0].sSliceCfg.uiSliceMode = SM_SINGLE_SLICE;
854+ param_.sSpatialLayers[0].sSliceCfg.sSliceArgument.uiSliceNum = p.slicenum;
855+ encoder_->Uninitialize();
856+ int rv = encoder_->InitializeExt (&param_);
857+ ASSERT_TRUE (rv == cmResultSuccess);
858+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
859+ EXPECT_EQ (uiGet, (ERROR_CON_IDC) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
860+ int32_t iTraceLevel = WELS_LOG_QUIET;
861+ encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
862+ decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
863+
864+ //set EC=DISABLE
865+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
866+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
867+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
868+ EXPECT_EQ (uiGet, uiEcIdc);
869+
870+ //Start for enc/dec
871+ int frameSize = p.width * p.height * 3 / 2;
872+ buf_.SetLength (frameSize);
873+ ASSERT_TRUE (buf_.Length() == (size_t)frameSize);
874+ SFrameBSInfo info;
875+ memset (&info, 0, sizeof (SFrameBSInfo));
876+
877+ SSourcePicture pic;
878+ memset (&pic, 0, sizeof (SSourcePicture));
879+ pic.iPicWidth = p.width;
880+ pic.iPicHeight = p.height;
881+ pic.iColorFormat = videoFormatI420;
882+ pic.iStride[0] = pic.iPicWidth;
883+ pic.iStride[1] = pic.iStride[2] = pic.iPicWidth >> 1;
884+ pic.pData[0] = buf_.data();
885+ pic.pData[1] = pic.pData[0] + p.width * p.height;
886+ pic.pData[2] = pic.pData[1] + (p.width * p.height >> 2);
887+ int iIdx = 0;
888+ int len = 0;
889+ unsigned char* pData[3] = { NULL };
890+
891+ //Frame 0: IDR, EC_IDC=DISABLE, loss = 0
892+ memset (buf_.data(), rand() % 256, frameSize);
893+ rv = encoder_->EncodeFrame (&pic, &info);
894+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
895+ encToDecData (info, len);
896+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
897+ EXPECT_EQ (uiGet, (ERROR_CON_IDC) ERROR_CON_DISABLE);
898+ pData[0] = pData[1] = pData[2] = 0;
899+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
900+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
901+ EXPECT_EQ (rv, 0);
902+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
903+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
904+ EXPECT_EQ (rv, 0);
905+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
906+ iIdx++;
907+
908+ //Frame 1: P, EC_IDC=DISABLE, loss = 1
909+ memset (buf_.data(), rand() % 256, frameSize);
910+ rv = encoder_->EncodeFrame (&pic, &info);
911+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
912+ iIdx++;
913+
914+ //Frame 2: P, EC_IDC=DISABLE, loss = 0
915+ memset (buf_.data(), rand() % 256, frameSize);
916+ rv = encoder_->EncodeFrame (&pic, &info);
917+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
918+ encToDecData (info, len);
919+ pData[0] = pData[1] = pData[2] = 0;
920+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
921+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
922+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
923+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
924+ EXPECT_EQ (rv, 0); //parse correct
925+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
926+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
927+ EXPECT_TRUE (rv != 0); //construction error due to data loss
928+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output due to EC DISABLE
929+ iIdx++;
930+
931+ //set EC=SLICE_COPY
932+ uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
933+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
934+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
935+ EXPECT_EQ (uiGet, uiEcIdc);
936+ //Frame 3: P, EC_IDC=SLICE_COPY, loss = 0
937+ memset (buf_.data(), rand() % 256, frameSize);
938+ rv = encoder_->EncodeFrame (&pic, &info);
939+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
940+ encToDecData (info, len);
941+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
942+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
943+ pData[0] = pData[1] = pData[2] = 0;
944+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
945+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
946+ EXPECT_EQ (rv, 0); //parse correct
947+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
948+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
949+ EXPECT_TRUE (rv != 0); //construction error due to data loss
950+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
951+ iIdx++;
952+
953+ //set EC=DISABLE
954+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
955+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
956+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
957+ EXPECT_EQ (uiGet, uiEcIdc);
958+ //Frame 4: P, EC_IDC=DISABLE, loss = 0
959+ memset (buf_.data(), rand() % 256, frameSize);
960+ rv = encoder_->EncodeFrame (&pic, &info);
961+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
962+ encToDecData (info, len);
963+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
964+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
965+ pData[0] = pData[1] = pData[2] = 0;
966+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
967+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
968+ EXPECT_EQ (rv, 0); //parse correct
969+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
970+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
971+ if (rv == 0) //TODO: should depend on if ref-frame is OK.
972+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
973+ else
974+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
975+ iIdx++;
976+
977+ //Frame 5: P, EC_IDC=DISABLE, loss = 1
978+ memset (buf_.data(), rand() % 256, frameSize);
979+ rv = encoder_->EncodeFrame (&pic, &info);
980+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
981+ iIdx++;
982+
983+ //set EC=FRAME_COPY
984+ uiEcIdc = (uint32_t) (ERROR_CON_FRAME_COPY);
985+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
986+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
987+ EXPECT_EQ (uiGet, uiEcIdc);
988+ //Frame 6: P, EC_IDC=FRAME_COPY, loss = 1
989+ memset (buf_.data(), rand() % 256, frameSize);
990+ rv = encoder_->EncodeFrame (&pic, &info);
991+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
992+ EXPECT_EQ (uiGet, uiEcIdc);
993+ iIdx++;
994+
995+ //Frame 7: P, EC_IDC=FRAME_COPY, loss = 0
996+ memset (buf_.data(), rand() % 256, frameSize);
997+ rv = encoder_->EncodeFrame (&pic, &info);
998+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
999+ encToDecData (info, len);
1000+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1001+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_FRAME_COPY);
1002+ pData[0] = pData[1] = pData[2] = 0;
1003+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1004+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1005+ EXPECT_TRUE (rv != 0); //parse correct, but previous decoding error, ECed
1006+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
1007+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1008+ EXPECT_TRUE (rv != 0); //not sure if previous data drop would be detected in construction
1009+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
1010+ iIdx++;
1011+
1012+}
1013+
1014+//This case contain 2 slices per picture for IDR loss
1015+//coding order: 0 1 2 3 4
1016+//frame type IDR P P P P
1017+//EC_IDC 2 2 0 1 0
1018+//loss (2 slice: 1,2): 2 0 0 1 0
1019+
1020+TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificSliceChange_IDRLoss) {
1021+ uint32_t uiEcIdc;
1022+ uint32_t uiGet;
1023+ EncodeDecodeFileParamBase p = kFileParamArray[0];
1024+ prepareParam (p.width, p.height, p.frameRate);
1025+ param_.sSpatialLayers[0].sSliceCfg.uiSliceMode = SM_FIXEDSLCNUM_SLICE;
1026+ param_.sSpatialLayers[0].sSliceCfg.sSliceArgument.uiSliceNum = 2;
1027+ encoder_->Uninitialize();
1028+ int rv = encoder_->InitializeExt (&param_);
1029+ ASSERT_TRUE (rv == cmResultSuccess);
1030+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1031+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
1032+ int32_t iTraceLevel = WELS_LOG_QUIET;
1033+ encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
1034+ decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
1035+
1036+ //Start for enc/dec
1037+ int frameSize = p.width * p.height * 3 / 2;
1038+ buf_.SetLength (frameSize);
1039+ ASSERT_TRUE (buf_.Length() == (size_t)frameSize);
1040+ SFrameBSInfo info;
1041+ memset (&info, 0, sizeof (SFrameBSInfo));
1042+
1043+ SSourcePicture pic;
1044+ memset (&pic, 0, sizeof (SSourcePicture));
1045+ pic.iPicWidth = p.width;
1046+ pic.iPicHeight = p.height;
1047+ pic.iColorFormat = videoFormatI420;
1048+ pic.iStride[0] = pic.iPicWidth;
1049+ pic.iStride[1] = pic.iStride[2] = pic.iPicWidth >> 1;
1050+ pic.pData[0] = buf_.data();
1051+ pic.pData[1] = pic.pData[0] + p.width * p.height;
1052+ pic.pData[2] = pic.pData[1] + (p.width * p.height >> 2);
1053+ int iIdx = 0;
1054+ int len = 0;
1055+ unsigned char* pData[3] = { NULL };
1056+ int iTotalSliceSize = 0;
1057+
1058+ //Frame 0: IDR, EC_IDC=2, loss = 2
1059+ memset (buf_.data(), rand() % 256, frameSize);
1060+ rv = encoder_->EncodeFrame (&pic, &info);
1061+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1062+ iTotalSliceSize = 0;
1063+ encToDecSliceData (0, 0, info, len); //SPS
1064+ iTotalSliceSize = len;
1065+ encToDecSliceData (0, 1, info, len); //PPS
1066+ iTotalSliceSize += len;
1067+ encToDecSliceData (1, 0, info, len); //first slice
1068+ iTotalSliceSize += len;
1069+ //second slice loss
1070+ pData[0] = pData[1] = pData[2] = 0;
1071+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1072+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1073+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
1074+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, iTotalSliceSize, pData, &dstBufInfo_);
1075+ EXPECT_EQ (rv, 0); //parse correct
1076+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1077+ EXPECT_EQ (rv, 0); //parse correct
1078+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice incomplete, no output
1079+ iIdx++;
1080+
1081+ //Frame 1: P, EC_IDC=2, loss = 0
1082+ //will clean SPS/PPS status
1083+ memset (buf_.data(), rand() % 256, frameSize);
1084+ rv = encoder_->EncodeFrame (&pic, &info);
1085+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1086+ encToDecData (info, len); //all slice together
1087+ pData[0] = pData[1] = pData[2] = 0;
1088+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1089+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1090+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
1091+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1092+ EXPECT_TRUE (rv & 32); //parse correct, but reconstruct ECed
1093+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 0
1094+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //ECed status, reconstruction current frame 1
1095+ EXPECT_TRUE (rv & 32); //decoder ECed status
1096+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 1
1097+ iIdx++;
1098+
1099+ //set EC=DISABLE
1100+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
1101+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1102+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1103+ EXPECT_EQ (uiGet, uiEcIdc);
1104+ //Frame 2: P, EC_IDC=0, loss = 0
1105+ /////will clean SPS/PPS status
1106+ memset (buf_.data(), rand() % 256, frameSize);
1107+ rv = encoder_->EncodeFrame (&pic, &info);
1108+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1109+ encToDecData (info, len); //all slice together
1110+ pData[0] = pData[1] = pData[2] = 0;
1111+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1112+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1113+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1114+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1115+ EXPECT_EQ (rv, 0); //parse correct
1116+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1117+ if (rv == 0) //TODO: should depend on if ref-frame is OK.
1118+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
1119+ else
1120+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
1121+ iIdx++;
1122+
1123+ //set EC=SLICE_COPY
1124+ uiEcIdc = (uint32_t) (ERROR_CON_FRAME_COPY);
1125+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1126+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1127+ EXPECT_EQ (uiGet, uiEcIdc);
1128+ //Frame 3: P, EC_IDC=2, loss = 1
1129+ memset (buf_.data(), rand() % 256, frameSize);
1130+ rv = encoder_->EncodeFrame (&pic, &info);
1131+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1132+ encToDecSliceData (0, 0, info, iTotalSliceSize); //slice 1 lost
1133+ encToDecSliceData (0, 1, info, len); //slice 2
1134+ pData[0] = pData[1] = pData[2] = 0;
1135+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1136+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1137+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_FRAME_COPY);
1138+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
1139+ EXPECT_TRUE (rv & 32);
1140+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
1141+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1142+ EXPECT_TRUE (rv & 32);
1143+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice loss
1144+ iIdx++;
1145+
1146+ //set EC=DISABLE
1147+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
1148+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1149+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1150+ EXPECT_EQ (uiGet, uiEcIdc);
1151+ //Frame 4: P, EC_IDC=0, loss = 0
1152+ memset (buf_.data(), rand() % 256, frameSize);
1153+ rv = encoder_->EncodeFrame (&pic, &info);
1154+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1155+ encToDecData (info, len); //all slice
1156+ pData[0] = pData[1] = pData[2] = 0;
1157+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1158+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1159+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1160+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1161+ EXPECT_TRUE (rv != 0);
1162+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
1163+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1164+ EXPECT_TRUE (rv != 0);
1165+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
1166+ iIdx++;
1167+
1168+}
1169+
1170+
1171+
1172+//This case contain 2 slices per picture for no IDR loss
1173+//coding order: 0 1 2 3 4 5
1174+//frame type IDR P P P P IDR
1175+//EC_IDC 0 2 0 2 0 ^2^
1176+//loss (2 slice: 1,2): 0 0 1 2 0 0
1177+
1178+TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificSliceChange_IDRNoLoss) {
1179+ uint32_t uiEcIdc;
1180+ uint32_t uiGet;
1181+ EncodeDecodeFileParamBase p = kFileParamArray[0];
1182+ prepareParam (p.width, p.height, p.frameRate);
1183+ param_.sSpatialLayers[0].sSliceCfg.uiSliceMode = SM_FIXEDSLCNUM_SLICE;
1184+ param_.sSpatialLayers[0].sSliceCfg.sSliceArgument.uiSliceNum = 2;
1185+ encoder_->Uninitialize();
1186+ int rv = encoder_->InitializeExt (&param_);
1187+ ASSERT_TRUE (rv == cmResultSuccess);
1188+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1189+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
1190+ int32_t iTraceLevel = WELS_LOG_QUIET;
1191+ encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
1192+ decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
1193+
1194+ //Start for enc/dec
1195+ int frameSize = p.width * p.height * 3 / 2;
1196+ buf_.SetLength (frameSize);
1197+ ASSERT_TRUE (buf_.Length() == (size_t)frameSize);
1198+ SFrameBSInfo info;
1199+ memset (&info, 0, sizeof (SFrameBSInfo));
1200+
1201+ SSourcePicture pic;
1202+ memset (&pic, 0, sizeof (SSourcePicture));
1203+ pic.iPicWidth = p.width;
1204+ pic.iPicHeight = p.height;
1205+ pic.iColorFormat = videoFormatI420;
1206+ pic.iStride[0] = pic.iPicWidth;
1207+ pic.iStride[1] = pic.iStride[2] = pic.iPicWidth >> 1;
1208+ pic.pData[0] = buf_.data();
1209+ pic.pData[1] = pic.pData[0] + p.width * p.height;
1210+ pic.pData[2] = pic.pData[1] + (p.width * p.height >> 2);
1211+ int iIdx = 0;
1212+ int len = 0;
1213+ unsigned char* pData[3] = { NULL };
1214+ int iTotalSliceSize = 0;
1215+
1216+ //set EC=DISABLE
1217+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
1218+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1219+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1220+ EXPECT_EQ (uiGet, uiEcIdc);
1221+ //Frame 0: IDR, EC_IDC=0, loss = 0
1222+ //Expected result: all OK, 2nd Output
1223+ memset (buf_.data(), rand() % 256, frameSize);
1224+ rv = encoder_->EncodeFrame (&pic, &info);
1225+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1226+ encToDecData (info, len); //all slice
1227+ pData[0] = pData[1] = pData[2] = 0;
1228+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1229+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1230+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1231+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1232+ EXPECT_EQ (rv, 0); //parse correct
1233+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1234+ EXPECT_EQ (rv, 0); //parse correct
1235+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //output frame 0
1236+ iIdx++;
1237+
1238+ //Frame 1: P, EC_IDC=0, loss = 0
1239+ //Expected result: all OK, 2nd Output
1240+ memset (buf_.data(), rand() % 256, frameSize);
1241+ rv = encoder_->EncodeFrame (&pic, &info);
1242+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1243+ encToDecData (info, len); //all slice together
1244+ pData[0] = pData[1] = pData[2] = 0;
1245+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1246+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1247+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1248+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1249+ EXPECT_EQ (rv, 0); //parse correct
1250+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //ECed output for frame 0
1251+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction current frame 1
1252+ EXPECT_EQ (rv, 0); //parse correct
1253+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 1
1254+ iIdx++;
1255+
1256+ //Frame 2: P, EC_IDC=0, loss = 1
1257+ //Expected result: all OK, no Output
1258+ memset (buf_.data(), rand() % 256, frameSize);
1259+ rv = encoder_->EncodeFrame (&pic, &info);
1260+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1261+ encToDecSliceData (0, 0, info, iTotalSliceSize); // slice 1 lost
1262+ encToDecSliceData (0, 1, info, len); // slice 2 only
1263+ pData[0] = pData[1] = pData[2] = 0;
1264+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1265+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1266+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1267+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
1268+ EXPECT_EQ (rv, 0); //parse correct
1269+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
1270+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1271+ EXPECT_EQ (rv, 0); //parse correct
1272+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
1273+ iIdx++;
1274+
1275+ //set EC=SLICE_COPY
1276+ uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
1277+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1278+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1279+ EXPECT_EQ (uiGet, uiEcIdc);
1280+ //Frame 3: P, EC_IDC=2, loss = 2
1281+ //Expected result: neither OK, 1st Output
1282+ memset (buf_.data(), rand() % 256, frameSize);
1283+ rv = encoder_->EncodeFrame (&pic, &info);
1284+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1285+ encToDecSliceData (0, 0, info, len); //slice 1 only
1286+ pData[0] = pData[1] = pData[2] = 0;
1287+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1288+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1289+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
1290+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1291+ EXPECT_TRUE (rv & 32); //ECed
1292+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //slice loss but ECed output Frame 2
1293+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
1294+ EXPECT_TRUE (rv & 32);
1295+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice loss
1296+ iIdx++;
1297+
1298+ //set EC=DISABLE
1299+ uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
1300+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1301+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1302+ EXPECT_EQ (uiGet, uiEcIdc);
1303+ //Frame 4: P, EC_IDC=0, loss = 0
1304+ //Expected result: depends on DecodeFrame2 result. If OK, output; else ,no output
1305+ memset (buf_.data(), rand() % 256, frameSize);
1306+ rv = encoder_->EncodeFrame (&pic, &info);
1307+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1308+ encToDecData (info, len); //all slice
1309+ pData[0] = pData[1] = pData[2] = 0;
1310+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1311+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1312+ EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
1313+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
1314+ EXPECT_TRUE (rv != 0); //previous slice not outputted, will return error due to incomplete frame
1315+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
1316+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
1317+ //not sure if current frame can be correctly decoded
1318+ if (rv == 0)
1319+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //output previous pic
1320+ else
1321+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
1322+ iIdx++;
1323+
1324+ //Frame 5: IDR, EC_IDC=2->0, loss = 0
1325+ //Expected result: depends on DecodeFrame2 result. If OK, output; else ,no output
1326+ int32_t iIDRPeriod = 1;
1327+ encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
1328+ memset (buf_.data(), rand() % 256, frameSize);
1329+ rv = encoder_->EncodeFrame (&pic, &info);
1330+ ASSERT_TRUE (rv == cmResultSuccess || rv == cmUnkonwReason);
1331+ EXPECT_TRUE (info.eFrameType == videoFrameTypeIDR);
1332+ encToDecSliceData (0, 0, info, len); //SPS
1333+ iTotalSliceSize = len;
1334+ encToDecSliceData (0, 1, info, len); //PPS
1335+ iTotalSliceSize += len;
1336+ encToDecSliceData (1, 0, info, len); //slice 1
1337+ iTotalSliceSize += len;
1338+ //set EC=SLICE_COPY for slice 1
1339+ uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
1340+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1341+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1342+ EXPECT_EQ (uiGet, uiEcIdc);
1343+ pData[0] = pData[1] = pData[2] = 0;
1344+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1345+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, iTotalSliceSize, pData, &dstBufInfo_);
1346+ EXPECT_TRUE (rv != 0); //TODO: should be correct, now ECed status will return error
1347+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //frame incomplete
1348+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
1349+ EXPECT_TRUE (rv != 0); //TODO: as above
1350+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
1351+ //set EC=DISABLE for slice 2
1352+ encToDecSliceData (1, 1, info, len); //slice 1
1353+ uiEcIdc = (int) (ERROR_CON_DISABLE);
1354+ decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
1355+ decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
1356+ EXPECT_EQ (uiGet, uiEcIdc);
1357+ pData[0] = pData[1] = pData[2] = 0;
1358+ memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
1359+ rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
1360+ EXPECT_EQ (rv, 0); //Parse correct under no EC
1361+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //frame incomplete
1362+ rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
1363+ EXPECT_EQ (rv, 0); //Parse correct under no EC
1364+ EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //output previous pic
1365+ iIdx++;
1366+
1367+}
1368+

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t