1 #include <gtest/gtest.h>
2 #include "codec_def.h"
3 #include "utils/BufferedData.h"
4 #include "utils/FileInputStream.h"
5 #include "BaseDecoderTest.h"
6 #include "BaseEncoderTest.h"
7 #include "wels_common_defs.h"
8 #include <string>
9 #include <vector>
10 #include "encode_decode_api_test.h"
11 using namespace WelsCommon;
12
TEST_P(EncodeDecodeTestAPI,SetOptionECFlag_ERROR_CON_DISABLE)13 TEST_P (EncodeDecodeTestAPI, SetOptionECFlag_ERROR_CON_DISABLE) {
14 SLTRMarkingFeedback m_LTR_Marking_Feedback;
15 SLTRRecoverRequest m_LTR_Recover_Request;
16 m_LTR_Recover_Request.uiIDRPicId = 0;
17 m_LTR_Recover_Request.iLayerId = 0;
18 m_LTR_Marking_Feedback.iLayerId = 0;
19 EncodeDecodeFileParamBase p = GetParam();
20 prepareParamDefault (1, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
21 param_.bEnableLongTermReference = true;
22 param_.iLTRRefNum = 1;
23 encoder_->Uninitialize();
24 int rv = encoder_->InitializeExt (¶m_);
25 ASSERT_TRUE (rv == cmResultSuccess);
26 if (decoder_ != NULL) {
27 decoder_->Uninitialize();
28 }
29 SDecodingParam decParam;
30 memset (&decParam, 0, sizeof (SDecodingParam));
31 decParam.uiTargetDqLayer = UCHAR_MAX;
32 decParam.eEcActiveIdc = ERROR_CON_DISABLE;
33 decParam.sVideoProperty.eVideoBsType = VIDEO_BITSTREAM_DEFAULT;
34 rv = decoder_->Initialize (&decParam);
35 ASSERT_EQ (0, rv);
36 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
37
38 ASSERT_TRUE (InitialEncDec (p.width, p.height));
39 int32_t iTraceLevel = WELS_LOG_QUIET;
40 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
41 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
42 int32_t iSpsPpsIdAddition = 1;
43 encoder_->SetOption (ENCODER_OPTION_SPS_PPS_ID_STRATEGY, &iSpsPpsIdAddition);
44 int32_t iIDRPeriod = 60;
45 encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
46 SLTRConfig sLtrConfigVal;
47 sLtrConfigVal.bEnableLongTermReference = 1;
48 sLtrConfigVal.iLTRRefNum = 1;
49 encoder_->SetOption (ENCODER_OPTION_LTR, &sLtrConfigVal);
50 int32_t iLtrPeriod = 2;
51 encoder_->SetOption (ENCODER_LTR_MARKING_PERIOD, &iLtrPeriod);
52 int iIdx = 0;
53 int iLossIdx = 0;
54 int iSkipedBytes;
55 bool bVCLLoss = false;
56 while (iIdx <= p.numframes) {
57 EncodeOneFrame (1);
58 if (m_LTR_Recover_Request.uiFeedbackType == IDR_RECOVERY_REQUEST) {
59 ASSERT_TRUE (info.eFrameType == videoFrameTypeIDR);
60 }
61 //decoding after each encoding frame
62 int len = 0;
63 encToDecData (info, len);
64 unsigned char* pData[3] = { NULL };
65 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
66 iSkipedBytes = SimulateNALLoss (info.sLayerInfo[0].pBsBuf, len, &m_SLostSim, p.pLossSequence, p.bLostPara, iLossIdx,
67 bVCLLoss);
68 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
69 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
70 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
71 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
72 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
73 LTRMarkFeedback (decoder_, encoder_, &m_LTR_Marking_Feedback, rv);
74 if (iSkipedBytes && bVCLLoss) {
75 ASSERT_TRUE (dstBufInfo_.iBufferStatus == 0);
76 }
77 iIdx++;
78 }
79 }
80
TEST_P(EncodeDecodeTestAPI,SetOptionECFlag_ERROR_CON_SLICE_COPY)81 TEST_P (EncodeDecodeTestAPI, SetOptionECFlag_ERROR_CON_SLICE_COPY) {
82 SLTRMarkingFeedback m_LTR_Marking_Feedback;
83 SLTRRecoverRequest m_LTR_Recover_Request;
84 m_LTR_Recover_Request.uiIDRPicId = 0;
85 m_LTR_Recover_Request.iLayerId = 0;
86 m_LTR_Marking_Feedback.iLayerId = 0;
87 EncodeDecodeFileParamBase p = GetParam();
88 prepareParamDefault (1, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
89 encoder_->Uninitialize();
90 int rv = encoder_->InitializeExt (¶m_);
91 ASSERT_TRUE (rv == cmResultSuccess);
92 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
93
94 ASSERT_TRUE (InitialEncDec (p.width, p.height));
95 int32_t iTraceLevel = WELS_LOG_QUIET;
96 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
97 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
98 int32_t iSpsPpsIdAddition = 1;
99 encoder_->SetOption (ENCODER_OPTION_SPS_PPS_ID_STRATEGY, &iSpsPpsIdAddition);
100 int32_t iIDRPeriod = 60;
101 encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
102 SLTRConfig sLtrConfigVal;
103 sLtrConfigVal.bEnableLongTermReference = 1;
104 sLtrConfigVal.iLTRRefNum = 1;
105 encoder_->SetOption (ENCODER_OPTION_LTR, &sLtrConfigVal);
106 int32_t iLtrPeriod = 2;
107 encoder_->SetOption (ENCODER_LTR_MARKING_PERIOD, &iLtrPeriod);
108 int iIdx = 0;
109 int iLossIdx = 0;
110 int iSkipedBytes;
111 bool bVCLLoss = false;
112 while (iIdx <= p.numframes) {
113 EncodeOneFrame (1);
114 if (m_LTR_Recover_Request.uiFeedbackType == IDR_RECOVERY_REQUEST) {
115 ASSERT_TRUE (info.eFrameType == videoFrameTypeIDR);
116 }
117 //decoding after each encoding frame
118 int len = 0;
119 encToDecData (info, len);
120 unsigned char* pData[3] = { NULL };
121 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
122 iSkipedBytes = SimulateNALLoss (info.sLayerInfo[0].pBsBuf, len, &m_SLostSim, p.pLossSequence, p.bLostPara, iLossIdx,
123 bVCLLoss);
124 uint32_t uiEcIdc = rand() % 2 == 1 ? ERROR_CON_DISABLE : ERROR_CON_SLICE_COPY;
125 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
126 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
127 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
128 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
129 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
130 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
131 LTRMarkFeedback (decoder_, encoder_, &m_LTR_Marking_Feedback, rv);
132 iIdx++;
133 }
134 (void) iSkipedBytes;
135 }
136
137 static const EncodeDecodeFileParamBase kFileParamArray[] = {
138 {300, 160, 96, 6.0f, 2, 1, "000000000000001010101010101010101010101001101010100000010101000011"},
139 {300, 140, 96, 6.0f, 4, 1, "000000000000001010101010101010101010101001101010100000010101000011"},
140 {300, 140, 96, 6.0f, 4, 1, "000000000000001010111010101011101010101001101010100000010101110011010101"},
141 };
142
143 INSTANTIATE_TEST_CASE_P (EncodeDecodeTestAPIBase, EncodeDecodeTestAPI,
144 ::testing::ValuesIn (kFileParamArray));
145
TEST_P(EncodeDecodeTestAPI,SetOptionECIDC_GeneralSliceChange)146 TEST_P (EncodeDecodeTestAPI, SetOptionECIDC_GeneralSliceChange) {
147 uint32_t uiEcIdc;
148 uint32_t uiGet;
149 EncodeDecodeFileParamBase p = GetParam();
150 prepareParamDefault (1, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
151 param_.iSpatialLayerNum = 1;
152 encoder_->Uninitialize();
153 int rv = encoder_->InitializeExt (¶m_);
154 ASSERT_TRUE (rv == cmResultSuccess);
155 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
156 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
157
158 uiEcIdc = 0;
159 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
160 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
161 EXPECT_EQ (uiGet, uiEcIdc);
162
163 //Start for enc/dec
164
165 ASSERT_TRUE (InitialEncDec (p.width, p.height));
166 int32_t iTraceLevel = WELS_LOG_QUIET;
167 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
168 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
169 int iIdx = 0;
170 bool bVCLLoss = false;
171 int iPacketNum;
172 int len;
173 int iTotalSliceSize;
174
175 //enc/dec pictures
176 while (iIdx <= p.numframes) {
177 EncodeOneFrame (1);
178 //decoding after each encoding frame
179 len = 0;
180 iPacketNum = 0;
181 iTotalSliceSize = 0;
182 unsigned char* pData[3] = { NULL };
183 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
184 while (iPacketNum < info.sLayerInfo[0].iNalCount) {
185 encToDecSliceData (0, iPacketNum, info, len);
186 uiEcIdc = (ERROR_CON_IDC) (rand() % 2);
187 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
188 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
189 EXPECT_EQ (uiGet, uiEcIdc);
190
191 bVCLLoss = rand() & 1; //loss or not
192 if (!bVCLLoss) { //not loss
193 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize,
194 info.sLayerInfo[0].pNalLengthInByte[iPacketNum], pData, &dstBufInfo_);
195 if (uiEcIdc == ERROR_CON_DISABLE) {
196 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
197 }
198 }
199 //EC_IDC should not change till now
200 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
201 EXPECT_EQ (uiGet, uiEcIdc);
202 //Set again inside
203 uiEcIdc = (ERROR_CON_IDC) (rand() % 2);
204 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
205 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
206 EXPECT_EQ (uiGet, uiEcIdc);
207
208 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
209 //EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
210 if (uiEcIdc == ERROR_CON_DISABLE && rv != 0) {
211 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
212 }
213
214 //deal with next slice
215 iTotalSliceSize += len;
216 iPacketNum++;
217 } //while slice
218 iIdx++;
219 } //while frame
220 }
221
222 //This case contain 1 slice per picture
223 //coding order: 0 1 2 3 4 5 6 7
224 //frame type: IDR P P P P P P P
225 //EC_IDC: 0 0 0 2 0 0 1 1
226 //loss: N Y N N N Y Y N
227
TEST_F(EncodeDecodeTestAPI,SetOptionECIDC_SpecificFrameChange)228 TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificFrameChange) {
229 uint32_t uiEcIdc;
230 uint32_t uiGet;
231 EncodeDecodeFileParamBase p = kFileParamArray[0];
232 prepareParamDefault (1, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
233
234 param_.iSpatialLayerNum = 1;
235 encoder_->Uninitialize();
236 int rv = encoder_->InitializeExt (¶m_);
237 ASSERT_TRUE (rv == cmResultSuccess);
238 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
239 EXPECT_EQ (uiGet, (ERROR_CON_IDC) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
240 int32_t iTraceLevel = WELS_LOG_QUIET;
241 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
242 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
243
244 //set EC=DISABLE
245 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
246 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
247 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
248 EXPECT_EQ (uiGet, uiEcIdc);
249
250 //Start for enc/dec
251 int iIdx = 0;
252 int len = 0;
253 unsigned char* pData[3] = { NULL };
254 ASSERT_TRUE (InitialEncDec (p.width, p.height));
255 //Frame 0: IDR, EC_IDC=DISABLE, loss = 0
256 EncodeOneFrame (1);
257 encToDecData (info, len);
258 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
259 EXPECT_EQ (uiGet, (ERROR_CON_IDC) ERROR_CON_DISABLE);
260 pData[0] = pData[1] = pData[2] = 0;
261 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
262 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
263 EXPECT_EQ (rv, 0);
264 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
265 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
266 EXPECT_EQ (rv, 0);
267 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
268 iIdx++;
269
270 //Frame 1: P, EC_IDC=DISABLE, loss = 1
271 EncodeOneFrame (1);
272 iIdx++;
273
274 //Frame 2: P, EC_IDC=DISABLE, loss = 0
275 EncodeOneFrame (1);
276 encToDecData (info, len);
277 pData[0] = pData[1] = pData[2] = 0;
278 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
279 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
280 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
281 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
282 EXPECT_EQ (rv, 0); //parse correct
283 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
284 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
285 EXPECT_TRUE (rv != 0); //construction error due to data loss
286 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output due to EC DISABLE
287 iIdx++;
288
289 //set EC=SLICE_COPY
290 uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
291 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
292 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
293 EXPECT_EQ (uiGet, uiEcIdc);
294 //Frame 3: P, EC_IDC=SLICE_COPY, loss = 0
295 EncodeOneFrame (1);
296 encToDecData (info, len);
297 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
298 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
299 pData[0] = pData[1] = pData[2] = 0;
300 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
301 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
302 EXPECT_EQ (rv, 0); //parse correct
303 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
304 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
305 EXPECT_TRUE (rv != 0); //construction error due to data loss
306 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
307 iIdx++;
308
309 //set EC=DISABLE
310 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
311 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
312 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
313 EXPECT_EQ (uiGet, uiEcIdc);
314 //Frame 4: P, EC_IDC=DISABLE, loss = 0
315 EncodeOneFrame (1);
316 encToDecData (info, len);
317 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
318 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
319 pData[0] = pData[1] = pData[2] = 0;
320 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
321 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
322 EXPECT_EQ (rv, 0); //parse correct
323 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
324 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
325 //Ref picture is ECed, so current status is ECed, when EC disable, NO output
326 EXPECT_TRUE (rv != 0);
327 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
328 iIdx++;
329
330 //Frame 5: P, EC_IDC=DISABLE, loss = 1
331 EncodeOneFrame (1);
332 iIdx++;
333
334 //set EC=FRAME_COPY
335 uiEcIdc = (uint32_t) (ERROR_CON_FRAME_COPY);
336 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
337 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
338 EXPECT_EQ (uiGet, uiEcIdc);
339 //Frame 6: P, EC_IDC=FRAME_COPY, loss = 1
340 EncodeOneFrame (1);
341 EXPECT_EQ (uiGet, uiEcIdc);
342 iIdx++;
343
344 //Frame 7: P, EC_IDC=FRAME_COPY, loss = 0
345 EncodeOneFrame (1);
346 encToDecData (info, len);
347 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
348 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_FRAME_COPY);
349 pData[0] = pData[1] = pData[2] = 0;
350 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
351 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
352 EXPECT_TRUE (rv == 0); // Now the parse process is Error_None, and the reconstruction will has error return
353 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //no output
354 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
355 EXPECT_TRUE (rv != 0); //not sure if previous data drop would be detected in construction
356 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1);
357 iIdx++;
358 }
359
360 //This case contain 2 slices per picture for IDR loss
361 //coding order: 0 1 2 3 4
362 //frame type IDR P P P P
363 //EC_IDC 2 2 0 1 0
364 //loss (2 slice: 1,2): 2 0 0 1 0
365
TEST_F(EncodeDecodeTestAPI,SetOptionECIDC_SpecificSliceChange_IDRLoss)366 TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificSliceChange_IDRLoss) {
367 uint32_t uiEcIdc = 2; //default set as SLICE_COPY
368 uint32_t uiGet;
369 EncodeDecodeFileParamBase p = kFileParamArray[0];
370 prepareParamDefault (1, 2, p.width, p.height, p.frameRate, ¶m_);
371 param_.iSpatialLayerNum = 1;
372 encoder_->Uninitialize();
373 int rv = encoder_->InitializeExt (¶m_);
374 ASSERT_TRUE (rv == cmResultSuccess);
375 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
376 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
377 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
378 int32_t iTraceLevel = WELS_LOG_QUIET;
379 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
380 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
381
382 //Start for enc/dec
383 int iIdx = 0;
384 int len = 0;
385 unsigned char* pData[3] = { NULL };
386 int iTotalSliceSize = 0;
387
388 ASSERT_TRUE (InitialEncDec (p.width, p.height));
389
390 //Frame 0: IDR, EC_IDC=2, loss = 2
391 EncodeOneFrame (1);
392 iTotalSliceSize = 0;
393 encToDecSliceData (0, 0, info, len); //SPS
394 iTotalSliceSize = len;
395 encToDecSliceData (0, 1, info, len); //PPS
396 iTotalSliceSize += len;
397 encToDecSliceData (1, 0, info, len); //first slice
398 iTotalSliceSize += len;
399 //second slice loss
400 pData[0] = pData[1] = pData[2] = 0;
401 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
402 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
403 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
404 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, iTotalSliceSize, pData, &dstBufInfo_);
405 EXPECT_EQ (rv, 0); //parse correct
406 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
407 EXPECT_EQ (rv, 0); // Reconstruct first slice OK
408 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice incomplete, no output
409 iIdx++;
410
411 //Frame 1: P, EC_IDC=2, loss = 0
412 //will clean SPS/PPS status
413 EncodeOneFrame (1);
414 encToDecData (info, len); //all slice together
415 pData[0] = pData[1] = pData[2] = 0;
416 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
417 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
418 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
419 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
420 EXPECT_TRUE ((rv & 32) != 0); //parse correct, but reconstruct ECed
421 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 0
422 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //ECed status, reconstruction current frame 1
423 EXPECT_TRUE ((rv & 32) != 0); //decoder ECed status
424 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 1
425 iIdx++;
426
427 //set EC=DISABLE
428 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
429 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
430 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
431 EXPECT_EQ (uiGet, uiEcIdc);
432 //Frame 2: P, EC_IDC=0, loss = 0
433 /////will clean SPS/PPS status
434 EncodeOneFrame (1);
435 encToDecData (info, len); //all slice together
436 pData[0] = pData[1] = pData[2] = 0;
437 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
438 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
439 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
440 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
441 EXPECT_EQ (rv, 0); //parse correct
442 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
443 // Ref picture is ECed, so reconstructed picture is ECed
444 EXPECT_TRUE ((rv & 32) != 0);
445 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
446 iIdx++;
447
448 //set EC=SLICE_COPY
449 uiEcIdc = (uint32_t) (ERROR_CON_FRAME_COPY);
450 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
451 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
452 EXPECT_EQ (uiGet, uiEcIdc);
453 //Frame 3: P, EC_IDC=2, loss = 1
454 EncodeOneFrame (1);
455 encToDecSliceData (0, 0, info, iTotalSliceSize); //slice 1 lost
456 encToDecSliceData (0, 1, info, len); //slice 2
457 pData[0] = pData[1] = pData[2] = 0;
458 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
459 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
460 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_FRAME_COPY);
461 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
462 EXPECT_EQ (rv, 0); //parse correct
463 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
464 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
465 EXPECT_TRUE ((rv & 32) != 0);
466 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice loss
467 iIdx++;
468
469 //set EC=DISABLE
470 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
471 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
472 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
473 EXPECT_EQ (uiGet, uiEcIdc);
474 //Frame 4: P, EC_IDC=0, loss = 0
475 EncodeOneFrame (1);
476 encToDecData (info, len); //all slice
477 pData[0] = pData[1] = pData[2] = 0;
478 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
479 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
480 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
481 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
482 EXPECT_TRUE (rv != 0);
483 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); // EC_IDC=0, previous picture slice lost, no output
484 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
485 EXPECT_TRUE (rv != 0);
486 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); // No ref picture, no output
487 iIdx++;
488
489 }
490
491
492
493 //This case contain 2 slices per picture for no IDR loss
494 //coding order: 0 1 2 3 4 5
495 //frame type IDR P P P P IDR
496 //EC_IDC 0 2 0 2 0 ^2^
497 //loss (2 slice: 1,2): 0 0 1 2 0 0
498
TEST_F(EncodeDecodeTestAPI,SetOptionECIDC_SpecificSliceChange_IDRNoLoss)499 TEST_F (EncodeDecodeTestAPI, SetOptionECIDC_SpecificSliceChange_IDRNoLoss) {
500 uint32_t uiEcIdc;
501 uint32_t uiGet;
502 EncodeDecodeFileParamBase p = kFileParamArray[0];
503 prepareParamDefault (1, 2, p.width, p.height, p.frameRate, ¶m_);
504 param_.iSpatialLayerNum = 1;
505 encoder_->Uninitialize();
506 int rv = encoder_->InitializeExt (¶m_);
507 ASSERT_TRUE (rv == cmResultSuccess);
508 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
509 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY); //default value should be ERROR_CON_SLICE_COPY
510 int32_t iTraceLevel = WELS_LOG_QUIET;
511 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
512 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
513
514 //Start for enc/dec
515 int iIdx = 0;
516 int len = 0;
517 unsigned char* pData[3] = { NULL };
518 int iTotalSliceSize = 0;
519
520 ASSERT_TRUE (InitialEncDec (p.width, p.height));
521
522 //set EC=DISABLE
523 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
524 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
525 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
526 EXPECT_EQ (uiGet, uiEcIdc);
527 //Frame 0: IDR, EC_IDC=0, loss = 0
528 //Expected result: all OK, 2nd Output
529 EncodeOneFrame (1);
530 encToDecData (info, len); //all slice
531 pData[0] = pData[1] = pData[2] = 0;
532 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
533 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
534 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
535 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
536 EXPECT_EQ (rv, 0); //parse correct
537 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
538 EXPECT_EQ (rv, 0); //parse correct
539 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //output frame 0
540 iIdx++;
541
542 //Frame 1: P, EC_IDC=0, loss = 0
543 //Expected result: all OK, 2nd Output
544 EncodeOneFrame (1);
545 encToDecData (info, len); //all slice together
546 pData[0] = pData[1] = pData[2] = 0;
547 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
548 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
549 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
550 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
551 EXPECT_EQ (rv, 0); //parse correct
552 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //ECed output for frame 0
553 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction current frame 1
554 EXPECT_EQ (rv, 0); //parse correct
555 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //ECed output for frame 1
556 iIdx++;
557
558 //Frame 2: P, EC_IDC=0, loss = 1
559 //Expected result: all OK, no Output
560 EncodeOneFrame (1);
561 encToDecSliceData (0, 0, info, iTotalSliceSize); // slice 1 lost
562 encToDecSliceData (0, 1, info, len); // slice 2 only
563 pData[0] = pData[1] = pData[2] = 0;
564 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
565 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
566 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
567 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
568 EXPECT_EQ (rv, 0); //parse correct
569 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
570 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
571 EXPECT_EQ (rv, 0); //parse correct
572 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0);
573 iIdx++;
574
575 //set EC=SLICE_COPY
576 uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
577 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
578 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
579 EXPECT_EQ (uiGet, uiEcIdc);
580 //Frame 3: P, EC_IDC=2, loss = 2
581 //Expected result: neither OK, 1st Output
582 EncodeOneFrame (1);
583 encToDecSliceData (0, 0, info, len); //slice 1 only
584 pData[0] = pData[1] = pData[2] = 0;
585 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
586 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
587 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_SLICE_COPY);
588 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
589 EXPECT_TRUE ((rv & 32) != 0); //parse OK but frame 2 ECed
590 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //slice loss but ECed output Frame 2
591 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
592 EXPECT_TRUE ((rv & 32) != 0);
593 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //slice loss
594 iIdx++;
595
596 //set EC=DISABLE
597 uiEcIdc = (uint32_t) (ERROR_CON_DISABLE);
598 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
599 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
600 EXPECT_EQ (uiGet, uiEcIdc);
601 //Frame 4: P, EC_IDC=0, loss = 0
602 //Expected result: depends on DecodeFrame2 result. If OK, output; else ,no output
603 EncodeOneFrame (1);
604 encToDecData (info, len); //all slice
605 pData[0] = pData[1] = pData[2] = 0;
606 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
607 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
608 EXPECT_EQ (uiGet, (uint32_t) ERROR_CON_DISABLE);
609 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
610 EXPECT_TRUE (rv != 0); //previous slice not outputted, will return error due to incomplete frame
611 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
612 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
613 // previous frame NOT output, no ref
614 EXPECT_TRUE (rv != 0);
615 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
616 iIdx++;
617
618 //Frame 5: IDR, EC_IDC=2->0, loss = 0
619 //Expected result: depends on DecodeFrame2 result. If OK, output; else ,no output
620 int32_t iIDRPeriod = 1;
621 encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
622 EncodeOneFrame (1);
623 EXPECT_TRUE (info.eFrameType == videoFrameTypeIDR);
624 encToDecSliceData (0, 0, info, len); //SPS
625 iTotalSliceSize = len;
626 encToDecSliceData (0, 1, info, len); //PPS
627 iTotalSliceSize += len;
628 encToDecSliceData (1, 0, info, len); //slice 1
629 iTotalSliceSize += len;
630 //set EC=SLICE_COPY for slice 1
631 uiEcIdc = (uint32_t) (ERROR_CON_SLICE_COPY);
632 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
633 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
634 EXPECT_EQ (uiGet, uiEcIdc);
635 pData[0] = pData[1] = pData[2] = 0;
636 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
637 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, iTotalSliceSize, pData, &dstBufInfo_);
638 EXPECT_TRUE (rv == 0); // IDR status return error_free
639 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //frame incomplete
640 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
641 EXPECT_TRUE (rv == 0);
642 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //output previous pic
643 //set EC=DISABLE for slice 2
644 encToDecSliceData (1, 1, info, len); //slice 1
645 uiEcIdc = (int) (ERROR_CON_DISABLE);
646 decoder_->SetOption (DECODER_OPTION_ERROR_CON_IDC, &uiEcIdc);
647 decoder_->GetOption (DECODER_OPTION_ERROR_CON_IDC, &uiGet);
648 EXPECT_EQ (uiGet, uiEcIdc);
649 pData[0] = pData[1] = pData[2] = 0;
650 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
651 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf + iTotalSliceSize, len, pData, &dstBufInfo_);
652 EXPECT_EQ (rv, 0); //Parse correct under no EC
653 EXPECT_EQ (dstBufInfo_.iBufferStatus, 0); //frame incomplete
654 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction,
655 EXPECT_EQ (rv, 0);
656 EXPECT_EQ (dstBufInfo_.iBufferStatus, 1); //output previous pic
657 iIdx++;
658
659 }
660
661 static const EncodeDecodeFileParamBase kSVCSwitch[] = {
662 {300, 160, 96, 6.0f, 2, 1, "120012130101012311201221323"},
663 };
664
TEST_F(EncodeDecodeTestAPI,Engine_SVC_Switch_I)665 TEST_F (EncodeDecodeTestAPI, Engine_SVC_Switch_I) {
666 SLTRMarkingFeedback m_LTR_Marking_Feedback;
667 SLTRRecoverRequest m_LTR_Recover_Request;
668 m_LTR_Recover_Request.uiIDRPicId = 0;
669 m_LTR_Recover_Request.iLayerId = 0;
670 m_LTR_Marking_Feedback.iLayerId = 0;
671 EncodeDecodeFileParamBase p = kSVCSwitch[0];
672 p.width = p.width << 2;
673 p.height = p.height << 2;
674 prepareParamDefault (4, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
675 param_.iTemporalLayerNum = (rand() % 4) + 1;
676 param_.iSpatialLayerNum = 4;
677 encoder_->Uninitialize();
678 int rv = encoder_->InitializeExt (¶m_);
679 ASSERT_TRUE (rv == cmResultSuccess);
680 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
681
682 ASSERT_TRUE (InitialEncDec (p.width, p.height));
683 int32_t iTraceLevel = WELS_LOG_QUIET;
684 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
685 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
686 int32_t iSpsPpsIdAddition = 1;
687 encoder_->SetOption (ENCODER_OPTION_SPS_PPS_ID_STRATEGY, &iSpsPpsIdAddition);
688 int32_t iIDRPeriod = (int32_t) pow (2.0f, (param_.iTemporalLayerNum - 1)) * ((rand() % 5) + 1);
689 encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
690 SLTRConfig sLtrConfigVal;
691 sLtrConfigVal.bEnableLongTermReference = 1;
692 sLtrConfigVal.iLTRRefNum = 1;
693 encoder_->SetOption (ENCODER_OPTION_LTR, &sLtrConfigVal);
694 int32_t iLtrPeriod = 2;
695 encoder_->SetOption (ENCODER_LTR_MARKING_PERIOD, &iLtrPeriod);
696 int iIdx = 0;
697 int iTarDid = 0;
698 while (iIdx <= p.numframes) {
699 EncodeOneFrame (1);
700 if (m_LTR_Recover_Request.uiFeedbackType == IDR_RECOVERY_REQUEST) {
701 ASSERT_TRUE (info.eFrameType == videoFrameTypeIDR);
702 }
703 if (info.eFrameType == videoFrameTypeIDR) {
704 iTarDid = rand() % 4;
705 }
706 //decoding after each encoding frame
707 int len = 0;
708 encToDecData (info, len);
709 unsigned char* pData[3] = { NULL };
710 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
711
712 ExtractDidNal (&info, len, &m_SLostSim, iTarDid);
713 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
714 ASSERT_EQ (rv, 0);
715 int iTid = -1;
716 decoder_->GetOption (DECODER_OPTION_TEMPORAL_ID, &iTid);
717 ASSERT_EQ (iTid, -1);
718 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
719 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
720 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
721 ASSERT_EQ (rv, 0);
722 decoder_->GetOption (DECODER_OPTION_TEMPORAL_ID, &iTid);
723 ASSERT_EQ (iTid, info.sLayerInfo[0].uiTemporalId);
724 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, true);
725 LTRMarkFeedback (decoder_, encoder_, &m_LTR_Marking_Feedback, rv);
726 iIdx++;
727 }
728 }
729
TEST_F(EncodeDecodeTestAPI,Engine_SVC_Switch_P)730 TEST_F (EncodeDecodeTestAPI, Engine_SVC_Switch_P) {
731 SLTRMarkingFeedback m_LTR_Marking_Feedback;
732 SLTRRecoverRequest m_LTR_Recover_Request;
733 m_LTR_Recover_Request.uiIDRPicId = 0;
734 m_LTR_Recover_Request.iLayerId = 0;
735 m_LTR_Marking_Feedback.iLayerId = 0;
736 EncodeDecodeFileParamBase p = kSVCSwitch[0];
737 int iTarDid = 0;
738 int iLastDid = 0;
739 p.width = p.width << 2;
740 p.height = p.height << 2;
741 prepareParamDefault (4, p.slicenum, p.width, p.height, p.frameRate, ¶m_);
742 param_.iTemporalLayerNum = (rand() % 4) + 1;
743 param_.iSpatialLayerNum = 4;
744 encoder_->Uninitialize();
745 int rv = encoder_->InitializeExt (¶m_);
746 ASSERT_TRUE (rv == cmResultSuccess);
747 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
748
749 ASSERT_TRUE (InitialEncDec (p.width, p.height));
750 int32_t iTraceLevel = WELS_LOG_QUIET;
751 encoder_->SetOption (ENCODER_OPTION_TRACE_LEVEL, &iTraceLevel);
752 decoder_->SetOption (DECODER_OPTION_TRACE_LEVEL, &iTraceLevel);
753 int32_t iSpsPpsIdAddition = 1;
754 encoder_->SetOption (ENCODER_OPTION_SPS_PPS_ID_STRATEGY, &iSpsPpsIdAddition);
755 int32_t iIDRPeriod = 60;
756 encoder_->SetOption (ENCODER_OPTION_IDR_INTERVAL, &iIDRPeriod);
757 SLTRConfig sLtrConfigVal;
758 sLtrConfigVal.bEnableLongTermReference = 1;
759 sLtrConfigVal.iLTRRefNum = 1;
760 encoder_->SetOption (ENCODER_OPTION_LTR, &sLtrConfigVal);
761 int32_t iLtrPeriod = 2;
762 encoder_->SetOption (ENCODER_LTR_MARKING_PERIOD, &iLtrPeriod);
763 int iIdx = 0;
764
765 while (iIdx <= p.numframes) {
766 EncodeOneFrame (1);
767 if (m_LTR_Recover_Request.uiFeedbackType == IDR_RECOVERY_REQUEST) {
768 ASSERT_TRUE (info.eFrameType == videoFrameTypeIDR);
769 }
770 //decoding after each encoding frame
771 int len = 0;
772 encToDecData (info, len);
773 unsigned char* pData[3] = { NULL };
774 memset (&dstBufInfo_, 0, sizeof (SBufferInfo));
775 if (iIdx < (int) strlen (p.pLossSequence)) {
776 switch (p.pLossSequence[iIdx]) {
777 case '0':
778 iTarDid = 0;
779 break;
780 case '1':
781 iTarDid = 1;
782 break;
783 case '2':
784 iTarDid = 2;
785 break;
786 case '3':
787 iTarDid = 3;
788 break;
789 default :
790 iTarDid = rand() % 4;
791 break;
792 }
793 } else {
794 iTarDid = rand() % 4;
795 }
796
797 ExtractDidNal (&info, len, &m_SLostSim, iTarDid);
798 rv = decoder_->DecodeFrame2 (info.sLayerInfo[0].pBsBuf, len, pData, &dstBufInfo_);
799 int iTid = -1;
800 decoder_->GetOption (DECODER_OPTION_TEMPORAL_ID, &iTid);
801 ASSERT_EQ (iTid, -1);
802 m_LTR_Recover_Request.uiFeedbackType = NO_RECOVERY_REQUSET;
803 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, false);
804 rv = decoder_->DecodeFrame2 (NULL, 0, pData, &dstBufInfo_); //reconstruction
805 if (info.eFrameType == videoFrameTypeP && iIdx > 0 && iLastDid != iTarDid) {
806 ASSERT_NE (rv, 0);
807 } else if (info.eFrameType == videoFrameTypeIDR) {
808 ASSERT_EQ (rv, 0);
809 }
810 decoder_->GetOption (DECODER_OPTION_TEMPORAL_ID, &iTid);
811 ASSERT_EQ (iTid, info.sLayerInfo[0].uiTemporalId);
812 LTRRecoveryRequest (decoder_, encoder_, &m_LTR_Recover_Request, rv, false);
813 LTRMarkFeedback (decoder_, encoder_, &m_LTR_Marking_Feedback, rv);
814 iIdx++;
815 iLastDid = iTarDid;
816 }
817 }
818
819
820