1 /*
2 * Copyright (c) 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     encode_packet_utilities.cpp
24 //! \brief    Defines encode packrt utilities.
25 //!
26 
27 #include "encode_packet_utilities.h"
28 #include "codec_def_common_encode.h"
29 
30 namespace encode {
Init()31     MOS_STATUS PacketUtilities::Init()
32     {
33 #if USE_CODECHAL_DEBUG_TOOL
34         MediaUserSetting::Value outValue;
35         ReadUserSettingForDebug(
36             m_userSettingPtr,
37             outValue,
38             "Fake Header Size Enable",
39             MediaUserSetting::Group::Sequence);
40         m_enableFakeHrdSize = outValue.Get<uint32_t>();
41 
42         ReadUserSettingForDebug(
43             m_userSettingPtr,
44             outValue,
45             "Fake IFrame Header Size",
46             MediaUserSetting::Group::Sequence);
47         m_fakeIFrameHrdSize = outValue.Get<uint32_t>();
48 
49         ReadUserSettingForDebug(
50             m_userSettingPtr,
51             outValue,
52             "Fake PBFrame Header Size",
53             MediaUserSetting::Group::Sequence);
54         m_fakePBFrameHrdSize = outValue.Get<uint32_t>();
55 #endif
56 
57         return MOS_STATUS_SUCCESS;
58     }
59 
PacketUtilities(CodechalHwInterfaceNext * hwInterface,MediaFeatureManager * featureManager)60     PacketUtilities::PacketUtilities(CodechalHwInterfaceNext *hwInterface, MediaFeatureManager *featureManager)
61     {
62         m_hwInterface       = hwInterface;
63         m_featureManager    = featureManager;
64 
65         ENCODE_CHK_NULL_NO_STATUS_RETURN(hwInterface);
66         m_miItf          = hwInterface->GetMiInterfaceNext();
67         auto osInterface = hwInterface->GetOsInterface();
68         ENCODE_CHK_NULL_NO_STATUS_RETURN(osInterface);
69         m_userSettingPtr = osInterface->pfnGetUserSettingInstance(osInterface);
70         if (!m_userSettingPtr)
71         {
72             ENCODE_NORMALMESSAGE("Initialize m_userSettingPtr instance failed!");
73         }
74     }
75 
~PacketUtilities()76     PacketUtilities::~PacketUtilities()
77     {
78     }
79 
AddMemCopyCmd(PMOS_COMMAND_BUFFER cmdBuf,PMOS_RESOURCE pDst,PMOS_RESOURCE pSrc,uint32_t size)80     MOS_STATUS PacketUtilities::AddMemCopyCmd(PMOS_COMMAND_BUFFER cmdBuf, PMOS_RESOURCE pDst, PMOS_RESOURCE pSrc, uint32_t size)
81     {
82         MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
83 
84         ENCODE_FUNC_CALL();
85 
86         ENCODE_CHK_NULL_RETURN(cmdBuf);
87         ENCODE_CHK_NULL_RETURN(pDst);
88         ENCODE_CHK_NULL_RETURN(pSrc);
89         ENCODE_CHK_NULL_RETURN(m_miItf);
90 
91         auto &copyMemMemParams       = m_miItf->MHW_GETPAR_F(MI_COPY_MEM_MEM)();
92         copyMemMemParams             = {};
93         copyMemMemParams.presSrc     = pSrc;
94         copyMemMemParams.presDst     = pDst;
95         for (uint32_t i = 0; i < size; i = i + 4)
96         {
97             copyMemMemParams.dwSrcOffset = i;
98             copyMemMemParams.dwDstOffset = i;
99             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_COPY_MEM_MEM)(cmdBuf));
100         }
101         return eStatus;
102     }
103 
AddStoreDataImmCmd(PMOS_COMMAND_BUFFER cmdBuf,PMOS_RESOURCE pSrc,uint32_t offset,uint32_t flag)104     MOS_STATUS PacketUtilities::AddStoreDataImmCmd(PMOS_COMMAND_BUFFER cmdBuf, PMOS_RESOURCE pSrc, uint32_t offset, uint32_t flag)
105     {
106         ENCODE_FUNC_CALL();
107         auto &storeDataParam = m_miItf->MHW_GETPAR_F(MI_STORE_DATA_IMM)();
108         storeDataParam                  = {};
109         storeDataParam.pOsResource      = pSrc;
110         storeDataParam.dwResourceOffset = offset;
111         storeDataParam.dwValue          = flag;
112         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_STORE_DATA_IMM)(cmdBuf));
113 
114         auto &flushDwParams                         = m_miItf->MHW_GETPAR_F(MI_FLUSH_DW)();
115         flushDwParams                               = {};
116         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_FLUSH_DW)(cmdBuf));
117         return MOS_STATUS_SUCCESS;
118     }
119 
SendMarkerCommand(PMOS_COMMAND_BUFFER cmdBuffer,PMOS_RESOURCE presSetMarker)120     MOS_STATUS PacketUtilities::SendMarkerCommand(PMOS_COMMAND_BUFFER cmdBuffer, PMOS_RESOURCE presSetMarker)
121     {
122         ENCODE_FUNC_CALL();
123 
124         ENCODE_CHK_NULL_RETURN(cmdBuffer);
125 
126         EncodeBasicFeature *basicFeature = dynamic_cast<EncodeBasicFeature *>(m_featureManager->GetFeature(FeatureIDs::basicFeature));
127         ENCODE_CHK_NULL_RETURN(basicFeature);
128 
129         if (presSetMarker == nullptr)
130         {
131             return MOS_STATUS_SUCCESS;
132         }
133 
134         // Send flush_dw to get the timestamp
135         auto &params             = m_miItf->MHW_GETPAR_F(MI_FLUSH_DW)();
136         params                   = {};
137         params.pOsResource       = presSetMarker;
138         params.dwResourceOffset  = 0;  //sizeof(uint64_t);
139         params.postSyncOperation = MHW_FLUSH_WRITE_TIMESTAMP_REG;
140         params.bQWordEnable      = 1;
141         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_FLUSH_DW)(cmdBuffer));
142 
143         return MOS_STATUS_SUCCESS;
144     }
145 
SendPredicationCommand(PMOS_COMMAND_BUFFER cmdBuffer)146     MOS_STATUS PacketUtilities::SendPredicationCommand(PMOS_COMMAND_BUFFER cmdBuffer)
147     {
148         ENCODE_FUNC_CALL();
149 
150         ENCODE_CHK_NULL_RETURN(cmdBuffer);
151 
152         EncodeBasicFeature *basicFeature = dynamic_cast<EncodeBasicFeature *>(m_featureManager->GetFeature(FeatureIDs::basicFeature));
153         ENCODE_CHK_NULL_RETURN(basicFeature);
154 
155         // Predication can be set based on the value of 64-bits within a buffer
156         auto PreparePredicationBuf = [&](bool predicationNotEqualZero) {
157             auto  mmioRegistersMfx = m_hwInterface->SelectVdAndGetMmioReg(m_vdboxIndex, cmdBuffer);
158             auto &flushDwParams    = m_miItf->MHW_GETPAR_F(MI_FLUSH_DW)();
159             flushDwParams          = {};
160             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_FLUSH_DW)(cmdBuffer));
161 
162             // load presPredication to general purpose register0
163             auto &miLoadRegMemParams           = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_MEM)();
164             miLoadRegMemParams                  = {};
165             miLoadRegMemParams.presStoreBuffer  = basicFeature->m_presPredication;
166             miLoadRegMemParams.dwOffset         = (uint32_t)basicFeature->m_predicationResOffset;
167             miLoadRegMemParams.dwRegister       = mmioRegistersMfx->generalPurposeRegister0LoOffset;
168             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_MEM)(cmdBuffer));
169 
170             auto &miLoadRegImmParams      = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_IMM)();
171             miLoadRegImmParams            = {};
172             miLoadRegImmParams.dwData     = 0;
173             miLoadRegImmParams.dwRegister = mmioRegistersMfx->generalPurposeRegister0HiOffset;
174             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
175 
176             miLoadRegMemParams                 = {};
177             miLoadRegMemParams.presStoreBuffer = basicFeature->m_presPredication;
178             miLoadRegMemParams.dwOffset        = (uint32_t)basicFeature->m_predicationResOffset + sizeof(uint32_t);
179             miLoadRegMemParams.dwRegister      = mmioRegistersMfx->generalPurposeRegister4LoOffset;
180             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_MEM)(cmdBuffer));
181 
182             miLoadRegImmParams            = {};
183             miLoadRegImmParams.dwData     = 0;
184             miLoadRegImmParams.dwRegister = mmioRegistersMfx->generalPurposeRegister4HiOffset;
185             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
186 
187             mhw::mi::MHW_MI_ALU_PARAMS miAluParams[4] = {};
188             miAluParams[0].AluOpcode         = MHW_MI_ALU_LOAD;
189             miAluParams[0].Operand1          = MHW_MI_ALU_SRCA;
190             miAluParams[0].Operand2          = MHW_MI_ALU_GPREG0;
191             // load     srcB, reg4
192             miAluParams[1].AluOpcode = MHW_MI_ALU_LOAD;
193             miAluParams[1].Operand1  = MHW_MI_ALU_SRCB;
194             miAluParams[1].Operand2  = MHW_MI_ALU_GPREG4;
195             // add      srcA, srcB
196             miAluParams[2].AluOpcode = predicationNotEqualZero ? MHW_MI_ALU_ADD : MHW_MI_ALU_OR;
197             miAluParams[2].Operand1  = MHW_MI_ALU_SRCB;
198             miAluParams[2].Operand2  = MHW_MI_ALU_GPREG4;
199             // store      reg0, ZF
200             miAluParams[3].AluOpcode = MHW_MI_ALU_STORE;
201             miAluParams[3].Operand1  = MHW_MI_ALU_GPREG0;
202             miAluParams[3].Operand2  = predicationNotEqualZero ? MHW_MI_ALU_ZF : MHW_MI_ALU_ACCU;
203 
204             auto &miMathParams = m_miItf->MHW_GETPAR_F(MI_MATH)();
205             miMathParams                = {};
206             miMathParams.pAluPayload = miAluParams;
207             miMathParams.dwNumAluParams = 4;
208             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_MATH)(cmdBuffer));
209 
210             // if MHW_MI_ALU_ZF, the zero flag will be 0xFFFFFFFF, else zero flag will be 0x0.
211             // if MHW_MI_ALU_ACCU, the OR result directly copied
212             auto &miStoreRegMemParams           = m_miItf->MHW_GETPAR_F(MI_STORE_REGISTER_MEM)();
213             miStoreRegMemParams                 = {};
214             miStoreRegMemParams.presStoreBuffer = basicFeature->m_predicationBuffer;
215             miStoreRegMemParams.dwOffset        = 0;
216             miStoreRegMemParams.dwRegister      = mmioRegistersMfx->generalPurposeRegister0LoOffset;
217             ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_STORE_REGISTER_MEM)(cmdBuffer));
218 
219             ENCODE_CHK_NULL_RETURN(basicFeature->m_tempPredicationBuffer);
220             *basicFeature->m_tempPredicationBuffer = basicFeature->m_predicationBuffer;
221 
222             return MOS_STATUS_SUCCESS;
223         };
224 
225         ENCODE_CHK_STATUS_RETURN(PreparePredicationBuf(basicFeature->m_predicationNotEqualZero));
226 
227         auto &miConditionalBatchBufferEndParams               = m_miItf->MHW_GETPAR_F(MI_CONDITIONAL_BATCH_BUFFER_END)();
228         miConditionalBatchBufferEndParams                     = {};
229         miConditionalBatchBufferEndParams.dwOffset            = 0;
230         miConditionalBatchBufferEndParams.dwValue             = 0;
231         miConditionalBatchBufferEndParams.bDisableCompareMask = true;
232         miConditionalBatchBufferEndParams.presSemaphoreBuffer = basicFeature->m_predicationBuffer;
233         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_CONDITIONAL_BATCH_BUFFER_END)(cmdBuffer));
234 
235         return MOS_STATUS_SUCCESS;
236     }
237 
238 #if USE_CODECHAL_DEBUG_TOOL
ModifyEncodedFrameSizeWithFakeHeaderSize(PMOS_COMMAND_BUFFER cmdBuffer,uint32_t fakeHeaderSizeInByte,PMOS_RESOURCE resBrcUpdateCurbe,uint32_t targetSizePos,PMOS_RESOURCE resPakStat,uint32_t slcHrdSizePos)239     MOS_STATUS PacketUtilities::ModifyEncodedFrameSizeWithFakeHeaderSize(
240         PMOS_COMMAND_BUFFER     cmdBuffer,
241         uint32_t                fakeHeaderSizeInByte,
242         PMOS_RESOURCE           resBrcUpdateCurbe,
243         uint32_t                targetSizePos,
244         PMOS_RESOURCE           resPakStat,
245         uint32_t                slcHrdSizePos)
246     {
247         ENCODE_FUNC_CALL();
248 
249         ENCODE_CHK_NULL_RETURN(m_featureManager);
250         EncodeBasicFeature* basicFeature = dynamic_cast<EncodeBasicFeature*>(m_featureManager->GetFeature(FeatureIDs::basicFeature));
251         ENCODE_CHK_NULL_RETURN(basicFeature);
252 
253         //calculate slice headers size
254         PCODEC_ENCODER_SLCDATA slcData = basicFeature->m_slcData;
255         ENCODE_CHK_NULL_RETURN(slcData);
256         uint32_t totalSliceHeaderSize = 0;
257         for (uint32_t slcCount = 0; slcCount < basicFeature->m_numSlices; slcCount++)
258         {
259             totalSliceHeaderSize += (slcData->BitSize + 7) >> 3;
260             slcData++;
261         }
262 
263         uint32_t firstHdrSz = 0;
264         for (uint32_t i = 0; i < basicFeature->m_NumNalUnits; i++)
265         {
266             firstHdrSz += basicFeature->m_nalUnitParams[i]->uiSize;
267         }
268 
269         totalSliceHeaderSize += firstHdrSz;
270 
271         ENCODE_CHK_STATUS_RETURN(AddBufferWithIMMValue(
272             cmdBuffer,
273             resBrcUpdateCurbe,
274             targetSizePos,
275             fakeHeaderSizeInByte - totalSliceHeaderSize,
276             true));
277 
278         ENCODE_CHK_STATUS_RETURN(AddBufferWithIMMValue(
279             cmdBuffer,
280             resPakStat,
281             slcHrdSizePos,
282             fakeHeaderSizeInByte * 8,
283             true));
284 
285         return MOS_STATUS_SUCCESS;
286     }
287 
ModifyEncodedFrameSizeWithFakeHeaderSizeAVC(PMOS_COMMAND_BUFFER cmdBuffer,uint32_t fakeHeaderSizeInByte,PMOS_RESOURCE * resBrcUpdateCurbe,uint32_t targetSizePos,PMOS_RESOURCE resPakStat,uint32_t slcHrdSizePos)288     MOS_STATUS PacketUtilities::ModifyEncodedFrameSizeWithFakeHeaderSizeAVC(
289         PMOS_COMMAND_BUFFER cmdBuffer,
290         uint32_t            fakeHeaderSizeInByte,
291         PMOS_RESOURCE       *resBrcUpdateCurbe,
292         uint32_t            targetSizePos,
293         PMOS_RESOURCE       resPakStat,
294         uint32_t            slcHrdSizePos)
295     {
296         ENCODE_FUNC_CALL();
297 
298         ENCODE_CHK_NULL_RETURN(m_featureManager);
299         EncodeBasicFeature *basicFeature = dynamic_cast<EncodeBasicFeature *>(m_featureManager->GetFeature(FeatureIDs::basicFeature));
300         ENCODE_CHK_NULL_RETURN(basicFeature);
301 
302         //calculate all frame headers size, including 1st slice header
303         uint32_t totalHeaderSize = uint32_t(basicFeature->m_bsBuffer.pCurrent - basicFeature->m_bsBuffer.pBase);
304 
305         // change encoded frame size for next frame and next pass
306         for (int i = 0; i < 2; i++)
307         {
308             if (resBrcUpdateCurbe[i] == nullptr)
309                 continue;
310             ENCODE_CHK_STATUS_RETURN(AddBufferWithIMMValue(
311                 cmdBuffer,
312                 resBrcUpdateCurbe[i],
313                 sizeof(uint32_t) * 5,
314                 fakeHeaderSizeInByte - totalHeaderSize,
315                 true));
316         }
317 
318         // change headers size (U16)
319         ENCODE_CHK_STATUS_RETURN(SetBufferWithIMMValueU16(
320             cmdBuffer,
321             resPakStat,
322             0,
323             fakeHeaderSizeInByte * 8,
324             0));  // second or first word in dword
325 
326         return MOS_STATUS_SUCCESS;
327     }
328 
AddBufferWithIMMValue(PMOS_COMMAND_BUFFER cmdBuffer,PMOS_RESOURCE presStoreBuffer,uint32_t offset,uint32_t value,bool bAdd)329     MOS_STATUS PacketUtilities::AddBufferWithIMMValue(
330         PMOS_COMMAND_BUFFER     cmdBuffer,
331         PMOS_RESOURCE           presStoreBuffer,
332         uint32_t                offset,
333         uint32_t                value,
334         bool                    bAdd)
335     {
336         MHW_MI_STORE_REGISTER_MEM_PARAMS    StoreRegParams;
337         MHW_MI_STORE_DATA_PARAMS            StoreDataParams;
338         MHW_MI_LOAD_REGISTER_REG_PARAMS     LoadRegRegParams;
339         MOS_STATUS                          eStatus = MOS_STATUS_SUCCESS;
340 
341         ENCODE_FUNC_CALL();
342 
343         ENCODE_CHK_NULL_RETURN(m_hwInterface);
344 
345         if (m_vdboxIndex > m_hwInterface->GetMaxVdboxIndex())
346         {
347             ENCODE_ASSERTMESSAGE("ERROR - vdbox index exceed the maximum");
348             eStatus = MOS_STATUS_INVALID_PARAMETER;
349             return eStatus;
350         }
351 
352         auto pMmioRegisters = m_hwInterface->GetVdencInterfaceNext()->GetMmioRegisters(m_vdboxIndex);
353 
354         auto &parFlush = m_miItf->MHW_GETPAR_F(MI_FLUSH_DW)();
355         parFlush       = {};
356         m_miItf->MHW_ADDCMD_F(MI_FLUSH_DW)(cmdBuffer);
357 
358         MOS_ZeroMemory(&LoadRegRegParams, sizeof(LoadRegRegParams));
359 
360         auto &registerMemParams           = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_MEM)();
361         registerMemParams                 = {};
362         registerMemParams.presStoreBuffer = presStoreBuffer;
363         registerMemParams.dwOffset        = offset;
364         registerMemParams.dwRegister      = pMmioRegisters->generalPurposeRegister0LoOffset;
365         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_MEM)(cmdBuffer));
366 
367         auto &loadRegImmParams      = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_IMM)();
368         loadRegImmParams            = {};
369         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister0HiOffset;
370         loadRegImmParams.dwData     = 0;
371         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
372 
373         loadRegImmParams            = {};
374         loadRegImmParams.dwData     = value;
375         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4LoOffset;
376         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
377 
378         loadRegImmParams            = {};
379         loadRegImmParams.dwData     = 0;
380         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4HiOffset;
381         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
382 
383         mhw::mi::MHW_MI_ALU_PARAMS aluParams[4] = {0};
384         int                        aluCount     = 0;
385 
386         // load     srcA, reg0
387         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
388         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCA;
389         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG0;
390         ++aluCount;
391         // load     srcB, reg4
392         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
393         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCB;
394         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG4;
395         ++aluCount;
396         if (bAdd)
397         {
398             // add      srcA, srcB
399             aluParams[aluCount].AluOpcode = MHW_MI_ALU_ADD;
400         }
401         else
402         {
403             // sub      srcA, srcB
404             aluParams[aluCount].AluOpcode = MHW_MI_ALU_SUB;
405         }
406         ++aluCount;
407         // store      reg0, ACCU
408         aluParams[aluCount].AluOpcode = MHW_MI_ALU_STORE;
409         aluParams[aluCount].Operand1  = MHW_MI_ALU_GPREG0;
410         aluParams[aluCount].Operand2  = MHW_MI_ALU_ACCU;
411         ++aluCount;
412 
413         auto &miMathParams          = m_miItf->MHW_GETPAR_F(MI_MATH)();
414         miMathParams                = {};
415         miMathParams.dwNumAluParams = aluCount;
416         miMathParams.pAluPayload    = aluParams;
417         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_MATH)(cmdBuffer));
418 
419         // update the value
420         auto &miStoreRegMemParams           = m_miItf->MHW_GETPAR_F(MI_STORE_REGISTER_MEM)();
421         miStoreRegMemParams                 = {};
422         miStoreRegMemParams.presStoreBuffer = presStoreBuffer;
423         miStoreRegMemParams.dwOffset        = offset;
424         miStoreRegMemParams.dwRegister      = pMmioRegisters->generalPurposeRegister0LoOffset;
425         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_STORE_REGISTER_MEM)(cmdBuffer));
426         return eStatus;
427     }
428 
SetBufferWithIMMValueU16(PMOS_COMMAND_BUFFER cmdBuffer,PMOS_RESOURCE presStoreBuffer,uint32_t offset,uint32_t value,bool bSecond)429     MOS_STATUS PacketUtilities::SetBufferWithIMMValueU16(
430         PMOS_COMMAND_BUFFER cmdBuffer,
431         PMOS_RESOURCE       presStoreBuffer,
432         uint32_t            offset,
433         uint32_t            value,
434         bool                bSecond)
435     {
436         MHW_MI_STORE_REGISTER_MEM_PARAMS StoreRegParams;
437         MHW_MI_LOAD_REGISTER_IMM_PARAMS  LoadRegisterImmParams;
438         MHW_MI_MATH_PARAMS               MiMathParams;
439         MHW_MI_ALU_PARAMS                MiAluParams[4];  // is used twice
440         MOS_STATUS                       eStatus = MOS_STATUS_SUCCESS;
441 
442         ENCODE_FUNC_CALL();
443 
444         ENCODE_CHK_NULL_RETURN(m_hwInterface);
445 
446         if (m_vdboxIndex > m_hwInterface->GetMaxVdboxIndex())
447         {
448             ENCODE_ASSERTMESSAGE("ERROR - vdbox index exceed the maximum");
449             eStatus = MOS_STATUS_INVALID_PARAMETER;
450             return eStatus;
451         }
452 
453         auto pMmioRegisters = m_hwInterface->GetVdencInterfaceNext()->GetMmioRegisters(m_vdboxIndex);
454 
455         auto &parFlush = m_miItf->MHW_GETPAR_F(MI_FLUSH_DW)();
456         parFlush       = {};
457         m_miItf->MHW_ADDCMD_F(MI_FLUSH_DW)(cmdBuffer);
458 
459         auto &registerMemParams           = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_MEM)();
460         registerMemParams                 = {};
461         registerMemParams.presStoreBuffer = presStoreBuffer;
462         registerMemParams.dwOffset        = offset;
463         registerMemParams.dwRegister      = pMmioRegisters->generalPurposeRegister0LoOffset;
464         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_MEM)(cmdBuffer));
465 
466         auto &loadRegImmParams      = m_miItf->MHW_GETPAR_F(MI_LOAD_REGISTER_IMM)();
467         loadRegImmParams            = {};
468         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister0HiOffset;
469         loadRegImmParams.dwData     = 0;
470         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
471 
472         uint32_t mask = bSecond ? 0xffff : 0xffff0000;
473         value         = bSecond ? value << 16 : value;
474 
475         loadRegImmParams            = {};
476         loadRegImmParams.dwData     = mask;
477         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4LoOffset;
478         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
479 
480         loadRegImmParams            = {};
481         loadRegImmParams.dwData     = 0;
482         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4HiOffset;
483         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
484 
485         mhw::mi::MHW_MI_ALU_PARAMS aluParams[4] = {0};
486         int                        aluCount     = 0;
487 
488         // load    srcA, reg0
489         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
490         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCA;
491         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG0;
492         aluCount++;
493         // load    srcB, reg4
494         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
495         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCB;
496         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG4;
497         aluCount++;
498         // and     srcA, srcB
499         aluParams[aluCount].AluOpcode = MHW_MI_ALU_AND;
500         aluCount++;
501         // store   reg0, ACCU
502         aluParams[aluCount].AluOpcode = MHW_MI_ALU_STORE;
503         aluParams[aluCount].Operand1  = MHW_MI_ALU_GPREG0;
504         aluParams[aluCount].Operand2  = MHW_MI_ALU_ACCU;
505         aluCount++;
506 
507         auto &miMathParams          = m_miItf->MHW_GETPAR_F(MI_MATH)();
508         miMathParams                = {};
509         miMathParams.dwNumAluParams = aluCount;
510         miMathParams.pAluPayload    = aluParams;
511         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_MATH)(cmdBuffer));
512 
513         loadRegImmParams            = {};
514         loadRegImmParams.dwData     = value;
515         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4LoOffset;
516         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
517 
518         loadRegImmParams            = {};
519         loadRegImmParams.dwData     = 0;
520         loadRegImmParams.dwRegister = pMmioRegisters->generalPurposeRegister4HiOffset;
521         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_LOAD_REGISTER_IMM)(cmdBuffer));
522 
523         aluCount = 0;
524         // load    srcA, reg0
525         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
526         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCA;
527         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG0;
528         aluCount++;
529         // load    srcB, reg4
530         aluParams[aluCount].AluOpcode = MHW_MI_ALU_LOAD;
531         aluParams[aluCount].Operand1  = MHW_MI_ALU_SRCB;
532         aluParams[aluCount].Operand2  = MHW_MI_ALU_GPREG4;
533         aluCount++;
534 
535         // or      srcA, srcB
536         aluParams[aluCount].AluOpcode = MHW_MI_ALU_OR;
537         aluCount++;
538 
539         // store   reg0, ACCU
540         aluParams[aluCount].AluOpcode = MHW_MI_ALU_STORE;
541         aluParams[aluCount].Operand1  = MHW_MI_ALU_GPREG0;
542         aluParams[aluCount].Operand2  = MHW_MI_ALU_ACCU;
543         aluCount++;
544 
545         miMathParams                = {};
546         miMathParams                = {};
547         miMathParams.dwNumAluParams = aluCount;
548         miMathParams.pAluPayload    = aluParams;
549         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_MATH)(cmdBuffer));
550 
551         // update the value
552         auto &miStoreRegMemParams           = m_miItf->MHW_GETPAR_F(MI_STORE_REGISTER_MEM)();
553         miStoreRegMemParams                 = {};
554         miStoreRegMemParams.presStoreBuffer = presStoreBuffer;
555         miStoreRegMemParams.dwOffset        = offset;
556         miStoreRegMemParams.dwRegister      = pMmioRegisters->generalPurposeRegister0LoOffset;
557         ENCODE_CHK_STATUS_RETURN(m_miItf->MHW_ADDCMD_F(MI_STORE_REGISTER_MEM)(cmdBuffer));
558 
559         return eStatus;
560     }
561 
GetFakeHeaderSettings(uint32_t & fakeHeaderSizeInByte,bool isIframe)562     bool PacketUtilities::GetFakeHeaderSettings(uint32_t &fakeHeaderSizeInByte, bool isIframe)
563     {
564         ENCODE_FUNC_CALL();
565 
566         fakeHeaderSizeInByte = isIframe ? m_fakeIFrameHrdSize : m_fakePBFrameHrdSize;
567 
568         return m_enableFakeHrdSize;
569     }
570 #endif
571 }
572