1 /*
2 * Copyright (c) 2014-2021, 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 mhw_utilities.c
24 //! \brief This modules implements utilities which are shared by both the HW interface and the state heap interface.
25 //!
26 #include "mhw_utilities.h"
27 #include "mhw_render_legacy.h"
28 #include "mhw_state_heap.h"
29 #include "hal_oca_interface.h"
30 #include "mos_interface.h"
31 #include "mhw_mi_itf.h"
32
33 //!
34 //! \brief Inserts the generic prologue command for a command buffer
35 //! \details Client facing function to add the generic prologue commands:
36 //! - the command buffer header (if necessary)
37 //! - flushes for the read/write caches (MI_FLUSH_DW or PIPE_CONTROL)
38 //! - CP prologue if necessary
39 //! \param PMOS_COMMAND_BUFFER pCmdBuffer
40 //! [in] Command buffer
41 //! \param PMHW_GENERIC_PROLOG_PARAMS pParams
42 //! [in] Parameters necessary to add the generic prologue commands
43 //! \return MOS_STATUS
44 //! MOS_STATUS_SUCCESS if success, else fail reason
45 //!
Mhw_SendGenericPrologCmd(PMOS_COMMAND_BUFFER pCmdBuffer,PMHW_GENERIC_PROLOG_PARAMS pParams,MHW_MI_MMIOREGISTERS * pMmioReg)46 MOS_STATUS Mhw_SendGenericPrologCmd(
47 PMOS_COMMAND_BUFFER pCmdBuffer,
48 PMHW_GENERIC_PROLOG_PARAMS pParams,
49 MHW_MI_MMIOREGISTERS *pMmioReg)
50 {
51 PMOS_INTERFACE pOsInterface;
52 MhwMiInterface *pMiInterface;
53 MEDIA_FEATURE_TABLE *pSkuTable;
54 MEDIA_WA_TABLE *pWaTable;
55 MOS_GPU_CONTEXT GpuContext;
56 MHW_PIPE_CONTROL_PARAMS PipeControlParams;
57 MHW_MI_FLUSH_DW_PARAMS FlushDwParams;
58 bool bRcsEngineUsed = false;
59 MOS_STATUS eStatus = MOS_STATUS_SUCCESS;
60
61 MHW_FUNCTION_ENTER;
62
63 MHW_CHK_NULL(pCmdBuffer);
64 MHW_CHK_NULL(pParams);
65 MHW_CHK_NULL(pParams->pOsInterface);
66
67 pOsInterface = pParams->pOsInterface;
68
69 MHW_CHK_NULL(pParams->pvMiInterface);
70 pMiInterface = (MhwMiInterface *)pParams->pvMiInterface;
71 MHW_CHK_NULL(pMiInterface);
72 pSkuTable = pOsInterface->pfnGetSkuTable(pOsInterface);
73 MHW_CHK_NULL(pSkuTable);
74 pWaTable = pOsInterface->pfnGetWaTable(pOsInterface);
75 MHW_CHK_NULL(pWaTable);
76
77 GpuContext = pOsInterface->pfnGetGpuContext(pOsInterface);
78
79 if ( pOsInterface->Component != COMPONENT_CM )
80 {
81 if ( GpuContext == MOS_GPU_CONTEXT_RENDER ||
82 GpuContext == MOS_GPU_CONTEXT_RENDER2 ||
83 GpuContext == MOS_GPU_CONTEXT_RENDER3 ||
84 GpuContext == MOS_GPU_CONTEXT_RENDER4 ||
85 GpuContext == MOS_GPU_CONTEXT_VIDEO ||
86 GpuContext == MOS_GPU_CONTEXT_VIDEO2 ||
87 GpuContext == MOS_GPU_CONTEXT_VIDEO3 ||
88 GpuContext == MOS_GPU_CONTEXT_VIDEO4 ||
89 GpuContext == MOS_GPU_CONTEXT_VDBOX2_VIDEO ||
90 GpuContext == MOS_GPU_CONTEXT_VDBOX2_VIDEO2 ||
91 GpuContext == MOS_GPU_CONTEXT_VDBOX2_VIDEO3 ||
92 GpuContext == MOS_GPU_CONTEXT_VEBOX ||
93 GpuContext == MOS_GPU_CONTEXT_VIDEO5 ||
94 GpuContext == MOS_GPU_CONTEXT_VIDEO6 ||
95 GpuContext == MOS_GPU_CONTEXT_VIDEO7 )
96 {
97 MHW_CHK_STATUS(pMiInterface->AddWatchdogTimerStartCmd(pCmdBuffer));
98 }
99 }
100
101 bRcsEngineUsed = MOS_RCS_ENGINE_USED(GpuContext);
102
103 if (bRcsEngineUsed)
104 {
105 MOS_ZeroMemory(&PipeControlParams, sizeof(PipeControlParams));
106
107 PipeControlParams.dwFlushMode = MHW_FLUSH_WRITE_CACHE;
108 MHW_CHK_STATUS(pMiInterface->AddPipeControl(
109 pCmdBuffer,
110 nullptr,
111 &PipeControlParams));
112
113 PipeControlParams.dwFlushMode = MHW_FLUSH_READ_CACHE;
114 PipeControlParams.presDest = pParams->presStoreData;
115 PipeControlParams.dwPostSyncOp = MHW_FLUSH_WRITE_IMMEDIATE_DATA;
116 PipeControlParams.dwResourceOffset = pParams->dwStoreDataOffset;
117 PipeControlParams.dwDataDW1 = pParams->dwStoreDataValue;
118 MHW_CHK_STATUS(pMiInterface->AddPipeControl(
119 pCmdBuffer,
120 nullptr,
121 &PipeControlParams));
122
123 if(pCmdBuffer->Attributes.bUmdSSEUEnable)
124 {
125 MHW_MI_LOAD_REGISTER_IMM_PARAMS MiLoadRegImmParams;
126 MHW_RENDER_PWR_CLK_STATE_PARAMS params;
127
128 MOS_ZeroMemory(¶ms, sizeof(params));
129 params.PowerClkStateEn = true;
130 params.SCountEn = true;
131 params.SSCountEn = true;
132 params.SliceCount = pCmdBuffer->Attributes.dwNumRequestedEUSlices;
133 params.SubSliceCount = pCmdBuffer->Attributes.dwNumRequestedSubSlices;
134 params.EUmax = pCmdBuffer->Attributes.dwNumRequestedEUs;
135 params.EUmin = pCmdBuffer->Attributes.dwNumRequestedEUs;
136
137 MOS_ZeroMemory(&MiLoadRegImmParams, sizeof(MiLoadRegImmParams));
138 MiLoadRegImmParams.dwRegister = MHW__PWR_CLK_STATE_REG;
139 MiLoadRegImmParams.dwData = params.Data;
140 MHW_CHK_STATUS(pMiInterface->AddMiLoadRegisterImmCmd(
141 pCmdBuffer,
142 &MiLoadRegImmParams));
143 }
144 }
145 else
146 {
147 // Send MI_FLUSH with protection bit off, which will FORCE exit protected mode for MFX
148 MOS_ZeroMemory(&FlushDwParams, sizeof(FlushDwParams));
149 FlushDwParams.bVideoPipelineCacheInvalidate = true;
150 FlushDwParams.pOsResource = pParams->presStoreData;
151 FlushDwParams.dwResourceOffset = pParams->dwStoreDataOffset;
152 FlushDwParams.dwDataDW1 = pParams->dwStoreDataValue;
153 MHW_CHK_STATUS(pMiInterface->AddMiFlushDwCmd(
154 pCmdBuffer,
155 &FlushDwParams));
156 }
157
158 MHW_CHK_STATUS(pMiInterface->AddProtectedProlog(pCmdBuffer));
159
160 if (pMmioReg)
161 {
162 HalOcaInterface::On1stLevelBBStart(
163 *pCmdBuffer,
164 *pOsInterface->pOsContext,
165 pOsInterface->CurrentGpuContextHandle,
166 *pMiInterface,
167 *pMmioReg);
168 }
169
170 finish:
171
172 return eStatus;
173 }
174