1 /*
2 * Copyright (c) 2017-2020, Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included
12 * in all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 */
22 //!
23 //! \file codechal_decode_jpeg_g12.cpp
24 //! \brief Implements the decode interface extension for JPEG.
25 //! \details Implements all functions and constants required by CodecHal for JPEG decoding.
26 //!
27
28 #include "codechal_decoder.h"
29 #include "codechal_decode_jpeg_g12.h"
30 #include "mhw_vdbox_mfx_g12_X.h"
31 #include "codechal_mmc_decode_jpeg_g12.h"
32 #include "codechal_decode_sfc_jpeg_g12.h"
33 #include "hal_oca_interface.h"
34
35
~CodechalDecodeJpegG12()36 CodechalDecodeJpegG12::~CodechalDecodeJpegG12()
37 {
38 CODECHAL_DECODE_FUNCTION_ENTER;
39
40 if (m_veState != nullptr)
41 {
42 MOS_FreeMemAndSetNull(m_veState);
43 m_veState = nullptr;
44 }
45 }
46
InitMmcState()47 MOS_STATUS CodechalDecodeJpegG12::InitMmcState()
48 {
49 #ifdef _MMC_SUPPORTED
50 m_mmc = MOS_New(CodechalMmcDecodeJpegG12, m_hwInterface, this);
51 CODECHAL_DECODE_CHK_NULL_RETURN(m_mmc);
52 #endif
53 return MOS_STATUS_SUCCESS;
54 }
55
56 #ifdef _DECODE_PROCESSING_SUPPORTED
InitSfcState()57 MOS_STATUS CodechalDecodeJpegG12::InitSfcState()
58 {
59 m_sfcState = MOS_New(CodechalJpegSfcStateG12);
60 CODECHAL_DECODE_CHK_NULL_RETURN(m_sfcState);
61 return MOS_STATUS_SUCCESS;
62 }
63 #endif
64
SetGpuCtxCreatOption(CodechalSetting * codecHalSetting)65 MOS_STATUS CodechalDecodeJpegG12::SetGpuCtxCreatOption(
66 CodechalSetting *codecHalSetting)
67 {
68 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
69
70 CODECHAL_DECODE_FUNCTION_ENTER;
71
72 if (!MOS_VE_CTXBASEDSCHEDULING_SUPPORTED(m_osInterface))
73 {
74 CodechalDecode::SetGpuCtxCreatOption(codecHalSetting);
75 }
76 else
77 {
78 m_gpuCtxCreatOpt = MOS_New(MOS_GPUCTX_CREATOPTIONS_ENHANCED);
79 bool sfcInUse = codecHalSetting->sfcInUseHinted && IsSfcInUse(codecHalSetting);
80 CODECHAL_DECODE_CHK_STATUS_RETURN(CodecHalDecodeSinglePipeVE_ConstructParmsForGpuCtxCreation(
81 m_veState,
82 (PMOS_GPUCTX_CREATOPTIONS_ENHANCED)m_gpuCtxCreatOpt,
83 sfcInUse));
84 }
85
86 return eStatus;
87 }
88
SetFrameStates()89 MOS_STATUS CodechalDecodeJpegG12::SetFrameStates()
90 {
91 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
92
93 CODECHAL_DECODE_FUNCTION_ENTER;
94
95 CODECHAL_DECODE_CHK_STATUS_RETURN(CodechalDecodeJpeg::SetFrameStates());
96
97 if (MOS_VE_SUPPORTED(m_osInterface) && !MOS_VE_CTXBASEDSCHEDULING_SUPPORTED(m_osInterface))
98 {
99 MOS_VIRTUALENGINE_SET_PARAMS vesetParams;
100
101 MOS_ZeroMemory(&vesetParams, sizeof(vesetParams));
102 #ifdef _DECODE_PROCESSING_SUPPORTED
103 vesetParams.bSFCInUse = m_sfcState->m_sfcPipeOut;
104 #else
105 vesetParams.bSFCInUse = false;
106 #endif
107 vesetParams.bNeedSyncWithPrevious = true;
108 vesetParams.bSameEngineAsLastSubmission = false;
109 CODECHAL_DECODE_CHK_STATUS_RETURN(CodecHalDecodeSinglePipeVE_SetHintParams(
110 m_veState,
111 &vesetParams));
112 }
113
114 return eStatus;
115 }
116
DecodeStateLevel()117 MOS_STATUS CodechalDecodeJpegG12::DecodeStateLevel()
118 {
119 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
120
121 CODECHAL_DECODE_FUNCTION_ENTER;
122 #ifdef _MMC_SUPPORTED
123 // To WA invalid aux data caused HW issue when MMC on
124 // Add disable Clear CCS WA due to green corruption issue
125 if (m_mmc->IsMmcEnabled() && !Mos_ResourceIsNull(&m_destSurface.OsResource) &&
126 m_destSurface.OsResource.bConvertedFromDDIResource)
127 {
128 if (MEDIA_IS_WA(m_waTable, Wa_1408785368) || MEDIA_IS_WA(m_waTable, Wa_22010493002) && (!MEDIA_IS_WA(m_waTable, WaDisableClearCCS)))
129 {
130 CODECHAL_DECODE_VERBOSEMESSAGE("Clear CCS by VE resolve before frame %d submission", m_frameNum);
131 CODECHAL_DECODE_CHK_STATUS_RETURN(static_cast<CodecHalMmcStateG12 *>(m_mmc)->ClearAuxSurf(
132 this, m_miInterface, &m_destSurface.OsResource, m_veState));
133 }
134 }
135 #endif
136
137 MHW_VDBOX_JPEG_DECODE_PIC_STATE jpegPicState;
138 jpegPicState.dwOutputFormat = m_decodeParams.m_destSurface->Format;
139
140 #ifdef _DECODE_PROCESSING_SUPPORTED
141 if (m_sfcState->m_sfcPipeOut)
142 {
143 jpegPicState.dwOutputFormat = m_sfcState->m_sfcInSurface.Format;
144 }
145 #endif
146
147 //Three new formats from HSW C0,HSW ULT can only be supported in specific conditions.
148 if (jpegPicState.dwOutputFormat == Format_NV12 ||
149 jpegPicState.dwOutputFormat == Format_YUY2 ||
150 jpegPicState.dwOutputFormat == Format_UYVY)
151 {
152 //Only interleaved single scan are supported.
153 if (m_jpegPicParams->m_totalScans != 1 ||
154 m_jpegPicParams->m_interleavedData == 0)
155 {
156 return MOS_STATUS_UNKNOWN;
157 }
158
159 switch (m_jpegPicParams->m_chromaType)
160 {
161 case jpegYUV420:
162 case jpegYUV422H2Y:
163 case jpegYUV422H4Y:
164 break;
165 case jpegYUV422V2Y:
166 case jpegYUV422V4Y:
167 if (jpegPicState.dwOutputFormat == Format_NV12)
168 {
169 break;
170 }
171 default:
172 return MOS_STATUS_UNKNOWN;
173 }
174 }
175
176 MOS_COMMAND_BUFFER cmdBuffer;
177 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnGetCommandBuffer(
178 m_osInterface,
179 &cmdBuffer,
180 0));
181
182 auto mmioRegisters = m_hwInterface->GetMfxInterface()->GetMmioRegisters(m_vdboxIndex);
183 HalOcaInterface::On1stLevelBBStart(cmdBuffer, *m_osInterface->pOsContext, m_osInterface->CurrentGpuContextHandle, *m_miInterface, *mmioRegisters);
184
185 MHW_MI_FORCE_WAKEUP_PARAMS forceWakeupParams;
186 MOS_ZeroMemory(&forceWakeupParams, sizeof(MHW_MI_FORCE_WAKEUP_PARAMS));
187 forceWakeupParams.bMFXPowerWellControl = true;
188 forceWakeupParams.bMFXPowerWellControlMask = true;
189 forceWakeupParams.bHEVCPowerWellControl = false;
190 forceWakeupParams.bHEVCPowerWellControlMask = true;
191 CODECHAL_DECODE_CHK_STATUS_RETURN(m_miInterface->AddMiForceWakeupCmd(
192 &cmdBuffer,
193 &forceWakeupParams));
194
195 CODECHAL_DECODE_CHK_STATUS_RETURN(SendPrologWithFrameTracking(
196 &cmdBuffer, true));
197
198 // Set PIPE_MODE_SELECT
199 MHW_VDBOX_PIPE_MODE_SELECT_PARAMS pipeModeSelectParams;
200 pipeModeSelectParams.Mode = CODECHAL_DECODE_MODE_JPEG;
201 pipeModeSelectParams.bStreamOutEnabled = m_streamOutEnabled;
202 pipeModeSelectParams.bDeblockerStreamOutEnable = false;
203 pipeModeSelectParams.bPostDeblockOutEnable = false;
204 pipeModeSelectParams.bPreDeblockOutEnable = true;
205
206 // Set CMD_MFX_SURFACE_STATE
207 MHW_VDBOX_SURFACE_PARAMS surfaceParams;
208 MOS_ZeroMemory(&surfaceParams, sizeof(surfaceParams));
209 surfaceParams.Mode = CODECHAL_DECODE_MODE_JPEG;
210 surfaceParams.psSurface = &m_destSurface;
211 surfaceParams.ChromaType = m_jpegPicParams->m_chromaType;
212
213 #ifdef _DECODE_PROCESSING_SUPPORTED
214 if (m_sfcState->m_sfcPipeOut)
215 {
216 surfaceParams.psSurface = &m_sfcState->m_sfcInSurface;
217 }
218 #endif
219
220 // Set MFX_PIPE_BUF_ADDR_STATE_CMD
221 MHW_VDBOX_PIPE_BUF_ADDR_PARAMS pipeBufAddrParams;
222 pipeBufAddrParams.Mode = CODECHAL_DECODE_MODE_JPEG;
223 // Predeblock surface is the same as destination surface here because there is no deblocking for JPEG
224 pipeBufAddrParams.psPreDeblockSurface = &m_destSurface;
225
226 #ifdef _MMC_SUPPORTED
227 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mmc->SetPipeBufAddr(&pipeBufAddrParams));
228 #endif
229
230 // Set MFX_IND_OBJ_BASE_ADDR_STATE_CMD
231 MHW_VDBOX_IND_OBJ_BASE_ADDR_PARAMS indObjBaseAddrParams;
232 MOS_ZeroMemory(&indObjBaseAddrParams, sizeof(indObjBaseAddrParams));
233 indObjBaseAddrParams.Mode = CODECHAL_DECODE_MODE_JPEG;
234 indObjBaseAddrParams.dwDataSize = m_copiedDataBufferInUse ? m_nextCopiedDataOffset : m_dataSize;
235 indObjBaseAddrParams.presDataBuffer = &m_resDataBuffer;
236
237 // Set MFX_JPEG_PIC_STATE_CMD
238 jpegPicState.pJpegPicParams = m_jpegPicParams;
239 if ((m_jpegPicParams->m_rotation == jpegRotation90) || (m_jpegPicParams->m_rotation == jpegRotation270))
240 {
241 jpegPicState.dwWidthInBlocks = (m_destSurface.dwHeight / CODECHAL_DECODE_JPEG_BLOCK_SIZE) - 1;
242 jpegPicState.dwHeightInBlocks = (m_destSurface.dwWidth / CODECHAL_DECODE_JPEG_BLOCK_SIZE) - 1;
243 }
244 else
245 {
246 jpegPicState.dwWidthInBlocks = (m_destSurface.dwWidth / CODECHAL_DECODE_JPEG_BLOCK_SIZE) - 1;
247 jpegPicState.dwHeightInBlocks = (m_destSurface.dwHeight / CODECHAL_DECODE_JPEG_BLOCK_SIZE) - 1;
248 }
249
250 // Add commands to command buffer
251 // MI_FLUSH_DW command -> must be before to MFX_PIPE_MODE_SELECT
252 MHW_MI_FLUSH_DW_PARAMS flushDwParams;
253 MOS_ZeroMemory(&flushDwParams, sizeof(flushDwParams));
254 CODECHAL_DECODE_CHK_STATUS_RETURN(m_miInterface->AddMiFlushDwCmd(
255 &cmdBuffer,
256 &flushDwParams));
257
258 if (m_statusQueryReportingEnabled)
259 {
260 CODECHAL_DECODE_CHK_STATUS_RETURN(StartStatusReport(
261 &cmdBuffer));
262 }
263
264 // MFX_PIPE_MODE_SELECT_CMD
265 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxPipeModeSelectCmd(
266 &cmdBuffer,
267 &pipeModeSelectParams));
268
269 #ifdef _DECODE_PROCESSING_SUPPORTED
270 // Output decode result through SFC
271 CODECHAL_DECODE_CHK_STATUS_RETURN(m_sfcState->AddSfcCommands(&cmdBuffer));
272 #endif
273
274 // CMD_MFX_SURFACE_STATE
275 #ifdef _MMC_SUPPORTED
276 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mmc->SetSurfaceState(&surfaceParams)); //class CodechalMmcDecodeJpegG12
277 #endif
278 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxSurfaceCmd(
279 &cmdBuffer,
280 &surfaceParams));
281
282 // MFX_PIPE_BUF_ADDR_STATE_CMD
283 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxPipeBufAddrCmd(
284 &cmdBuffer,
285 &pipeBufAddrParams));
286
287 // MFX_IND_OBJ_BASE_ADDR_STATE_CMD
288 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxIndObjBaseAddrCmd(
289 &cmdBuffer,
290 &indObjBaseAddrParams));
291
292 // MFX_JPEG_PIC_STATE_CMD
293 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxJpegPicCmd(
294 &cmdBuffer,
295 &jpegPicState));
296
297 m_osInterface->pfnReturnCommandBuffer(m_osInterface, &cmdBuffer, 0);
298
299 return eStatus;
300 }
301
DecodePrimitiveLevel()302 MOS_STATUS CodechalDecodeJpegG12::DecodePrimitiveLevel()
303 {
304 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
305
306 CODECHAL_DECODE_FUNCTION_ENTER;
307
308 // if the bitstream is not complete, don't do any decoding work.
309 if (m_incompletePicture)
310 {
311 return MOS_STATUS_SUCCESS;
312
313 }
314
315 CODECHAL_DECODE_CHK_NULL_RETURN(m_osInterface);
316
317 MOS_COMMAND_BUFFER cmdBuffer;
318 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnGetCommandBuffer(
319 m_osInterface,
320 &cmdBuffer,
321 0));
322
323 // MFX_QM_STATE_CMD
324 MHW_VDBOX_QM_PARAMS qmParams;
325 MOS_ZeroMemory(&qmParams, sizeof(qmParams));
326 qmParams.Standard = CODECHAL_JPEG;
327 qmParams.pJpegQuantMatrix = m_jpegQMatrix;
328
329 // Swapping QM(x,y) to QM(y,x) for 90/270 degree rotation
330 if ((m_jpegPicParams->m_rotation == jpegRotation90) ||
331 (m_jpegPicParams->m_rotation == jpegRotation270))
332 {
333 qmParams.bJpegQMRotation = true;
334 }
335 else
336 {
337 qmParams.bJpegQMRotation = false;
338 }
339
340 for (uint16_t scanCount = 0; scanCount < m_jpegPicParams->m_numCompInFrame; scanCount++)
341 {
342 // Using scanCount here because the same command is used for JPEG decode and encode
343 uint32_t quantTableSelector = m_jpegPicParams->m_quantTableSelector[scanCount];
344 if (quantTableSelector >= JPEG_MAX_NUM_OF_QUANTMATRIX)
345 {
346 CODECHAL_DECODE_ASSERTMESSAGE("Unsupported QuantTableSelector in JPEG Picture parameter.");
347 return MOS_STATUS_INVALID_PARAMETER;
348 }
349 qmParams.pJpegQuantMatrix->m_jpegQMTableType[quantTableSelector] = scanCount;
350 qmParams.JpegQMTableSelector = quantTableSelector;
351 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxQmCmd(
352 &cmdBuffer,
353 &qmParams));
354 }
355
356 uint32_t dcCurHuffTblIndex[2] = { 0xff, 0xff };
357 uint32_t acCurHuffTblIndex[2] = { 0xff, 0xff };
358
359 for (uint16_t scanCount = 0; scanCount < m_jpegScanParams->NumScans; scanCount++)
360 {
361 // MFX_JPEG_HUFF_TABLE
362 uint16_t numComponents = m_jpegScanParams->ScanHeader[scanCount].NumComponents;
363 for (uint16_t scanComponent = 0; scanComponent < numComponents; scanComponent++)
364 {
365 // Determine which huffman table we will be writing to
366 // For gray image, componentIdentifier[jpegComponentU] and componentIdentifier[jpegComponentV] are initialized to 0,
367 // and when componentSelector[scanComponent] is equal 0, variable huffTableID is set to 1, and wrong Huffman table is used,
368 // so it is more reasonable to use componentIdentifier[jpegComponentY] to determine which huffman table we will be writing to.
369 uint8_t componentSelector =
370 m_jpegScanParams->ScanHeader[scanCount].ComponentSelector[scanComponent];
371 uint16_t huffTableID = 0;
372 if (componentSelector == m_jpegPicParams->m_componentIdentifier[jpegComponentY])
373 {
374 huffTableID = 0;
375 }
376 else
377 {
378 huffTableID = 1;
379 }
380
381 int32_t acTableSelector =
382 m_jpegScanParams->ScanHeader[scanCount].AcHuffTblSelector[scanComponent];
383 int32_t dcTableSelector =
384 m_jpegScanParams->ScanHeader[scanCount].DcHuffTblSelector[scanComponent];
385
386 // Send the huffman table state command only if the table changed
387 if ((dcTableSelector != dcCurHuffTblIndex[huffTableID]) ||
388 (acTableSelector != acCurHuffTblIndex[huffTableID]))
389 {
390 MHW_VDBOX_HUFF_TABLE_PARAMS huffmanTableParams;
391 MOS_ZeroMemory(&huffmanTableParams, sizeof(huffmanTableParams));
392
393 huffmanTableParams.HuffTableID = huffTableID;
394 if (acTableSelector >= JPEG_MAX_NUM_HUFF_TABLE_INDEX || dcTableSelector >= JPEG_MAX_NUM_HUFF_TABLE_INDEX)
395 return MOS_STATUS_INVALID_PARAMETER;
396
397 huffmanTableParams.pACBits = &m_jpegHuffmanTable->HuffTable[acTableSelector].AC_BITS[0];
398 huffmanTableParams.pDCBits = &m_jpegHuffmanTable->HuffTable[dcTableSelector].DC_BITS[0];
399 huffmanTableParams.pACValues = &m_jpegHuffmanTable->HuffTable[acTableSelector].AC_HUFFVAL[0];
400 huffmanTableParams.pDCValues = &m_jpegHuffmanTable->HuffTable[dcTableSelector].DC_HUFFVAL[0];
401
402 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxJpegHuffTableCmd(
403 &cmdBuffer,
404 &huffmanTableParams));
405
406 // Set the current huffman table indices for the next scan
407 dcCurHuffTblIndex[huffTableID] = dcTableSelector;
408 acCurHuffTblIndex[huffTableID] = acTableSelector;
409 }
410 }
411
412 MHW_VDBOX_JPEG_BSD_PARAMS jpegBsdObject;
413 MOS_ZeroMemory(&jpegBsdObject, sizeof(jpegBsdObject));
414
415 // MFX_JPEG_BSD_OBJECT
416 jpegBsdObject.dwIndirectDataLength = m_jpegScanParams->ScanHeader[scanCount].DataLength;
417 jpegBsdObject.dwDataStartAddress = m_jpegScanParams->ScanHeader[scanCount].DataOffset;
418 jpegBsdObject.dwScanHorizontalPosition = m_jpegScanParams->ScanHeader[scanCount].ScanHoriPosition;
419 jpegBsdObject.dwScanVerticalPosition = m_jpegScanParams->ScanHeader[scanCount].ScanVertPosition;
420 jpegBsdObject.bInterleaved = (numComponents > 1) ? 1 : 0;
421 jpegBsdObject.dwMCUCount = m_jpegScanParams->ScanHeader[scanCount].MCUCount;
422 jpegBsdObject.dwRestartInterval = m_jpegScanParams->ScanHeader[scanCount].RestartInterval;
423
424 uint16_t scanComponentIndex = 0;
425
426 for (uint16_t scanComponent = 0; scanComponent < numComponents; scanComponent++)
427 {
428 uint8_t componentSelector =
429 m_jpegScanParams->ScanHeader[scanCount].ComponentSelector[scanComponent];
430
431 if (componentSelector == m_jpegPicParams->m_componentIdentifier[jpegComponentY])
432 {
433 scanComponentIndex = 0;
434 }
435 else if (componentSelector == m_jpegPicParams->m_componentIdentifier[jpegComponentU])
436 {
437 scanComponentIndex = 1;
438 }
439 else if (componentSelector == m_jpegPicParams->m_componentIdentifier[jpegComponentV])
440 {
441 scanComponentIndex = 2;
442 }
443 // Add logic for component identifier JPEG_A
444
445 jpegBsdObject.sScanComponent |= (1 << scanComponentIndex);
446 }
447
448 CODECHAL_DECODE_CHK_STATUS_RETURN(m_mfxInterface->AddMfxJpegBsdObjCmd(
449 &cmdBuffer,
450 &jpegBsdObject));
451 }
452
453 // Check if destination surface needs to be synchronized
454 MOS_SYNC_PARAMS syncParams = g_cInitSyncParams;
455 syncParams.GpuContext = m_videoContext;
456 syncParams.presSyncResource = &m_destSurface.OsResource;
457 syncParams.bReadOnly = false;
458 syncParams.bDisableDecodeSyncLock = m_disableDecodeSyncLock;
459 syncParams.bDisableLockForTranscode = m_disableLockForTranscode;
460
461 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnPerformOverlaySync(
462 m_osInterface,
463 &syncParams));
464 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnResourceWait(
465 m_osInterface,
466 &syncParams));
467
468 // Update the resource tag (s/w tag) for On-Demand Sync
469 m_osInterface->pfnSetResourceSyncTag(m_osInterface, &syncParams);
470
471 MHW_MI_FLUSH_DW_PARAMS flushDwParams;
472 MOS_ZeroMemory(&flushDwParams, sizeof(flushDwParams));
473 CODECHAL_DECODE_CHK_STATUS_RETURN(m_miInterface->AddMiFlushDwCmd(
474 &cmdBuffer,
475 &flushDwParams));
476
477 // Update the tag in GPU Sync eStatus buffer (H/W Tag) to match the current S/W tag
478 if (m_osInterface->bTagResourceSync)
479 {
480 CODECHAL_DECODE_CHK_STATUS_RETURN(m_hwInterface->WriteSyncTagToResource(
481 &cmdBuffer,
482 &syncParams));
483 }
484
485 if (m_statusQueryReportingEnabled)
486 {
487 CodechalDecodeStatusReport decodeStatusReport;
488 decodeStatusReport.m_statusReportNumber = m_statusReportFeedbackNumber;
489 decodeStatusReport.m_codecStatus = CODECHAL_STATUS_UNAVAILABLE;
490 decodeStatusReport.m_currDecodedPicRes = m_destSurface.OsResource;
491
492 CODECHAL_DECODE_CHK_STATUS_RETURN(EndStatusReport(
493 decodeStatusReport,
494 &cmdBuffer));
495 }
496
497 #if (_DEBUG || _RELEASE_INTERNAL)
498 uint32_t curIdx = (GetDecodeStatusBuf()->m_currIndex + CODECHAL_DECODE_STATUS_NUM - 1) % CODECHAL_DECODE_STATUS_NUM;
499 uint32_t frameCrcOffset = curIdx * sizeof(CodechalDecodeStatus) + GetDecodeStatusBuf()->m_decFrameCrcOffset + sizeof(uint32_t) * 2;
500 std::vector<MOS_RESOURCE> vSemaResource{GetDecodeStatusBuf()->m_statusBuffer};
501 m_debugInterface->DetectCorruptionHw(m_hwInterface, &m_frameCountTypeBuf, curIdx, frameCrcOffset, vSemaResource, &cmdBuffer, m_frameNum);
502 #endif
503
504 CODECHAL_DECODE_CHK_STATUS_RETURN(m_miInterface->AddMiBatchBufferEnd(
505 &cmdBuffer,
506 nullptr));
507
508 m_osInterface->pfnReturnCommandBuffer(m_osInterface, &cmdBuffer, 0);
509
510 CODECHAL_DEBUG_TOOL(
511 CODECHAL_DECODE_CHK_STATUS_RETURN(m_debugInterface->DumpCmdBuffer(
512 &cmdBuffer,
513 CODECHAL_NUM_MEDIA_STATES,
514 "_JPEG_DECODE_0"));
515 )
516
517 if (m_copiedDataBufferInUse)
518 {
519 //Sync up complete frame
520 syncParams = g_cInitSyncParams;
521 syncParams.GpuContext = m_videoContextForWa;
522 syncParams.presSyncResource = &m_resSyncObjectWaContextInUse;
523
524 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnEngineSignal(
525 m_osInterface,
526 &syncParams));
527
528 syncParams = g_cInitSyncParams;
529 syncParams.GpuContext = m_videoContext;
530 syncParams.presSyncResource = &m_resSyncObjectWaContextInUse;
531
532 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnEngineWait(
533 m_osInterface,
534 &syncParams));
535 }
536
537 if ( MOS_VE_SUPPORTED(m_osInterface))
538 {
539 CodecHalDecodeSinglePipeVE_PopulateHintParams(m_veState, &cmdBuffer, false);
540 }
541
542 HalOcaInterface::On1stLevelBBEnd(cmdBuffer, *m_osInterface);
543
544 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnSubmitCommandBuffer(
545 m_osInterface,
546 &cmdBuffer,
547 m_videoContextUsesNullHw));
548
549 CODECHAL_DEBUG_TOOL(
550 m_mmc->UpdateUserFeatureKey(&m_destSurface);)
551
552 if (m_statusQueryReportingEnabled)
553 {
554 CODECHAL_DECODE_CHK_STATUS_RETURN(ResetStatusReport(
555 m_videoContextUsesNullHw));
556 }
557
558 // Set output surface layout
559 SetOutputSurfaceLayout(&m_decodeParams.m_outputSurfLayout);
560
561 // Send the signal to indicate decode completion, in case On-Demand Sync is not present
562 CODECHAL_DECODE_CHK_STATUS_RETURN(m_osInterface->pfnResourceSignal(
563 m_osInterface,
564 &syncParams));
565
566 CODECHAL_DEBUG_TOOL(
567 CODECHAL_DECODE_CHK_STATUS_RETURN(m_debugInterface->DumpYUVSurface(
568 &m_destSurface,
569 CodechalDbgAttr::attrDecodeOutputSurface,
570 "DstSurf"));)
571 return eStatus;
572 }
573
AllocateStandard(CodechalSetting * settings)574 MOS_STATUS CodechalDecodeJpegG12::AllocateStandard(
575 CodechalSetting * settings)
576 {
577 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
578
579 CODECHAL_DECODE_FUNCTION_ENTER;
580
581 CODECHAL_DECODE_CHK_NULL_RETURN(settings);
582
583 CODECHAL_DECODE_CHK_STATUS_RETURN(CodechalDecodeJpeg::AllocateStandard(settings));
584
585 #ifdef _MMC_SUPPORTED
586 // To WA invalid aux data caused HW issue when MMC on
587 // Add disable Clear CCS WA due to green corruption issue
588 if (m_mmc->IsMmcEnabled())
589 {
590 if (MEDIA_IS_WA(m_waTable, Wa_1408785368) || MEDIA_IS_WA(m_waTable, Wa_22010493002) && (!MEDIA_IS_WA(m_waTable, WaDisableClearCCS)))
591 {
592 MHW_VDBOX_STATE_CMDSIZE_PARAMS stateCmdSizeParams;
593
594 //Add HUC STATE Commands
595 m_hwInterface->GetHucStateCommandSize(
596 CODECHAL_DECODE_MODE_JPEG,
597 &m_HucStateCmdBufferSizeNeeded,
598 &m_HucPatchListSizeNeeded,
599 &stateCmdSizeParams);
600 }
601 }
602 #endif
603
604 if ( MOS_VE_SUPPORTED(m_osInterface))
605 {
606 static_cast<MhwVdboxMfxInterfaceG12*>(m_mfxInterface)->DisableScalabilitySupport();
607
608 //single pipe VE initialize
609 m_veState = (PCODECHAL_DECODE_SINGLEPIPE_VIRTUALENGINE_STATE)MOS_AllocAndZeroMemory(sizeof(CODECHAL_DECODE_SINGLEPIPE_VIRTUALENGINE_STATE));
610 CODECHAL_DECODE_CHK_NULL_RETURN(m_veState);
611 CODECHAL_DECODE_CHK_STATUS_RETURN(CodecHalDecodeSinglePipeVE_InitInterface(m_osInterface, m_veState));
612 }
613
614 return eStatus;
615 }
616
CodechalDecodeJpegG12(CodechalHwInterface * hwInterface,CodechalDebugInterface * debugInterface,PCODECHAL_STANDARD_INFO standardInfo)617 CodechalDecodeJpegG12::CodechalDecodeJpegG12(
618 CodechalHwInterface *hwInterface,
619 CodechalDebugInterface* debugInterface,
620 PCODECHAL_STANDARD_INFO standardInfo) :
621 CodechalDecodeJpeg(hwInterface, debugInterface, standardInfo)
622 {
623 CODECHAL_DECODE_FUNCTION_ENTER;
624
625 CODECHAL_DECODE_CHK_NULL_NO_STATUS_RETURN(m_osInterface);
626
627 m_osInterface->pfnVirtualEngineSupported(m_osInterface, true, true);
628 }
629
CalcRequestedSpace(uint32_t & requestedSize,uint32_t & additionalSizeNeeded,uint32_t & requestedPatchListSize)630 void CodechalDecodeJpegG12::CalcRequestedSpace(
631 uint32_t &requestedSize,
632 uint32_t &additionalSizeNeeded,
633 uint32_t &requestedPatchListSize)
634 {
635 CODECHAL_DECODE_FUNCTION_ENTER;
636
637 requestedSize = m_commandBufferSizeNeeded + m_HucStateCmdBufferSizeNeeded +
638 (m_standardDecodeSizeNeeded * (m_decodeParams.m_numSlices + 1));
639 requestedPatchListSize = m_commandPatchListSizeNeeded + m_HucPatchListSizeNeeded +
640 (m_standardDecodePatchListSizeNeeded * (m_decodeParams.m_numSlices + 1));
641 additionalSizeNeeded = COMMAND_BUFFER_RESERVED_SPACE;
642 }
643
644