1 /*
2 * Copyright (c) 2017, 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 media_ddi_base.cpp
24 //! \brief Defines base class for DDI media encode/decoder.
25 //!
26
27 #include "media_ddi_base.h"
28
GetRenderTargetID(DDI_CODEC_RENDER_TARGET_TABLE * rtTbl,DDI_MEDIA_SURFACE * surface)29 int32_t DdiMediaBase::GetRenderTargetID(DDI_CODEC_RENDER_TARGET_TABLE *rtTbl, DDI_MEDIA_SURFACE *surface)
30 {
31 if((nullptr == surface) || (nullptr == rtTbl))
32 {
33 return DDI_CODEC_INVALID_FRAME_INDEX;
34 }
35
36 if (0 == rtTbl->iNumRenderTargets)
37 {
38 return DDI_CODEC_INVALID_FRAME_INDEX;
39 }
40
41 for(int32_t i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i++)
42 {
43 if(rtTbl->pRT[i] == surface)
44 {
45 return i;
46 }
47 }
48 return DDI_CODEC_INVALID_FRAME_INDEX;
49 }
50
RegisterRTSurfaces(DDI_CODEC_RENDER_TARGET_TABLE * rtTbl,DDI_MEDIA_SURFACE * surface)51 VAStatus DdiMediaBase::RegisterRTSurfaces(DDI_CODEC_RENDER_TARGET_TABLE *rtTbl, DDI_MEDIA_SURFACE *surface)
52 {
53 DDI_CHK_NULL(surface, "nullptr surface", VA_STATUS_ERROR_INVALID_PARAMETER);
54 DDI_CHK_NULL(rtTbl, "nullptr rtTbl", VA_STATUS_ERROR_INVALID_PARAMETER);
55
56 int32_t i = 0;
57 uint32_t emptyEntry = DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT + 1;
58 for (i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i++)
59 {
60 if (rtTbl->pRT[i] == surface)
61 {
62 //pCurrRT has already been registered
63 emptyEntry = DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT + 1;
64 break;
65 }
66 else if ((rtTbl->pRT[i] == nullptr) && (emptyEntry == (DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT + 1)))
67 {
68 //find the first empty entry
69 emptyEntry = i;
70 }
71 }
72
73 if (emptyEntry < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT)
74 {
75 i = emptyEntry;
76 }
77 //if pCurrRT has not registered in pRT, add it into the array
78 if (i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT)
79 {
80 if (emptyEntry < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT)
81 {
82 rtTbl->pRT[emptyEntry] = surface;
83 rtTbl->ucRTFlag[emptyEntry] = SURFACE_STATE_ACTIVE_IN_CURFRAME;
84 rtTbl->iNumRenderTargets++;
85 }
86 else
87 {
88 rtTbl->ucRTFlag[i] = SURFACE_STATE_ACTIVE_IN_CURFRAME;
89 }
90 }
91 else
92 {
93 uint32_t j = 0;
94 for(j = 0; j < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; j ++)
95 {
96 if(rtTbl->ucRTFlag[j] == SURFACE_STATE_INACTIVE)
97 {
98 rtTbl->pRT[j] = surface;
99 rtTbl->ucRTFlag[j] = SURFACE_STATE_ACTIVE_IN_CURFRAME;
100 break;
101 }
102 }
103 if(j == DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT)
104 {
105 DDI_VERBOSEMESSAGE("RT table is full, and have no one can be resued");
106 return VA_STATUS_ERROR_INVALID_PARAMETER;
107 }
108 }
109
110 return VA_STATUS_SUCCESS;
111 }
112
ClearRefList(DDI_CODEC_RENDER_TARGET_TABLE * rtTbl,bool withDpb)113 VAStatus DdiMediaBase::ClearRefList(DDI_CODEC_RENDER_TARGET_TABLE *rtTbl, bool withDpb)
114 {
115 DDI_CHK_NULL(rtTbl, "nullptr rtTbl", VA_STATUS_ERROR_INVALID_PARAMETER);
116
117 if(withDpb)
118 {
119 for(int32_t i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i ++)
120 {
121 if(rtTbl->ucRTFlag[i] == SURFACE_STATE_ACTIVE_IN_LASTFRAME)
122 {
123 rtTbl->ucRTFlag[i] = SURFACE_STATE_INACTIVE;
124 }
125 else if(rtTbl->ucRTFlag[i] == SURFACE_STATE_ACTIVE_IN_CURFRAME)
126 {
127 rtTbl->ucRTFlag[i] = SURFACE_STATE_ACTIVE_IN_LASTFRAME;
128 }
129 }
130 }
131 else
132 {
133 for(int32_t i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i ++)
134 {
135 if(rtTbl->ucRTFlag[i])
136 {
137 rtTbl->ucRTFlag[i] --;
138 }
139 }
140 }
141 return VA_STATUS_SUCCESS;
142 }
143
UpdateRegisteredRTSurfaceFlag(DDI_CODEC_RENDER_TARGET_TABLE * rtTbl,DDI_MEDIA_SURFACE * surface)144 VAStatus DdiMediaBase::UpdateRegisteredRTSurfaceFlag(DDI_CODEC_RENDER_TARGET_TABLE *rtTbl, DDI_MEDIA_SURFACE *surface)
145 {
146 DDI_CHK_NULL(rtTbl, "nullptr rtTbl", VA_STATUS_ERROR_INVALID_PARAMETER);
147 DDI_CHK_NULL(surface, "nullptr surface", VA_STATUS_ERROR_INVALID_PARAMETER);
148
149 for(int32_t i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i ++)
150 {
151 if(rtTbl->pRT[i] == surface)
152 {
153 rtTbl->ucRTFlag[i] = SURFACE_STATE_ACTIVE_IN_CURFRAME;
154 return VA_STATUS_SUCCESS;
155 }
156 }
157 DDI_VERBOSEMESSAGE("frame was not registered in the RTtbl");
158 return VA_STATUS_ERROR_INVALID_PARAMETER;
159 }
160
UnRegisterRTSurfaces(DDI_CODEC_RENDER_TARGET_TABLE * rtTbl,DDI_MEDIA_SURFACE * surface)161 VAStatus DdiMediaBase::UnRegisterRTSurfaces(DDI_CODEC_RENDER_TARGET_TABLE *rtTbl, DDI_MEDIA_SURFACE *surface)
162 {
163 DDI_CHK_NULL(rtTbl, "nullptr rtTbl", VA_STATUS_ERROR_INVALID_PARAMETER);
164 DDI_CHK_NULL(surface, "nullptr surface", VA_STATUS_ERROR_INVALID_PARAMETER);
165
166 uint32_t i;
167
168 for (i = 0; i < DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT; i++)
169 {
170 if (rtTbl->pRT[i] == surface)
171 {
172 rtTbl->pRT[i] = nullptr;
173 rtTbl->ucRTFlag[i] = SURFACE_STATE_INACTIVE;
174 rtTbl->iNumRenderTargets--;
175 break;
176 }
177 }
178 if (i == DDI_MEDIA_MAX_SURFACE_NUMBER_CONTEXT)
179 {
180 DDI_VERBOSEMESSAGE("The surface to be unregistered can not find in RTtbl!");
181 return VA_STATUS_ERROR_INVALID_PARAMETER;
182 }
183 return VA_STATUS_SUCCESS;
184 }
185
186