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_encode_hevc.h
24 //! \brief    HEVC class definition for DDI media encoder.
25 //!
26 
27 #ifndef __MEDIA_LIBVA_ENCODER_HEVC_H__
28 #define __MEDIA_LIBVA_ENCODER_HEVC_H__
29 
30 #include "media_ddi_encode_base.h"
31 
32 static const uint8_t sliceTypeB = 0;
33 static const uint8_t sliceTypeP = 1;
34 static const uint8_t sliceTypeI = 2;
35 
36 static const uint8_t numMaxRefFrame    = 15;
37 static const uint8_t vdencRoiBlockSize = 32;
38 
39 const int8_t maxChromaOffset = 127;
40 const int8_t minChromaOffset = -128;
41 
42 //!
43 //! \class  DdiEncodeHevc
44 //! \brief  DDi encode HEVC
45 //!
46 class DdiEncodeHevc : public DdiEncodeBase
47 {
48 public:
49     //!
50     //! \brief    Constructor
51     //!
DdiEncodeHevc()52     DdiEncodeHevc(){};
53 
54     //!
55     //! \brief    Destructor
56     //!
57     ~DdiEncodeHevc();
58 
59     //!
60     //! \brief    Initialize Encode Context and CodecHal Setting for Hevc
61     //!
62     //! \param    [out] codecHalSettings
63     //!           Pointer to CodechalSetting *
64     //!
65     //! \return   VAStatus
66     //!           VA_STATUS_SUCCESS if success, else fail reason
67     //!
68     VAStatus ContextInitialize(CodechalSetting *codecHalSettings) override;
69 
70     //!
71     //! \brief    Send required buffers to for process
72     //! \details  It sends needed buffers by the process to the driver
73     //!
74     //! \param    [in] ctx
75     //!           Pointer to VADriverContextP
76     //! \param    [in] context
77     //!           VA context ID
78     //! \param    [in] buffers
79     //!           Pointer to VABufferID
80     //! \param    [in] numBuffers
81     //!           Number of buffers
82     //!
83     //! \return   VAStatus
84     //!           VA_STATUS_SUCCESS if success, else fail reason
85     //!
86     VAStatus RenderPicture(
87         VADriverContextP ctx,
88         VAContextID      context,
89         VABufferID       *buffers,
90         int32_t          numBuffers) override;
91 
92 protected:
93 
94     //!
95     //! \brief    Reset Encode Context At Frame Level
96     //!
97     //! \return   VAStatus
98     //!           VA_STATUS_SUCCESS if success, else fail reason
99     //!
100     VAStatus ResetAtFrameLevel() override;
101 
102     //!
103     //! \brief    Encode in CodecHal for Hevc
104     //!
105     //! \param    [in] numSlices
106     //!           Number of slice data structures
107     //!
108     //! \return   VAStatus
109     //!           VA_STATUS_SUCCESS if success, else fail reason
110     //!
111     VAStatus EncodeInCodecHal(uint32_t numSlices) override;
112 
113     //!
114     //! \brief    Parse Picture Parameter buffer to Encode Context
115     //!
116     //! \param    [in] mediaCtx
117     //!           Pointer to DDI_MEDIA_CONTEXT
118     //! \param    [in] ptr
119     //!           Pointer to Picture Parameter buffer
120     //!
121     //! \return   VAStatus
122     //!           VA_STATUS_SUCCESS if success, else fail reason
123     //!
124     VAStatus ParsePicParams(DDI_MEDIA_CONTEXT *mediaCtx, void *ptr) override;
125 
126     uint32_t getSliceParameterBufferSize() override;
127 
128     uint32_t getSequenceParameterBufferSize() override;
129 
130     uint32_t getPictureParameterBufferSize() override;
131 
132     uint32_t getQMatrixBufferSize() override;
133 
134     //!
135     //! \brief    Parse Sequence Parameter buffer to Encode Context
136     //!
137     //! \param    [in] ptr
138     //!           Pointer to Sequence Parameter buffer
139     //!
140     //! \return   VAStatus
141     //!           VA_STATUS_SUCCESS if success, else fail reason
142     //!
143     VAStatus ParseSeqParams(void *ptr);
144 
145     //!
146     //! \brief    Parse Slice Parameter buffer to Encode Context
147     //!
148     //! \param    [in] mediaCtx
149     //!           Pointer to DDI_MEDIA_CONTEXT
150     //! \param    [in] ptr
151     //!           Pointer to Slice Parameter buffer
152     //! \param    [in] numSlices
153     //!           Number of slice
154     //!
155     //! \return   VAStatus
156     //!           VA_STATUS_SUCCESS if success, else fail reason
157     //!
158     VAStatus ParseSlcParams(DDI_MEDIA_CONTEXT *mediaCtx, void *ptr, uint32_t numSlices);
159 
160     //!
161     //! \brief    Find the NAL Unit Start Codes
162     //!
163     //! \param    [in] buf
164     //!           Pointer to packed header NAL unit data
165     //! \param    [in] size
166     //!           byte size of packed header NAL unit data
167     //! \param    [in] startCodesOffset
168     //!           Pointer to NAL unit start codes offset from the packed header
169     //!           NAL unit data buf
170     //! \param    [in] startCodesLength
171     //!           Pointer to NAL unit start codes length
172     //!
173     //! \return   VAStatus
174     //!           VA_STATUS_SUCCESS if success,
175     //!           else VA_STATUS_ERROR_INVALID_BUFFER if start codes doesn't exit
176     //!
177     VAStatus FindNalUnitStartCodes(
178         uint8_t * buf,
179         uint32_t size,
180         uint32_t * startCodesOffset,
181         uint32_t * startCodesLength);
182 
183     //!
184     //! \brief    Parse Packed Header Parameter buffer to Encode Context
185     //!
186     //! \param    [in] ptr
187     //!           Pointer to Packed Header Parameter buffer
188     //!
189     //! return    VAStatus
190     //!           VA_STATUS_SUCCESS if success, else fail reason
191     //!
192     VAStatus ParsePackedHeaderParams(void *ptr);
193 
194     //!
195     //! \brief    Parse Packed Header Data buffer to Encode Context
196     //!
197     //! \param    [in] ptr
198     //!           Pointer to Packed Header Data buffer
199     //!
200     //! return    VAStatus
201     //!           VA_STATUS_SUCCESS if success, else fail reason
202     //!
203     VAStatus ParsePackedHeaderData(void *ptr);
204 
205     //!
206     //! \brief    Parse Misc Parameter buffer to Encode Context
207     //!
208     //! \param    [in] ptr
209     //!           Pointer to Misc Parameter buffer
210     //!
211     //! \return   VAStatus
212     //!           VA_STATUS_SUCCESS if success, else fail reason
213     //!
214     VAStatus ParseMiscParams(void *ptr);
215 
216     //!
217     //! \brief    Parse QMatrix Parameter buffer to Encode Context
218     //!
219     //! \param    [in] ptr
220     //!           Pointer to QMatrix Parameter buffer
221     //!
222     //! \return   VAStatus
223     //!           VA_STATUS_SUCCESS if success, else fail reason
224     //!
225     VAStatus Qmatrix(void *ptr);
226 
227     uint16_t m_previousFRvalue = 0; //!< For saving FR value to be used in case of dynamic BRC reset.
228 
229 private:
230     //!
231     //! \brief    Get Encode Codechal Picture Type from Va Slice Type
232     //!
233     //! \param    [in] vaSliceType
234     //!           Va Slice Type
235     //!
236     //! \return   uint8_t
237     //!           Encode Codechal Picture Type
238     //!
239     uint8_t CodechalPicTypeFromVaSlcType(uint8_t vaSliceType);
240 
241     //!
242     //! \brief    Get Slice Reference frame Index from picture reference
243     //!
244     //! \param    [in] picReference
245     //!           Pointer to PCODEC_PICTURE
246     //! \param    [out] slcReference
247     //!           Pointer to PCODEC_PICTURE
248     //!
249     //! \return   void
250     //!
251     void GetSlcRefIdx(CODEC_PICTURE *picReference, CODEC_PICTURE *slcReference);
252 
253     //!
254     //! \brief    Setup params of Codechal Picture
255     //!
256     //! \param    [in] mediaCtx
257     //!           Pointer to DdiMediaContext
258     //! \param    [in] RTtbl
259     //!           Pointer to DDI_CODEC_RENDER_TARGET_TABLE
260     //! \param    [in] vaPicHEVC
261     //!           Pointer to VAPictureHEVC
262     //! \param    [in] picReference
263     //!           Picture reference flag
264     //! \param    [in] sliceReference
265     //!           Slice Reference flag
266     //! \param    [out] codecHalPic
267     //!           Pointer to PCODEC_PICTURE
268     //!
269     //! \return   void
270     //!
271     void SetupCodecPicture(
272         DDI_MEDIA_CONTEXT             *mediaCtx,
273         DDI_CODEC_RENDER_TARGET_TABLE *RTtbl,
274         CODEC_PICTURE                 *codecHalPic,
275         VAPictureHEVC                 vaPicHEVC,
276         bool                          picReference,
277         bool                          sliceReference);
278 
279     //!
280     //! \brief    Check whether swizzle needed
281     //!
282     //! \param    [in] rawSurface
283     //!           Pointer of Raw Surface
284     //! \param    [in] reconSurface
285     //!           Pointer of Recon Surface
286     //!
287     //! \return   bool, true if need, otherwise false
288     //!
NeedDisapayFormatSwizzle(DDI_MEDIA_SURFACE * rawSurface,DDI_MEDIA_SURFACE * reconSurface)289     inline bool NeedDisapayFormatSwizzle(
290         DDI_MEDIA_SURFACE *rawSurface,
291         DDI_MEDIA_SURFACE *reconSurface)
292     {
293         bool ret = false;
294 
295         if (Media_Format_A8R8G8B8 == rawSurface->format ||
296            Media_Format_B10G10R10A2 == rawSurface->format)
297         {
298             ret = true;
299         }
300 
301         if (ret &&
302             (Media_Format_A8R8G8B8 == reconSurface->format ||
303             Media_Format_B10G10R10A2 == reconSurface->format))
304         {
305             ret = false;
306         }
307 
308         return ret;
309     }
310 
311     //!
312     //! \brief    if it is hevc scc profile
313     //!
314     //! \return   true or false
315     //!
316     bool IsSccProfile();
317 
318     //! \brief Number of Rectangle
319     uint32_t    m_numDirtyRects = 0;
320 
321     //! \brief Pointer to dirty rectangle array with num_roi_rectangle elements
322     PCODEC_ROI  m_pDirtyRect = nullptr;
323 };
324 #endif  //__MEDIA_LIBVA_ENCODER_HEVC_H__
325