1 /*
2 * Copyright (c) 2020-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 vp_di_filter.cpp
24 //! \brief Defines the common interface for Adaptive Contrast Enhancement
25 //! this file is for the base interface which is shared by all Ace in driver.
26 //!
27 #include "vp_di_filter.h"
28 #include "vp_vebox_cmd_packet_base.h"
29 #include "hw_filter.h"
30 #include "sw_filter_pipe.h"
31 #include "vp_render_cmd_packet.h"
32
33 using namespace vp;
34
VpDiFilter(PVP_MHWINTERFACE vpMhwInterface)35 VpDiFilter::VpDiFilter(PVP_MHWINTERFACE vpMhwInterface) :
36 VpFilter(vpMhwInterface)
37 {
38
39 }
40
Init()41 MOS_STATUS VpDiFilter::Init()
42 {
43 VP_FUNC_CALL();
44
45 return MOS_STATUS_SUCCESS;
46 }
47
Prepare()48 MOS_STATUS VpDiFilter::Prepare()
49 {
50 VP_FUNC_CALL();
51
52 return MOS_STATUS_SUCCESS;
53 }
54
Destroy()55 MOS_STATUS VpDiFilter::Destroy()
56 {
57 VP_FUNC_CALL();
58
59 if (m_pVeboxDiParams)
60 {
61 MOS_FreeMemAndSetNull(m_pVeboxDiParams);
62 }
63
64 return MOS_STATUS_SUCCESS;
65 }
66
SetExecuteEngineCaps(FeatureParamDeinterlace & diParams,VP_EXECUTE_CAPS vpExecuteCaps)67 MOS_STATUS VpDiFilter::SetExecuteEngineCaps(
68 FeatureParamDeinterlace &diParams,
69 VP_EXECUTE_CAPS vpExecuteCaps)
70 {
71 VP_FUNC_CALL();
72
73 m_diParams = diParams;
74 m_executeCaps = vpExecuteCaps;
75
76 return MOS_STATUS_SUCCESS;
77 }
78
CalculateEngineParams()79 MOS_STATUS VpDiFilter::CalculateEngineParams()
80 {
81 VP_FUNC_CALL();
82 if (m_executeCaps.bVebox)
83 {
84 // create a filter Param buffer
85 if (!m_pVeboxDiParams)
86 {
87 m_pVeboxDiParams = (PVEBOX_DI_PARAMS)MOS_AllocAndZeroMemory(sizeof(VEBOX_DI_PARAMS));
88
89 if (m_pVeboxDiParams == nullptr)
90 {
91 VP_PUBLIC_ASSERTMESSAGE("Vebox DI Pamas buffer allocate failed, return nullpointer");
92 return MOS_STATUS_NO_SPACE;
93 }
94 }
95 else
96 {
97 MOS_ZeroMemory(m_pVeboxDiParams, sizeof(VEBOX_DI_PARAMS));
98 }
99
100 m_pVeboxDiParams->bDiEnabled = true;
101 m_pVeboxDiParams->sampleTypeInput = m_diParams.sampleTypeInput;
102 m_pVeboxDiParams->bHDContent = m_diParams.bHDContent;
103 m_pVeboxDiParams->bEnableQueryVariance = m_diParams.bQueryVarianceEnable;
104 if (m_diParams.diParams)
105 {
106 m_pVeboxDiParams->b60fpsDi = !m_diParams.diParams->bSingleField;
107 m_pVeboxDiParams->diMode = m_diParams.diParams->DIMode;
108 m_pVeboxDiParams->enableFMD = m_diParams.diParams->bEnableFMD;
109 m_pVeboxDiParams->bSCDEnabled = m_diParams.diParams->bSCDEnable;
110 }
111 }
112 else
113 {
114 VP_PUBLIC_ASSERTMESSAGE("Wrong engine caps! Vebox should be used for DI");
115 return MOS_STATUS_INVALID_PARAMETER;
116 }
117
118 return MOS_STATUS_SUCCESS;
119 }
120
121
122 /****************************************************************************************************/
123 /* HwFilter DI Parameter */
124 /****************************************************************************************************/
Create(HW_FILTER_DI_PARAM & param,FeatureType featureType)125 HwFilterParameter *HwFilterDiParameter::Create(HW_FILTER_DI_PARAM ¶m, FeatureType featureType)
126 {
127 VP_FUNC_CALL();
128
129 HwFilterDiParameter *p = MOS_New(HwFilterDiParameter, featureType);
130 if (p)
131 {
132 if (MOS_FAILED(p->Initialize(param)))
133 {
134 MOS_Delete(p);
135 return nullptr;
136 }
137 }
138 return p;
139 }
140
HwFilterDiParameter(FeatureType featureType)141 HwFilterDiParameter::HwFilterDiParameter(FeatureType featureType) : HwFilterParameter(featureType)
142 {
143 }
144
~HwFilterDiParameter()145 HwFilterDiParameter::~HwFilterDiParameter()
146 {
147 }
148
ConfigParams(HwFilter & hwFilter)149 MOS_STATUS HwFilterDiParameter::ConfigParams(HwFilter &hwFilter)
150 {
151 VP_FUNC_CALL();
152
153 return hwFilter.ConfigParam(m_Params);
154 }
155
Initialize(HW_FILTER_DI_PARAM & param)156 MOS_STATUS HwFilterDiParameter::Initialize(HW_FILTER_DI_PARAM ¶m)
157 {
158 VP_FUNC_CALL();
159
160 m_Params = param;
161 return MOS_STATUS_SUCCESS;
162 }
163
164 /****************************************************************************************************/
165 /* Packet Vebox DI Parameter */
166 /****************************************************************************************************/
Create(HW_FILTER_DI_PARAM & param)167 VpPacketParameter *VpDiParameter::Create(HW_FILTER_DI_PARAM ¶m)
168 {
169 VP_FUNC_CALL();
170
171 if (nullptr == param.pPacketParamFactory)
172 {
173 return nullptr;
174 }
175 VpDiParameter *p = dynamic_cast<VpDiParameter *>(param.pPacketParamFactory->GetPacketParameter(param.pHwInterface));
176 if (p)
177 {
178 if (MOS_FAILED(p->Initialize(param)))
179 {
180 VpPacketParameter *pParam = p;
181 param.pPacketParamFactory->ReturnPacketParameter(pParam);
182 return nullptr;
183 }
184 }
185 return p;
186 }
187
VpDiParameter(PVP_MHWINTERFACE pHwInterface,PacketParamFactoryBase * packetParamFactory)188 VpDiParameter::VpDiParameter(PVP_MHWINTERFACE pHwInterface, PacketParamFactoryBase *packetParamFactory) :
189 VpPacketParameter(packetParamFactory), m_diFilter(pHwInterface)
190 {
191 }
~VpDiParameter()192 VpDiParameter::~VpDiParameter() {}
193
SetPacketParam(VpCmdPacket * pPacket)194 bool VpDiParameter::SetPacketParam(VpCmdPacket *pPacket)
195 {
196 VP_FUNC_CALL();
197
198 VEBOX_DI_PARAMS *params = m_diFilter.GetVeboxParams();
199 if (nullptr == params)
200 {
201 VP_PUBLIC_ASSERTMESSAGE("Failed to get vebox di params");
202 return false;
203 }
204
205 VpVeboxCmdPacketBase *packet = dynamic_cast<VpVeboxCmdPacketBase *>(pPacket);
206 if (packet)
207 {
208 return MOS_SUCCEEDED(packet->SetDiParams(params));
209 }
210
211 VP_PUBLIC_ASSERTMESSAGE("Invalid packet for vebox di");
212 return false;
213 }
214
Initialize(HW_FILTER_DI_PARAM & params)215 MOS_STATUS VpDiParameter::Initialize(HW_FILTER_DI_PARAM ¶ms)
216 {
217 VP_FUNC_CALL();
218
219 VP_PUBLIC_CHK_STATUS_RETURN(m_diFilter.Init());
220 VP_PUBLIC_CHK_STATUS_RETURN(m_diFilter.SetExecuteEngineCaps(params.diParams, params.vpExecuteCaps));
221 VP_PUBLIC_CHK_STATUS_RETURN(m_diFilter.CalculateEngineParams());
222 return MOS_STATUS_SUCCESS;
223 }
224
225 /****************************************************************************************************/
226 /* Policy Vebox DI Handler */
227 /****************************************************************************************************/
PolicyDiHandler(VP_HW_CAPS & hwCaps)228 PolicyDiHandler::PolicyDiHandler(VP_HW_CAPS &hwCaps) : PolicyFeatureHandler(hwCaps)
229 {
230 m_Type = FeatureTypeDi;
231 }
~PolicyDiHandler()232 PolicyDiHandler::~PolicyDiHandler()
233 {
234 }
235
IsFeatureEnabled(VP_EXECUTE_CAPS vpExecuteCaps)236 bool PolicyDiHandler::IsFeatureEnabled(VP_EXECUTE_CAPS vpExecuteCaps)
237 {
238 VP_FUNC_CALL();
239
240 return vpExecuteCaps.bDI && (vpExecuteCaps.bVebox || vpExecuteCaps.bDIFmdKernel);
241 }
242
CreateHwFilterParam(VP_EXECUTE_CAPS vpExecuteCaps,SwFilterPipe & swFilterPipe,PVP_MHWINTERFACE pHwInterface)243 HwFilterParameter* PolicyDiHandler::CreateHwFilterParam(VP_EXECUTE_CAPS vpExecuteCaps, SwFilterPipe& swFilterPipe, PVP_MHWINTERFACE pHwInterface)
244 {
245 VP_FUNC_CALL();
246
247 SwFilterDeinterlace *swFilter = nullptr;
248
249 if (IsFeatureEnabled(vpExecuteCaps))
250 {
251 if (SwFilterPipeType1To1 != swFilterPipe.GetSwFilterPipeType())
252 {
253 VP_PUBLIC_ASSERTMESSAGE("Invalid parameter! Sfc only support 1To1 swFilterPipe!");
254 return nullptr;
255 }
256
257 swFilter = dynamic_cast<SwFilterDeinterlace *>(swFilterPipe.GetSwFilter(true, 0, FeatureTypeDiOnVebox));
258
259 if (nullptr == swFilter)
260 {
261 VP_PUBLIC_ASSERTMESSAGE("Invalid parameter! Feature enabled in vpExecuteCaps but no swFilter exists!");
262 return nullptr;
263 }
264
265 FeatureParamDeinterlace ¶m = swFilter->GetSwFilterParams();
266
267 HW_FILTER_DI_PARAM diParam = {};
268 diParam.type = m_Type;
269 diParam.pHwInterface = pHwInterface;
270 diParam.vpExecuteCaps = vpExecuteCaps;
271 diParam.pPacketParamFactory = &m_PacketParamFactory;
272 diParam.diParams = param;
273 diParam.pfnCreatePacketParam = PolicyDiHandler::CreatePacketParam;
274
275 HwFilterParameter *pHwFilterParam = GetHwFeatureParameterFromPool();
276
277 if (pHwFilterParam)
278 {
279 if (MOS_FAILED(((HwFilterDiParameter*)pHwFilterParam)->Initialize(diParam)))
280 {
281 ReleaseHwFeatureParameter(pHwFilterParam);
282 }
283 }
284 else
285 {
286 pHwFilterParam = HwFilterDiParameter::Create(diParam, m_Type);
287 }
288
289 return pHwFilterParam;
290 }
291 else
292 {
293 return nullptr;
294 }
295 }