1 /*
2 * Copyright(c) 2018 Intel Corporation
3 * SPDX - License - Identifier: BSD - 2 - Clause - Patent
4 */
5 
6 #include <stdlib.h>
7 #include <string.h>
8 
9 #include "EbDefinitions.h"
10 #include "EbSystemResourceManager.h"
11 #include "EbPictureControlSet.h"
12 #include "EbSequenceControlSet.h"
13 #include "EbPictureBufferDesc.h"
14 #include "EbErrorCodes.h"
15 #include "EbErrorHandling.h"
16 
17 #include "EbResourceCoordinationProcess.h"
18 
19 #include "EbResourceCoordinationResults.h"
20 #include "EbReferenceObject.h"
21 #include "EbUtility.h"
22 
ResourceCoordinationContextDctor(EB_PTR p)23 static void ResourceCoordinationContextDctor(EB_PTR p)
24 {
25     ResourceCoordinationContext_t *obj = (ResourceCoordinationContext_t*)p;
26     EB_FREE_ARRAY(obj->sequenceControlSetActiveArray);
27     EB_FREE_ARRAY(obj->pictureNumberArray);
28 }
29 
30 /************************************************
31  * Resource Coordination Context Constructor
32  ************************************************/
ResourceCoordinationContextCtor(ResourceCoordinationContext_t * contextPtr,EbFifo_t * inputBufferFifoPtr,EbFifo_t * resourceCoordinationResultsOutputFifoPtr,EbFifo_t ** pictureControlSetFifoPtrArray,EbSequenceControlSetInstance_t ** sequenceControlSetInstanceArray,EbFifo_t * sequenceControlSetEmptyFifoPtr,EbCallback_t ** appCallbackPtrArray,EB_U32 * computeSegmentsTotalCountArray,EB_U32 encodeInstancesTotalCount)33 EB_ERRORTYPE ResourceCoordinationContextCtor(
34     ResourceCoordinationContext_t   *contextPtr,
35     EbFifo_t                        *inputBufferFifoPtr,
36     EbFifo_t                        *resourceCoordinationResultsOutputFifoPtr,
37     EbFifo_t                       **pictureControlSetFifoPtrArray,
38     EbSequenceControlSetInstance_t **sequenceControlSetInstanceArray,
39     EbFifo_t                        *sequenceControlSetEmptyFifoPtr,
40     EbCallback_t                   **appCallbackPtrArray,
41     EB_U32                          *computeSegmentsTotalCountArray,
42     EB_U32                           encodeInstancesTotalCount)
43 {
44     contextPtr->dctor = ResourceCoordinationContextDctor;
45     contextPtr->inputBufferFifoPtr                       = inputBufferFifoPtr;
46     contextPtr->resourceCoordinationResultsOutputFifoPtr    = resourceCoordinationResultsOutputFifoPtr;
47     contextPtr->pictureControlSetFifoPtrArray               = pictureControlSetFifoPtrArray;
48     contextPtr->sequenceControlSetInstanceArray             = sequenceControlSetInstanceArray;
49     contextPtr->sequenceControlSetEmptyFifoPtr              = sequenceControlSetEmptyFifoPtr;
50     contextPtr->appCallbackPtrArray                         = appCallbackPtrArray;
51     contextPtr->computeSegmentsTotalCountArray              = computeSegmentsTotalCountArray;
52     contextPtr->encodeInstancesTotalCount                   = encodeInstancesTotalCount;
53 
54     // Allocate SequenceControlSetActiveArray
55     EB_CALLOC_ARRAY(contextPtr->sequenceControlSetActiveArray, contextPtr->encodeInstancesTotalCount);
56 
57     // Picture Stats
58     EB_CALLOC_ARRAY(contextPtr->pictureNumberArray, contextPtr->encodeInstancesTotalCount);
59 
60     return EB_ErrorNone;
61 }
62 
63 //******************************************************************************//
64 // Modify the Enc mode based on the buffer Status
65 // Inputs: TargetSpeed, Status of the SCbuffer
66 // Output: EncMod
67 //******************************************************************************//
SpeedBufferControl(ResourceCoordinationContext_t * contextPtr,PictureParentControlSet_t * pictureControlSetPtr,SequenceControlSet_t * sequenceControlSetPtr)68 static void SpeedBufferControl(
69 	ResourceCoordinationContext_t   *contextPtr,
70 	PictureParentControlSet_t       *pictureControlSetPtr,
71 	SequenceControlSet_t            *sequenceControlSetPtr)
72 {
73 
74     EB_U64 cursTimeSeconds = 0;
75     EB_U64 cursTimeuSeconds = 0;
76     double overallDuration = 0.0;
77     double instDuration = 0.0;
78 	EB_S8  encoderModeDelta = 0;
79 	EB_S64 inputFramesCount = 0;
80 	EB_S8 changeCond        = 0;
81 	EB_S64 targetFps        = (sequenceControlSetPtr->staticConfig.injectorFrameRate >> 16);
82 
83 
84     EB_S64 bufferTrshold1 = SC_FRAMES_INTERVAL_T1;
85     EB_S64 bufferTrshold2 = SC_FRAMES_INTERVAL_T2;
86     EB_S64 bufferTrshold3 = SC_FRAMES_INTERVAL_T3;
87     EB_S64 bufferTrshold4 = MAX(SC_FRAMES_INTERVAL_T1, targetFps);
88 	EbBlockOnMutex(sequenceControlSetPtr->encodeContextPtr->scBufferMutex);
89 
90 	if (sequenceControlSetPtr->encodeContextPtr->scFrameIn == 0) {
91         EbHevcStartTime((uint64_t*)&contextPtr->firstInPicArrivedTimeSeconds, (uint64_t*)&contextPtr->firstInPicArrivedTimeuSeconds);
92 	}
93 	else if (sequenceControlSetPtr->encodeContextPtr->scFrameIn == SC_FRAMES_TO_IGNORE) {
94 		contextPtr->startFlag = EB_TRUE;
95 	}
96 
97     // Compute duration since the start of the encode and since the previous checkpoint
98     EbHevcFinishTime((uint64_t*)&cursTimeSeconds, (uint64_t*)&cursTimeuSeconds);
99 
100     EbHevcComputeOverallElapsedTimeMs(
101         contextPtr->firstInPicArrivedTimeSeconds,
102         contextPtr->firstInPicArrivedTimeuSeconds,
103         cursTimeSeconds,
104         cursTimeuSeconds,
105         &overallDuration);
106 
107     EbHevcComputeOverallElapsedTimeMs(
108         contextPtr->prevsTimeSeconds,
109         contextPtr->prevsTimeuSeconds,
110         cursTimeSeconds,
111         cursTimeuSeconds,
112         &instDuration);
113 
114     inputFramesCount = (EB_S64)overallDuration *(sequenceControlSetPtr->staticConfig.injectorFrameRate >> 16) / 1000;
115 	sequenceControlSetPtr->encodeContextPtr->scBuffer = inputFramesCount - sequenceControlSetPtr->encodeContextPtr->scFrameIn;
116 
117 	encoderModeDelta = 0;
118 
119 	// Check every bufferTsshold1 for the changes (previousFrameInCheck1 variable)
120 	if ((sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousFrameInCheck1 + bufferTrshold1 && sequenceControlSetPtr->encodeContextPtr->scFrameIn >= SC_FRAMES_TO_IGNORE)) {
121 		// Go to a slower mode based on the fullness and changes of the buffer
122         if (sequenceControlSetPtr->encodeContextPtr->scBuffer < bufferTrshold4 && (contextPtr->prevEncModeDelta >-1 || (contextPtr->prevEncModeDelta < 0 && sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousModeChangeFrameIn + bufferTrshold4 * 2))) {
123 			if (contextPtr->previousBufferCheck1 > sequenceControlSetPtr->encodeContextPtr->scBuffer + bufferTrshold1) {
124 				encoderModeDelta += -1;
125 				changeCond = 2;
126 			}
127 			else if (contextPtr->previousModeChangeBuffer > bufferTrshold1 + sequenceControlSetPtr->encodeContextPtr->scBuffer && sequenceControlSetPtr->encodeContextPtr->scBuffer < bufferTrshold1) {
128 				encoderModeDelta += -1;
129 				changeCond = 4;
130 			}
131 		}
132 
133 		// Go to a faster mode based on the fullness and changes of the buffer
134 		if (sequenceControlSetPtr->encodeContextPtr->scBuffer >bufferTrshold1 + contextPtr->previousBufferCheck1) {
135 			encoderModeDelta += +1;
136 			changeCond = 1;
137 		}
138 		else if (sequenceControlSetPtr->encodeContextPtr->scBuffer > bufferTrshold1 + contextPtr->previousModeChangeBuffer) {
139 			encoderModeDelta += +1;
140 			changeCond = 3;
141 		}
142 
143 		// Update the encode mode based on the fullness of the buffer
144         // If previous ChangeCond was the same, double the threshold2
145 		if (sequenceControlSetPtr->encodeContextPtr->scBuffer > bufferTrshold3 &&
146 			(contextPtr->prevChangeCond != 7 || sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousModeChangeFrameIn + bufferTrshold2 * 2) &&
147 			sequenceControlSetPtr->encodeContextPtr->scBuffer > contextPtr->previousModeChangeBuffer) {
148 			encoderModeDelta += 1;
149 			changeCond = 7;
150 		}
151 		encoderModeDelta = CLIP3(-1, 1, encoderModeDelta);
152         sequenceControlSetPtr->encodeContextPtr->encMode = (EB_ENC_MODE)CLIP3(ENC_MODE_0, sequenceControlSetPtr->maxEncMode, (EB_S8)sequenceControlSetPtr->encodeContextPtr->encMode + encoderModeDelta);
153 
154 		// Update previous stats
155 		contextPtr->previousFrameInCheck1 = sequenceControlSetPtr->encodeContextPtr->scFrameIn;
156 		contextPtr->previousBufferCheck1 = sequenceControlSetPtr->encodeContextPtr->scBuffer;
157 
158 		if (encoderModeDelta) {
159 			contextPtr->previousModeChangeBuffer = sequenceControlSetPtr->encodeContextPtr->scBuffer;
160 			contextPtr->previousModeChangeFrameIn = sequenceControlSetPtr->encodeContextPtr->scFrameIn;
161 			contextPtr->prevEncModeDelta = encoderModeDelta;
162 		}
163 	}
164 
165 	// Check every bufferTrshold2 for the changes (previousFrameInCheck2 variable)
166 	if ((sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousFrameInCheck2 + bufferTrshold2 && sequenceControlSetPtr->encodeContextPtr->scFrameIn >= SC_FRAMES_TO_IGNORE)) {
167 		encoderModeDelta = 0;
168 
169 		// if no change in the encoder mode and buffer is low enough and level is not increasing, switch to a slower encoder mode
170         // If previous ChangeCond was the same, double the threshold2
171 		if (encoderModeDelta == 0 && sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousModeChangeFrameIn + bufferTrshold2 &&
172 			(contextPtr->prevChangeCond != 8 || sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousModeChangeFrameIn + bufferTrshold2 * 2) &&
173             ((sequenceControlSetPtr->encodeContextPtr->scBuffer - contextPtr->previousModeChangeBuffer < (bufferTrshold4 / 3)) || contextPtr->previousModeChangeBuffer == 0) &&
174 			sequenceControlSetPtr->encodeContextPtr->scBuffer < bufferTrshold3) {
175 			encoderModeDelta = -1;
176 			changeCond = 8;
177 		}
178 
179 		encoderModeDelta = CLIP3(-1, 1, encoderModeDelta);
180         sequenceControlSetPtr->encodeContextPtr->encMode = (EB_ENC_MODE)CLIP3(ENC_MODE_0, sequenceControlSetPtr->maxEncMode, (EB_S8)sequenceControlSetPtr->encodeContextPtr->encMode + encoderModeDelta);
181 		// Update previous stats
182 		contextPtr->previousFrameInCheck2 = sequenceControlSetPtr->encodeContextPtr->scFrameIn;
183 
184 		if (encoderModeDelta) {
185 			contextPtr->previousModeChangeBuffer = sequenceControlSetPtr->encodeContextPtr->scBuffer;
186 			contextPtr->previousModeChangeFrameIn = sequenceControlSetPtr->encodeContextPtr->scFrameIn;
187 			contextPtr->prevEncModeDelta = encoderModeDelta;
188 		}
189 
190 	}
191 	// Check every SC_FRAMES_INTERVAL_SPEED frames for the speed calculation (previousFrameInCheck3 variable)
192     if (contextPtr->startFlag || (sequenceControlSetPtr->encodeContextPtr->scFrameIn > contextPtr->previousFrameInCheck3 + SC_FRAMES_INTERVAL_SPEED && sequenceControlSetPtr->encodeContextPtr->scFrameIn >= SC_FRAMES_TO_IGNORE)) {
193 		if (contextPtr->startFlag) {
194 			contextPtr->curSpeed = (EB_U64)(sequenceControlSetPtr->encodeContextPtr->scFrameOut - 0) * 1000 / (EB_U64)(overallDuration);
195 		}
196 		else {
197             if (instDuration != 0)
198                 contextPtr->curSpeed = (EB_U64)(sequenceControlSetPtr->encodeContextPtr->scFrameOut - contextPtr->prevFrameOut) * 1000 / (EB_U64)(instDuration);
199 		}
200 		contextPtr->startFlag = EB_FALSE;
201 
202 		// Update previous stats
203 		contextPtr->previousFrameInCheck3 = sequenceControlSetPtr->encodeContextPtr->scFrameIn;
204         contextPtr->prevsTimeSeconds = cursTimeSeconds;
205         contextPtr->prevsTimeuSeconds = cursTimeuSeconds;
206 		contextPtr->prevFrameOut = sequenceControlSetPtr->encodeContextPtr->scFrameOut;
207 
208 	}
209     else if (sequenceControlSetPtr->encodeContextPtr->scFrameIn < SC_FRAMES_TO_IGNORE && (overallDuration != 0)) {
210         contextPtr->curSpeed = (EB_U64)(sequenceControlSetPtr->encodeContextPtr->scFrameOut - 0) * 1000 / (EB_U64)(overallDuration);
211 	}
212 
213 	if (changeCond) {
214 		contextPtr->prevChangeCond = changeCond;
215 	}
216 	sequenceControlSetPtr->encodeContextPtr->scFrameIn++;
217 	if (sequenceControlSetPtr->encodeContextPtr->scFrameIn >= SC_FRAMES_TO_IGNORE) {
218 		contextPtr->averageEncMod += sequenceControlSetPtr->encodeContextPtr->encMode;
219 	}
220 	else {
221 		contextPtr->averageEncMod = 0;
222 	}
223 
224 	// Set the encoder level
225 	pictureControlSetPtr->encMode = sequenceControlSetPtr->encodeContextPtr->encMode;
226 
227 	EbReleaseMutex(sequenceControlSetPtr->encodeContextPtr->scBufferMutex);
228 
229 	contextPtr->prevEncMod = sequenceControlSetPtr->encodeContextPtr->encMode;
230 }
231 
232 
233 
234 /******************************************************
235 * Derive Pre-Analysis settings for OQ
236 Input   : encoder mode and tune
237 Output  : Pre-Analysis signal(s)
238 ******************************************************/
SignalDerivationPreAnalysisOq(SequenceControlSet_t * sequenceControlSetPtr,PictureParentControlSet_t * pictureControlSetPtr)239 static EB_ERRORTYPE SignalDerivationPreAnalysisOq(
240     SequenceControlSet_t       *sequenceControlSetPtr,
241     PictureParentControlSet_t  *pictureControlSetPtr) {
242 
243     EB_ERRORTYPE return_error = EB_ErrorNone;
244 
245     EB_U8 inputResolution = sequenceControlSetPtr->inputResolution;
246 
247 
248     // Derive Noise Detection Method
249     if (inputResolution == INPUT_SIZE_4K_RANGE) {
250         if (pictureControlSetPtr->encMode <= ENC_MODE_3) {
251             pictureControlSetPtr->noiseDetectionMethod = NOISE_DETECT_FULL_PRECISION;
252         }
253         else {
254             pictureControlSetPtr->noiseDetectionMethod = NOISE_DETECT_HALF_PRECISION;
255         }
256     }
257     else if (inputResolution == INPUT_SIZE_1080p_RANGE) {
258         if (pictureControlSetPtr->encMode <= ENC_MODE_3) {
259             pictureControlSetPtr->noiseDetectionMethod = NOISE_DETECT_FULL_PRECISION;
260         }
261         else {
262             pictureControlSetPtr->noiseDetectionMethod = NOISE_DETECT_QUARTER_PRECISION;
263         }
264     }
265     else {
266         pictureControlSetPtr->noiseDetectionMethod = NOISE_DETECT_FULL_PRECISION;
267     }
268 
269 
270     // Derive Noise Detection Threshold
271     if (pictureControlSetPtr->encMode <= ENC_MODE_3) {
272         pictureControlSetPtr->noiseDetectionTh = 0;
273     }
274 	else if (pictureControlSetPtr->encMode <= ENC_MODE_8) {
275 		if (inputResolution <= INPUT_SIZE_1080p_RANGE) {
276 			pictureControlSetPtr->noiseDetectionTh = 1;
277 		}
278 		else {
279 			pictureControlSetPtr->noiseDetectionTh = 0;
280 		}
281 	}
282     else{
283         pictureControlSetPtr->noiseDetectionTh = 1;
284     }
285 
286     EB_U8  hmeMeLevel       = pictureControlSetPtr->encMode;
287 
288     EB_U32 inputRatio       = sequenceControlSetPtr->lumaWidth / sequenceControlSetPtr->lumaHeight;
289     EB_U8 resolutionIndex   = inputResolution <= INPUT_SIZE_576p_RANGE_OR_LOWER ?               0   : // 480P
290                                 (inputResolution <= INPUT_SIZE_1080i_RANGE && inputRatio < 2) ?    1   : // 720P
291                                 (inputResolution <= INPUT_SIZE_1080i_RANGE && inputRatio > 3) ?    2   : // 1080I
292                                 (inputResolution <= INPUT_SIZE_1080p_RANGE) ?                      3   : // 1080I
293                                                                                                 4;    // 4K
294 
295     // Derive HME Flag
296     if (sequenceControlSetPtr->staticConfig.useDefaultMeHme)
297         pictureControlSetPtr->enableHmeFlag = EB_TRUE;
298     else
299         pictureControlSetPtr->enableHmeFlag = sequenceControlSetPtr->staticConfig.enableHmeFlag;
300     pictureControlSetPtr->enableHmeLevel0Flag   = EnableHmeLevel0FlagOq[resolutionIndex][hmeMeLevel];
301     pictureControlSetPtr->enableHmeLevel1Flag   = EnableHmeLevel1FlagOq[resolutionIndex][hmeMeLevel];
302     pictureControlSetPtr->enableHmeLevel2Flag   = EnableHmeLevel2FlagOq[resolutionIndex][hmeMeLevel];
303 
304 	pictureControlSetPtr->enableDenoiseSrcFlag = EB_FALSE;
305 
306 	if (pictureControlSetPtr->encMode <= ENC_MODE_7) {
307 		pictureControlSetPtr->disableVarianceFlag = EB_FALSE;
308 	}
309 	else if (pictureControlSetPtr->encMode <= ENC_MODE_8) {
310 		if (inputResolution == INPUT_SIZE_4K_RANGE) {
311 			pictureControlSetPtr->disableVarianceFlag = EB_TRUE;
312 		}
313 		else {
314 			pictureControlSetPtr->disableVarianceFlag = EB_FALSE;
315 		}
316 	}
317 	else {
318 		pictureControlSetPtr->disableVarianceFlag = EB_TRUE;
319 	}
320 
321     return return_error;
322 }
323 
324 
325 
326 /***************************************
327  * ResourceCoordination Kernel
328  ***************************************/
ResourceCoordinationKernel(void * inputPtr)329 void* ResourceCoordinationKernel(void *inputPtr)
330 {
331     ResourceCoordinationContext_t *contextPtr = (ResourceCoordinationContext_t*) inputPtr;
332 
333     EbObjectWrapper_t               *pictureControlSetWrapperPtr;
334 
335     PictureParentControlSet_t       *pictureControlSetPtr;
336 
337     SequenceControlSet_t            *sequenceControlSetPtr;
338 
339     EbObjectWrapper_t               *ebInputWrapperPtr;
340     EB_BUFFERHEADERTYPE             *ebInputPtr;
341     EbObjectWrapper_t               *outputWrapperPtr;
342     ResourceCoordinationResults_t   *outputResultsPtr;
343 
344     EbObjectWrapper_t               *inputPictureWrapperPtr;
345     EbPictureBufferDesc_t           *inputPicturePtr;
346     EbObjectWrapper_t               *referencePictureWrapperPtr;
347 
348     EB_U32                           instanceIndex;
349 
350     EB_BOOL                          endOfSequenceFlag = EB_FALSE;
351 
352     EB_BOOL                          is16BitInput;
353 
354 	EB_U32							inputSize = 0;
355 	EbObjectWrapper_t              *prevPictureControlSetWrapperPtr = 0;
356     EB_U32                          chromaFormat = EB_YUV420;
357     EB_U32                          subWidthCMinus1 = 1;
358     EB_U32                          subHeightCMinus1 = 1;
359 
360     for(;;) {
361 
362         // Tie instanceIndex to zero for now...
363         instanceIndex = 0;
364 
365         // Get the Next Input Buffer [BLOCKING]
366         EbGetFullObject(
367             contextPtr->inputBufferFifoPtr,
368             &ebInputWrapperPtr);
369         EB_CHECK_END_OBJ(ebInputWrapperPtr);
370         ebInputPtr = (EB_BUFFERHEADERTYPE*) ebInputWrapperPtr->objectPtr;
371 
372         sequenceControlSetPtr       = contextPtr->sequenceControlSetInstanceArray[instanceIndex]->sequenceControlSetPtr;
373 
374         // Get source video bit depth
375         is16BitInput =  (EB_BOOL)(sequenceControlSetPtr->staticConfig.encoderBitDepth > EB_8BIT);
376 
377         chromaFormat = sequenceControlSetPtr->chromaFormatIdc;
378         subWidthCMinus1 = (chromaFormat == EB_YUV444 ? 1 : 2) - 1;
379         subHeightCMinus1 = (chromaFormat >= EB_YUV422 ? 1 : 2) - 1;
380         // If config changes occured since the last picture began encoding, then
381         //   prepare a new sequenceControlSetPtr containing the new changes and update the state
382         //   of the previous Active SequenceControlSet
383         EbBlockOnMutex(contextPtr->sequenceControlSetInstanceArray[instanceIndex]->configMutex);
384         if (contextPtr->sequenceControlSetInstanceArray[instanceIndex]->encodeContextPtr->initialPicture) {
385             inputSize = sequenceControlSetPtr->lumaWidth * sequenceControlSetPtr->lumaHeight;
386 
387             // HDR BT2020
388             if (sequenceControlSetPtr->staticConfig.videoUsabilityInfo)
389             {
390                 AppVideoUsabilityInfo_t *vuiPtr = sequenceControlSetPtr->videoUsabilityInfoPtr;
391 
392                 if (sequenceControlSetPtr->staticConfig.highDynamicRangeInput && is16BitInput){
393                     vuiPtr->aspectRatioInfoPresentFlag = EB_TRUE;
394                     vuiPtr->overscanInfoPresentFlag = EB_FALSE;
395 
396                     vuiPtr->videoSignalTypePresentFlag = EB_TRUE;
397                     vuiPtr->videoFormat = 5;
398                     vuiPtr->videoFullRangeFlag = EB_FALSE;
399 
400                     vuiPtr->colorDescriptionPresentFlag = EB_TRUE;
401                     vuiPtr->colorPrimaries = 9;   // BT2020
402                     vuiPtr->transferCharacteristics = 16;  // SMPTE ST2048
403                     vuiPtr->matrixCoeffs = 9;
404 
405                     vuiPtr->chromaLocInfoPresentFlag = EB_TRUE;
406                     vuiPtr->chromaSampleLocTypeTopField = 2;
407                     vuiPtr->chromaSampleLocTypeBottomField = 2;
408                 }
409 
410                 vuiPtr->vuiTimingInfoPresentFlag        = EB_TRUE;
411                 if (sequenceControlSetPtr->staticConfig.frameRateDenominator != 0 && sequenceControlSetPtr->staticConfig.frameRateNumerator != 0) {
412                     vuiPtr->vuiTimeScale = (sequenceControlSetPtr->staticConfig.frameRateNumerator);
413                     vuiPtr->vuiNumUnitsInTick = sequenceControlSetPtr->staticConfig.frameRateDenominator;
414                 }
415                 else {
416                     vuiPtr->vuiTimeScale = (sequenceControlSetPtr->staticConfig.frameRate) > 1000 ? (sequenceControlSetPtr->staticConfig.frameRate) : (sequenceControlSetPtr->staticConfig.frameRate)<<16;
417                     vuiPtr->vuiNumUnitsInTick = 1 << 16;
418                 }
419 
420             }
421             // Get empty SequenceControlSet [BLOCKING]
422             EbGetEmptyObject(
423                 contextPtr->sequenceControlSetEmptyFifoPtr,
424                 &contextPtr->sequenceControlSetActiveArray[instanceIndex]);
425 
426             // Copy the contents of the active SequenceControlSet into the new empty SequenceControlSet
427             CopySequenceControlSet(
428                 (SequenceControlSet_t*) contextPtr->sequenceControlSetActiveArray[instanceIndex]->objectPtr,
429                 sequenceControlSetPtr);
430 
431         }
432         EbReleaseMutex(contextPtr->sequenceControlSetInstanceArray[instanceIndex]->configMutex);
433         if (sequenceControlSetPtr->staticConfig.rateControlMode) {
434             // Sequence Control Set is released by Rate Control after passing through MDC->MD->ENCDEC->Packetization->RateControl
435             //   ,in the PictureManager after receiving the reference and in PictureManager after receiving the feedback
436             EbObjectIncLiveCount(
437                 contextPtr->sequenceControlSetActiveArray[instanceIndex],
438                 3);
439         }
440         else {
441             // Sequence Control Set is released by Rate Control after passing through MDC->MD->ENCDEC->Packetization->RateControl
442             //   and in the PictureManager
443             EbObjectIncLiveCount(
444                 contextPtr->sequenceControlSetActiveArray[instanceIndex],
445                 2);
446 
447         }
448         // Set the current SequenceControlSet
449         sequenceControlSetPtr   = (SequenceControlSet_t*) contextPtr->sequenceControlSetActiveArray[instanceIndex]->objectPtr;
450 
451         //Move to pcs init stage
452         //InitTileInfo(sequenceControlSetPtr);
453 
454         sequenceControlSetPtr->pictureWidthInLcu  = (EB_U8)((sequenceControlSetPtr->lumaWidth + sequenceControlSetPtr->lcuSize - 1) / sequenceControlSetPtr->lcuSize);
455         sequenceControlSetPtr->pictureHeightInLcu = (EB_U8)((sequenceControlSetPtr->lumaHeight + sequenceControlSetPtr->lcuSize - 1) / sequenceControlSetPtr->lcuSize);
456         sequenceControlSetPtr->lcuTotalCount = sequenceControlSetPtr->pictureWidthInLcu * sequenceControlSetPtr->pictureHeightInLcu;
457 
458 		// Init LCU Params
459         if (contextPtr->sequenceControlSetInstanceArray[instanceIndex]->encodeContextPtr->initialPicture) {
460             DeriveInputResolution(
461                 sequenceControlSetPtr,
462                 inputSize);
463 
464             LcuParamsInit(sequenceControlSetPtr);
465         }
466 
467         //Get a New ParentPCS where we will hold the new inputPicture
468         EbGetEmptyObject(
469             contextPtr->pictureControlSetFifoPtrArray[instanceIndex],
470             &pictureControlSetWrapperPtr);
471 
472         // Parent PCS is released by the Rate Control after passing through MDC->MD->ENCDEC->Packetization
473         EbObjectIncLiveCount(
474             pictureControlSetWrapperPtr,
475             2);
476 
477         pictureControlSetPtr        = (PictureParentControlSet_t*) pictureControlSetWrapperPtr->objectPtr;
478 
479         pictureControlSetPtr->pPcsWrapperPtr = pictureControlSetWrapperPtr;
480 
481         // Set the Encoder mode
482         pictureControlSetPtr->encMode = sequenceControlSetPtr->staticConfig.encMode;
483 
484 		// Keep track of the previous input for the ZZ SADs computation
485 		pictureControlSetPtr->previousPictureControlSetWrapperPtr = (contextPtr->sequenceControlSetInstanceArray[instanceIndex]->encodeContextPtr->initialPicture) ?
486 			pictureControlSetWrapperPtr :
487 			sequenceControlSetPtr->encodeContextPtr->previousPictureControlSetWrapperPtr;
488 
489 		sequenceControlSetPtr->encodeContextPtr->previousPictureControlSetWrapperPtr = pictureControlSetWrapperPtr;
490 
491         // Copy data from the buffer to the input frame
492         // *Note - Assumes 4:2:0 planar
493         inputPictureWrapperPtr  = NULL;
494         inputPicturePtr         = NULL;
495 
496         // assign the input picture
497         pictureControlSetPtr->enhancedPicturePtr = (EbPictureBufferDesc_t*)ebInputPtr->pBuffer;
498         // start latency measure as soon as we copy input picture from buffer
499         pictureControlSetPtr->startTimeSeconds = 0;
500         pictureControlSetPtr->startTimeuSeconds = 0;
501 
502         EbHevcStartTime((uint64_t*)&pictureControlSetPtr->startTimeSeconds, (uint64_t*)&pictureControlSetPtr->startTimeuSeconds);
503 
504         inputPicturePtr = pictureControlSetPtr->enhancedPicturePtr;
505 
506         // Setup new input picture buffer
507         inputPicturePtr->bitDepth           = sequenceControlSetPtr->inputBitdepth;
508 		inputPicturePtr->originX			= sequenceControlSetPtr->leftPadding;
509 
510         inputPicturePtr->originY            = sequenceControlSetPtr->topPadding;
511 
512         inputPicturePtr->maxWidth           = sequenceControlSetPtr->maxInputLumaWidth;
513         inputPicturePtr->maxHeight          = sequenceControlSetPtr->maxInputLumaHeight;
514         inputPicturePtr->lumaSize           =
515 			((sequenceControlSetPtr->maxInputLumaWidth - sequenceControlSetPtr->maxInputPadRight) + sequenceControlSetPtr->leftPadding + sequenceControlSetPtr->rightPadding) *
516 			((sequenceControlSetPtr->maxInputLumaHeight - sequenceControlSetPtr->maxInputPadBottom) + sequenceControlSetPtr->topPadding + sequenceControlSetPtr->botPadding);
517         inputPicturePtr->chromaSize         = inputPicturePtr->lumaSize >> (3 - chromaFormat);
518 
519         inputPicturePtr->width              = sequenceControlSetPtr->lumaWidth;
520         inputPicturePtr->height             = sequenceControlSetPtr->lumaHeight;
521         inputPicturePtr->strideY            = sequenceControlSetPtr->lumaWidth + sequenceControlSetPtr->leftPadding + sequenceControlSetPtr->rightPadding;
522         inputPicturePtr->strideCb           = inputPicturePtr->strideCr = inputPicturePtr->strideY >> subWidthCMinus1;
523 
524 		inputPicturePtr->strideBitIncY      = inputPicturePtr->strideY;
525 		inputPicturePtr->strideBitIncCb     = inputPicturePtr->strideCb;
526 		inputPicturePtr->strideBitIncCr     = inputPicturePtr->strideCr;
527 
528         pictureControlSetPtr->ebInputPtr    = ebInputPtr;
529         pictureControlSetPtr->ebInputWrapperPtr = ebInputWrapperPtr;
530 
531         endOfSequenceFlag = (ebInputPtr->nFlags & EB_BUFFERFLAG_EOS) ? EB_TRUE : EB_FALSE;
532 
533         pictureControlSetPtr->sequenceControlSetWrapperPtr    = contextPtr->sequenceControlSetActiveArray[instanceIndex];
534         pictureControlSetPtr->inputPictureWrapperPtr          = inputPictureWrapperPtr;
535 
536         // Set Picture Control Flags
537         pictureControlSetPtr->idrFlag                         = sequenceControlSetPtr->encodeContextPtr->initialPicture || (ebInputPtr->sliceType == EB_IDR_PICTURE);
538         pictureControlSetPtr->craFlag                         = (ebInputPtr->sliceType == EB_I_PICTURE) ? EB_TRUE : EB_FALSE;
539         pictureControlSetPtr->sceneChangeFlag                 = EB_FALSE;
540 
541         pictureControlSetPtr->qpOnTheFly                      = EB_FALSE;
542 
543 		//pictureControlSetPtr->lcuTotalCount					  = sequenceControlSetPtr->lcuTotalCount;
544 
545 		if (sequenceControlSetPtr->staticConfig.speedControlFlag) {
546 			SpeedBufferControl(
547 				contextPtr,
548 				pictureControlSetPtr,
549 				sequenceControlSetPtr);
550 		}
551 		else {
552 			pictureControlSetPtr->encMode = (EB_ENC_MODE)sequenceControlSetPtr->staticConfig.encMode;
553 		}
554 
555 		// Set the SCD Mode
556 		sequenceControlSetPtr->scdMode = sequenceControlSetPtr->staticConfig.sceneChangeDetection == 0 ?
557 			SCD_MODE_0 :
558 			SCD_MODE_1 ;
559 
560         SignalDerivationPreAnalysisOq(
561                 sequenceControlSetPtr,
562                 pictureControlSetPtr);
563 
564 	    // Rate Control
565 		// Set the ME Distortion and OIS Historgrams to zero
566         if (sequenceControlSetPtr->staticConfig.rateControlMode){
567 	            EB_MEMSET(pictureControlSetPtr->meDistortionHistogram, 0, NUMBER_OF_SAD_INTERVALS*sizeof(EB_U16));
568 	            EB_MEMSET(pictureControlSetPtr->oisDistortionHistogram, 0, NUMBER_OF_INTRA_SAD_INTERVALS*sizeof(EB_U16));
569         }
570 	    pictureControlSetPtr->fullLcuCount                    = 0;
571 
572         if (sequenceControlSetPtr->staticConfig.useQpFile == 1){
573             pictureControlSetPtr->qpOnTheFly = EB_TRUE;
574             if (ebInputPtr->qpValue > 51)
575                 CHECK_REPORT_ERROR_NC(contextPtr->sequenceControlSetInstanceArray[instanceIndex]->encodeContextPtr->appCallbackPtr, EB_ENC_RES_COORD_InvalidQP);
576             pictureControlSetPtr->pictureQp = (EB_U8)ebInputPtr->qpValue;
577         }
578         else {
579             pictureControlSetPtr->qpOnTheFly = EB_FALSE;
580             pictureControlSetPtr->pictureQp = (EB_U8)sequenceControlSetPtr->qp;
581         }
582 
583         // Picture Stats
584         pictureControlSetPtr->pictureNumber                   = contextPtr->pictureNumberArray[instanceIndex]++;
585 
586 #if DEADLOCK_DEBUG
587         if ((pictureControlSetPtr->pictureNumber >= MIN_POC) && (pictureControlSetPtr->pictureNumber <= MAX_POC))
588             if (!endOfSequenceFlag)
589                 SVT_LOG("POC %lu RESCOOR IN \n", pictureControlSetPtr->pictureNumber);
590 #endif
591         // Set the picture structure: 0: progressive, 1: top, 2: bottom
592         pictureControlSetPtr->pictStruct = sequenceControlSetPtr->interlacedVideo == EB_FALSE ?
593             PROGRESSIVE_PICT_STRUCT :
594             pictureControlSetPtr->pictureNumber % 2 == 0 ?
595                 TOP_FIELD_PICT_STRUCT :
596                 BOTTOM_FIELD_PICT_STRUCT ;
597 
598         sequenceControlSetPtr->encodeContextPtr->initialPicture = EB_FALSE;
599 
600         // Get Empty Reference Picture Object
601         EbGetEmptyObject(
602             sequenceControlSetPtr->encodeContextPtr->paReferencePicturePoolFifoPtr,
603             &referencePictureWrapperPtr);
604 
605         pictureControlSetPtr->paReferencePictureWrapperPtr = referencePictureWrapperPtr;
606 
607         // Note: the PPCS and its PA reference picture will be released in both EncDec and RateControl kernels.
608         // Give the new Reference a nominal liveCount of 2
609         EbObjectIncLiveCount(
610                 pictureControlSetPtr->paReferencePictureWrapperPtr,
611                 2);
612 
613         // Get Empty Output Results Object
614         // Note: record the PCS object into output of the Resource Coordination process for EOS frame(s).
615         //       Because EbH265GetPacket() can get the encoded bit stream only if Packetization process has
616         //       posted the buffer as its result, and the buffer belonging to a PCS object is recorded in
617         //       the Initial Rate Control process. So need to record the PCS object immediately once the
618         //       1st frame is EOS, to make it go through the whole encoding kernels.
619         if (((pictureControlSetPtr->pictureNumber > 0) && (prevPictureControlSetWrapperPtr != (EbObjectWrapper_t*)EB_NULL)) ||
620                 endOfSequenceFlag) {
621             if (prevPictureControlSetWrapperPtr && prevPictureControlSetWrapperPtr->objectPtr)
622                 ((PictureParentControlSet_t *)prevPictureControlSetWrapperPtr->objectPtr)->endOfSequenceFlag = endOfSequenceFlag;
623 
624             EbGetEmptyObject(
625                     contextPtr->resourceCoordinationResultsOutputFifoPtr,
626                     &outputWrapperPtr);
627             outputResultsPtr = (ResourceCoordinationResults_t *)outputWrapperPtr->objectPtr;
628             if (endOfSequenceFlag && (pictureControlSetPtr->pictureNumber == 0)) {
629                 ((PictureParentControlSet_t *)pictureControlSetWrapperPtr->objectPtr)->endOfSequenceFlag = endOfSequenceFlag;
630                 outputResultsPtr->pictureControlSetWrapperPtr = pictureControlSetWrapperPtr;
631             } else
632                 outputResultsPtr->pictureControlSetWrapperPtr = prevPictureControlSetWrapperPtr;
633 
634             // Post the finished Results Object
635             EbPostFullObject(outputWrapperPtr);
636 #if DEADLOCK_DEBUG
637             if ((((PictureParentControlSet_t *)outputResultsPtr->pictureControlSetWrapperPtr->objectPtr)->pictureNumber >= MIN_POC) &&
638                     (((PictureParentControlSet_t *)outputResultsPtr->pictureControlSetWrapperPtr->objectPtr)->pictureNumber <= MAX_POC))
639                 SVT_LOG("POC %lu RESCOOR OUT \n", ((PictureParentControlSet_t *)outputResultsPtr->pictureControlSetWrapperPtr->objectPtr)->pictureNumber);
640 #endif
641         }
642 
643         prevPictureControlSetWrapperPtr = pictureControlSetWrapperPtr;
644 
645         if (sequenceControlSetPtr->staticConfig.segmentOvEnabled) {
646             EB_MEMCPY(pictureControlSetPtr->segmentOvArray, ebInputPtr->segmentOvPtr, sizeof(SegmentOverride_t) * sequenceControlSetPtr->lcuTotalCount);
647         }
648     }
649 
650     return EB_NULL;
651 }
652