1 /*
2 * Copyright (c) 2021-2022, 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 //!
24 //! \file media_capstable_specific.cpp
25 //! \brief implemantation of media caps table class on specific os
26 //!
27
28 #include "media_capstable_specific.h"
29 #include "media_libva.h"
30 #include "hwinfo_linux.h"
31 #include "linux_system_info.h"
32 #include "media_libva_caps_factory.h"
33 #include "ddi_cp_caps_interface.h"
34
operator <(const ComponentInfo & lhs,const ComponentInfo & rhs)35 bool operator<(const ComponentInfo &lhs, const ComponentInfo &rhs)
36 {
37 return memcmp(&lhs, &rhs, sizeof(ComponentInfo)) < 0;
38 }
39
~MediaCapsTableSpecific()40 MediaCapsTableSpecific::~MediaCapsTableSpecific()
41 {
42 if(m_cpCaps)
43 {
44 MOS_Delete(m_cpCaps);
45 m_cpCaps = nullptr;
46 }
47 }
48
MediaCapsTableSpecific(HwDeviceInfo & deviceInfo)49 MediaCapsTableSpecific::MediaCapsTableSpecific(HwDeviceInfo &deviceInfo)
50 {
51 m_plt.ipVersion = deviceInfo.ipVersion;
52 m_plt.usRevId = deviceInfo.usRevId;
53
54 MediaCapsTable::Iterator capsIter;
55 if(GetCapsTablePlatform(m_plt, capsIter))
56 {
57 m_profileMap = const_cast<ProfileMap *>(capsIter->second.profileMap);
58 m_imgTbl = const_cast<ImgTable *>(capsIter->second.imgTbl);
59 }
60 else
61 {
62 DDI_ASSERTMESSAGE("unknown platform with usRevId=%d, ipVersion=%d\n", (int)m_plt.usRevId, (int)m_plt.ipVersion);
63 }
64 }
65
Init(DDI_MEDIA_CONTEXT * mediaCtx)66 VAStatus MediaCapsTableSpecific::Init(DDI_MEDIA_CONTEXT *mediaCtx)
67 {
68 DDI_FUNC_ENTER;
69
70 if (m_profileMap == nullptr)
71 {
72 DDI_ASSERTMESSAGE("Invalid parameter for profileMap");
73 return VA_STATUS_ERROR_INVALID_PARAMETER;
74 }
75
76 m_cpCaps = CreateDdiCpCaps();
77 DDI_CHK_NULL(m_cpCaps, "CP caps fail with null pointer", VA_STATUS_ERROR_INVALID_PARAMETER);
78
79 if (m_cpCaps->InitProfileMap(mediaCtx, m_profileMap) != VA_STATUS_SUCCESS)
80 {
81 DDI_ASSERTMESSAGE("Init CP caps failed");
82 MOS_Delete(m_cpCaps);
83 m_cpCaps = nullptr;
84 return VA_STATUS_ERROR_INVALID_PARAMETER;
85 }
86
87 for (auto profileMapIter: *m_profileMap)
88 {
89 auto profile = profileMapIter.first;
90 for(auto entrypointMapIter: *profileMapIter.second)
91 {
92 auto entrypoint = entrypointMapIter.first;
93 auto entrypointData = entrypointMapIter.second;
94 DDI_CHK_NULL(entrypointData, "Null pointer", VA_STATUS_ERROR_INVALID_PARAMETER);
95
96 auto attriblist = entrypointData->attribList;
97 DDI_CHK_NULL(attriblist, "Null pointer", VA_STATUS_ERROR_INVALID_PARAMETER);
98
99 auto componentData = entrypointData->configDataList;
100 int32_t numAttribList = attriblist->size();
101 if(componentData && componentData->size() != 0)
102 {
103 for(int i = 0; i < componentData->size(); i++)
104 {
105 auto configData = componentData->at(i);
106 m_configList.emplace_back(profile, entrypoint, const_cast<VAConfigAttrib*>(attriblist->data()), numAttribList, configData);
107 }
108 }
109 else
110 {
111 ComponentData configData = {};
112 m_configList.emplace_back(profile, entrypoint, const_cast<VAConfigAttrib*>(attriblist->data()), numAttribList, configData);
113 }
114 }
115 }
116
117 return VA_STATUS_SUCCESS;
118 }
119
QueryConfigProfiles(VAProfile * profileList,int32_t * profilesNum)120 VAStatus MediaCapsTableSpecific::QueryConfigProfiles(
121 VAProfile *profileList,
122 int32_t *profilesNum)
123 {
124 DDI_FUNC_ENTER;
125
126 DDI_CHK_NULL(profileList, "Null pointer", VA_STATUS_ERROR_INVALID_PARAMETER);
127 DDI_CHK_NULL(profilesNum, "Null pointer", VA_STATUS_ERROR_INVALID_PARAMETER);
128
129 int i = 0;
130
131 if(m_profileMap->size() <= 0)
132 {
133 return VA_STATUS_ERROR_INVALID_CONFIG;
134 }
135
136 for (auto it = m_profileMap->begin(); it!=m_profileMap->end(); ++it)
137 {
138 profileList[i++] = (VAProfile)(it->first);
139 }
140 *profilesNum = m_profileMap->size();
141 return VA_STATUS_SUCCESS;
142 }
143
QueryConfigEntrypointsMap(VAProfile profile)144 EntrypointMap* MediaCapsTableSpecific::QueryConfigEntrypointsMap(
145 VAProfile profile)
146 {
147 DDI_FUNC_ENTER;
148
149 int i = 0;
150
151 if(m_profileMap->find(profile) == m_profileMap->end())
152 {
153 return nullptr;
154 }
155
156 return const_cast<EntrypointMap*>(m_profileMap->at(profile));
157 }
158
QuerySupportedAttrib(VAProfile profile,VAEntrypoint entrypoint)159 AttribList* MediaCapsTableSpecific::QuerySupportedAttrib(
160 VAProfile profile,
161 VAEntrypoint entrypoint)
162 {
163 DDI_FUNC_ENTER;
164
165 if(m_profileMap->find(profile) == m_profileMap->end() ||
166 m_profileMap->at(profile)->find(entrypoint) == m_profileMap->at(profile)->end())
167 {
168 return nullptr;
169 }
170
171 return const_cast<AttribList*>(m_profileMap->at(profile)->at(entrypoint)->attribList);
172 }
173
GetConfigList()174 ConfigList* MediaCapsTableSpecific::GetConfigList()
175 {
176 DDI_FUNC_ENTER;
177
178 return &m_configList;
179 }
180
QueryConfigItemFromIndex(VAConfigID configId)181 ConfigLinux* MediaCapsTableSpecific::QueryConfigItemFromIndex(
182 VAConfigID configId)
183 {
184 DDI_FUNC_ENTER;
185
186 if (!IS_VALID_CONFIG_ID(configId))
187 {
188 DDI_ASSERTMESSAGE("Invalid config ID");
189 return nullptr;
190 }
191
192 if(IsDecConfigId(configId) && REMOVE_CONFIG_ID_DEC_OFFSET(configId) < m_configList.size())
193 {
194 return &m_configList[REMOVE_CONFIG_ID_DEC_OFFSET(configId)];
195 }
196 else if(IsEncConfigId(configId) && REMOVE_CONFIG_ID_ENC_OFFSET(configId) < m_configList.size())
197 {
198 return &m_configList[REMOVE_CONFIG_ID_ENC_OFFSET(configId)];
199 }
200 else if(IsVpConfigId(configId) && REMOVE_CONFIG_ID_VP_OFFSET(configId) < m_configList.size())
201 {
202 return &m_configList[REMOVE_CONFIG_ID_VP_OFFSET(configId)];
203 }
204 else if((m_cpCaps != nullptr) && (m_cpCaps->IsCpConfigId(configId)))
205 {
206 uint32_t index = m_cpCaps->GetCpConfigId(configId);
207 DDI_CHK_CONDITION((index >= m_configList.size()), "Invalid config ID", nullptr)
208
209 return &m_configList[index];
210 }
211 else
212 {
213 DDI_ASSERTMESSAGE("Invalid config ID");
214 return nullptr;
215 }
216 }
217
CreateConfig(VAProfile profile,VAEntrypoint entrypoint,VAConfigAttrib * attribList,int32_t numAttribs,VAConfigID * configId)218 VAStatus MediaCapsTableSpecific::CreateConfig(
219 VAProfile profile,
220 VAEntrypoint entrypoint,
221 VAConfigAttrib *attribList,
222 int32_t numAttribs,
223 VAConfigID *configId)
224 {
225 DDI_FUNC_ENTER;
226
227 DDI_UNUSED(attribList);
228 DDI_UNUSED(numAttribs);
229 DDI_UNUSED(configId);
230
231 VAStatus ret = VA_STATUS_ERROR_UNSUPPORTED_PROFILE;
232 for (auto configItem : m_configList)
233 {
234 // check profile, entrypoint here
235 if (configItem.profile == profile)
236 {
237 ret = VA_STATUS_ERROR_UNSUPPORTED_ENTRYPOINT;
238 if(configItem.entrypoint == entrypoint)
239 {
240 ret = VA_STATUS_SUCCESS;
241 break;
242 }
243 }
244 }
245
246 return ret;
247 }
248
IsDecConfigId(VAConfigID configId)249 bool MediaCapsTableSpecific::IsDecConfigId(VAConfigID configId)
250 {
251 VAConfigID curConfigId = REMOVE_CONFIG_ID_OFFSET(configId);
252
253 return ((curConfigId >= DDI_CODEC_GEN_CONFIG_ATTRIBUTES_DEC_BASE) &&
254 (curConfigId <= DDI_CODEC_GEN_CONFIG_ATTRIBUTES_DEC_MAX));
255 }
256
IsEncConfigId(VAConfigID configId)257 bool MediaCapsTableSpecific::IsEncConfigId(VAConfigID configId)
258 {
259 VAConfigID curConfigId = REMOVE_CONFIG_ID_OFFSET(configId);
260
261 return ((curConfigId >= DDI_CODEC_GEN_CONFIG_ATTRIBUTES_ENC_BASE) &&
262 (curConfigId <= DDI_CODEC_GEN_CONFIG_ATTRIBUTES_ENC_MAX));
263 }
264
IsVpConfigId(VAConfigID configId)265 bool MediaCapsTableSpecific::IsVpConfigId(VAConfigID configId)
266 {
267 VAConfigID curConfigId = REMOVE_CONFIG_ID_OFFSET(configId);
268
269 return ((curConfigId >= DDI_VP_GEN_CONFIG_ATTRIBUTES_BASE) &&
270 (curConfigId <= DDI_VP_GEN_CONFIG_ATTRIBUTES_MAX));
271 }
272
DestroyConfig(VAConfigID configId)273 VAStatus MediaCapsTableSpecific::DestroyConfig(VAConfigID configId)
274 {
275 uint32_t index = 0;
276 VAStatus status = VA_STATUS_SUCCESS;
277 DDI_FUNC_ENTER;
278
279 if(!IS_VALID_CONFIG_ID(configId))
280 {
281 DDI_ASSERTMESSAGE("Invalid config ID");
282 return VA_STATUS_ERROR_INVALID_CONFIG;
283 }
284
285 if(IsDecConfigId(configId))
286 {
287 index = REMOVE_CONFIG_ID_DEC_OFFSET(configId);
288 }
289 else if(IsEncConfigId(configId))
290 {
291 index = REMOVE_CONFIG_ID_ENC_OFFSET(configId);
292 }
293 else if(IsVpConfigId(configId))
294 {
295 index = REMOVE_CONFIG_ID_VP_OFFSET(configId);
296 }
297 else if( (m_cpCaps != nullptr) && (m_cpCaps->IsCpConfigId(configId)) )
298 {
299 index = m_cpCaps->GetCpConfigId(configId);
300 }
301 else
302 {
303 DDI_ASSERTMESSAGE("Invalid config ID");
304 return VA_STATUS_ERROR_INVALID_CONFIG;
305 }
306
307 if(index < m_configList.size())
308 {
309 DDI_NORMALMESSAGE("Succeed Destroy config ID");
310 status = VA_STATUS_SUCCESS;
311 }
312 else
313 {
314 DDI_NORMALMESSAGE("Invalid config ID");
315 status = VA_STATUS_ERROR_INVALID_CONFIG;
316 }
317
318 return status;
319 }
320
GetImgTable()321 ImgTable* MediaCapsTableSpecific::GetImgTable()
322 {
323 DDI_FUNC_ENTER;
324
325 return m_imgTbl;
326 }
327
GetImageFormatsMaxNum()328 uint32_t MediaCapsTableSpecific::GetImageFormatsMaxNum()
329 {
330 DDI_FUNC_ENTER;
331
332 return m_imgTbl->size();
333 }
334
QuerySurfaceAttributesFromConfigId(VAConfigID configId)335 ProfileSurfaceAttribInfo* MediaCapsTableSpecific::QuerySurfaceAttributesFromConfigId(
336 VAConfigID configId)
337 {
338 DDI_FUNC_ENTER;
339
340 if (!IS_VALID_CONFIG_ID(configId))
341 {
342 DDI_ASSERTMESSAGE("Invalid config ID");
343 return nullptr;
344 }
345
346 ConfigLinux* configItem = nullptr;
347 configItem = QueryConfigItemFromIndex(configId);
348 DDI_CHK_NULL(configItem, "Invalid config id!", nullptr);
349
350 VAProfile profile = configItem->profile;
351 VAEntrypoint entrypoint = configItem->entrypoint;
352
353 uint32_t i = 0;
354
355 if (m_profileMap->find(profile) == m_profileMap->end() ||
356 m_profileMap->at(profile)->find(entrypoint) == m_profileMap->at(profile)->end())
357 {
358 return nullptr;
359 }
360
361 return const_cast<ProfileSurfaceAttribInfo*>(m_profileMap->at(profile)->at(entrypoint)->surfaceAttrib);
362 }