xref: /aosp_15_r20/external/libavc/common/ih264_ihadamard_scaling.c (revision 495ae853bb871d1e5a258cb02c2cc13cde8ddb9a)
1*495ae853SAndroid Build Coastguard Worker /******************************************************************************
2*495ae853SAndroid Build Coastguard Worker  *
3*495ae853SAndroid Build Coastguard Worker  * Copyright (C) 2015 The Android Open Source Project
4*495ae853SAndroid Build Coastguard Worker  *
5*495ae853SAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
6*495ae853SAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
7*495ae853SAndroid Build Coastguard Worker  * You may obtain a copy of the License at:
8*495ae853SAndroid Build Coastguard Worker  *
9*495ae853SAndroid Build Coastguard Worker  * http://www.apache.org/licenses/LICENSE-2.0
10*495ae853SAndroid Build Coastguard Worker  *
11*495ae853SAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
12*495ae853SAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
13*495ae853SAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14*495ae853SAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
15*495ae853SAndroid Build Coastguard Worker  * limitations under the License.
16*495ae853SAndroid Build Coastguard Worker  *
17*495ae853SAndroid Build Coastguard Worker  *****************************************************************************
18*495ae853SAndroid Build Coastguard Worker  * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19*495ae853SAndroid Build Coastguard Worker */
20*495ae853SAndroid Build Coastguard Worker 
21*495ae853SAndroid Build Coastguard Worker /**
22*495ae853SAndroid Build Coastguard Worker *******************************************************************************
23*495ae853SAndroid Build Coastguard Worker * @file
24*495ae853SAndroid Build Coastguard Worker *  ih264_ihadamard_scaling.c
25*495ae853SAndroid Build Coastguard Worker *
26*495ae853SAndroid Build Coastguard Worker * @brief
27*495ae853SAndroid Build Coastguard Worker *  Contains definition of functions for h264 inverse hadamard 4x4 transform and
28*495ae853SAndroid Build Coastguard Worker *  scaling
29*495ae853SAndroid Build Coastguard Worker *
30*495ae853SAndroid Build Coastguard Worker * @author
31*495ae853SAndroid Build Coastguard Worker *  ittiam
32*495ae853SAndroid Build Coastguard Worker *
33*495ae853SAndroid Build Coastguard Worker * @par List of Functions:
34*495ae853SAndroid Build Coastguard Worker *  - ih264_ihadamard_scaling_4x4
35*495ae853SAndroid Build Coastguard Worker *  - ih264_ihadamard_scaling_2x2_uv
36*495ae853SAndroid Build Coastguard Worker *
37*495ae853SAndroid Build Coastguard Worker * @remarks
38*495ae853SAndroid Build Coastguard Worker *  none
39*495ae853SAndroid Build Coastguard Worker *
40*495ae853SAndroid Build Coastguard Worker *******************************************************************************
41*495ae853SAndroid Build Coastguard Worker */
42*495ae853SAndroid Build Coastguard Worker 
43*495ae853SAndroid Build Coastguard Worker /*****************************************************************************/
44*495ae853SAndroid Build Coastguard Worker /* File Includes                                                             */
45*495ae853SAndroid Build Coastguard Worker /*****************************************************************************/
46*495ae853SAndroid Build Coastguard Worker 
47*495ae853SAndroid Build Coastguard Worker /* User Include Files */
48*495ae853SAndroid Build Coastguard Worker #include "ih264_typedefs.h"
49*495ae853SAndroid Build Coastguard Worker #include "ih264_macros.h"
50*495ae853SAndroid Build Coastguard Worker #include "ih264_defs.h"
51*495ae853SAndroid Build Coastguard Worker #include "ih264_trans_macros.h"
52*495ae853SAndroid Build Coastguard Worker #include "ih264_trans_data.h"
53*495ae853SAndroid Build Coastguard Worker #include "ih264_size_defs.h"
54*495ae853SAndroid Build Coastguard Worker #include "ih264_structs.h"
55*495ae853SAndroid Build Coastguard Worker #include "ih264_trans_quant_itrans_iquant.h"
56*495ae853SAndroid Build Coastguard Worker 
57*495ae853SAndroid Build Coastguard Worker 
58*495ae853SAndroid Build Coastguard Worker /*****************************************************************************/
59*495ae853SAndroid Build Coastguard Worker /* Function Definitions                                                      */
60*495ae853SAndroid Build Coastguard Worker /*****************************************************************************/
61*495ae853SAndroid Build Coastguard Worker 
62*495ae853SAndroid Build Coastguard Worker /**
63*495ae853SAndroid Build Coastguard Worker ********************************************************************************
64*495ae853SAndroid Build Coastguard Worker *
65*495ae853SAndroid Build Coastguard Worker * @brief This function performs a 4x4 inverse hadamard transform on the luma
66*495ae853SAndroid Build Coastguard Worker * DC coefficients and then performs scaling.
67*495ae853SAndroid Build Coastguard Worker *
68*495ae853SAndroid Build Coastguard Worker * @par Description:
69*495ae853SAndroid Build Coastguard Worker *  The DC coefficients pass through a 2-stage inverse hadamard transform.
70*495ae853SAndroid Build Coastguard Worker *  This inverse transformed content is scaled to based on Qp value.
71*495ae853SAndroid Build Coastguard Worker *
72*495ae853SAndroid Build Coastguard Worker * @param[in] pi2_src
73*495ae853SAndroid Build Coastguard Worker *  input 4x4 block of DC coefficients
74*495ae853SAndroid Build Coastguard Worker *
75*495ae853SAndroid Build Coastguard Worker * @param[out] pi2_out
76*495ae853SAndroid Build Coastguard Worker *  output 4x4 block
77*495ae853SAndroid Build Coastguard Worker *
78*495ae853SAndroid Build Coastguard Worker * @param[in] pu2_iscal_mat
79*495ae853SAndroid Build Coastguard Worker *  pointer to scaling list
80*495ae853SAndroid Build Coastguard Worker *
81*495ae853SAndroid Build Coastguard Worker * @param[in] pu2_weigh_mat
82*495ae853SAndroid Build Coastguard Worker *  pointer to weight matrix
83*495ae853SAndroid Build Coastguard Worker *
84*495ae853SAndroid Build Coastguard Worker * @param[in] u4_qp_div_6
85*495ae853SAndroid Build Coastguard Worker *  Floor (qp/6)
86*495ae853SAndroid Build Coastguard Worker *
87*495ae853SAndroid Build Coastguard Worker * @param[in] pi4_tmp
88*495ae853SAndroid Build Coastguard Worker *  temporary buffer of size 1*16
89*495ae853SAndroid Build Coastguard Worker *
90*495ae853SAndroid Build Coastguard Worker * @returns none
91*495ae853SAndroid Build Coastguard Worker *
92*495ae853SAndroid Build Coastguard Worker * @remarks none
93*495ae853SAndroid Build Coastguard Worker *
94*495ae853SAndroid Build Coastguard Worker *******************************************************************************
95*495ae853SAndroid Build Coastguard Worker */
ih264_ihadamard_scaling_4x4(WORD16 * pi2_src,WORD16 * pi2_out,const UWORD16 * pu2_iscal_mat,const UWORD16 * pu2_weigh_mat,UWORD32 u4_qp_div_6,WORD32 * pi4_tmp)96*495ae853SAndroid Build Coastguard Worker void ih264_ihadamard_scaling_4x4(WORD16* pi2_src,
97*495ae853SAndroid Build Coastguard Worker                                  WORD16* pi2_out,
98*495ae853SAndroid Build Coastguard Worker                                  const UWORD16 *pu2_iscal_mat,
99*495ae853SAndroid Build Coastguard Worker                                  const UWORD16 *pu2_weigh_mat,
100*495ae853SAndroid Build Coastguard Worker                                  UWORD32 u4_qp_div_6,
101*495ae853SAndroid Build Coastguard Worker                                  WORD32* pi4_tmp)
102*495ae853SAndroid Build Coastguard Worker {
103*495ae853SAndroid Build Coastguard Worker     WORD32 i;
104*495ae853SAndroid Build Coastguard Worker     WORD32 x0, x1, x2, x3, x4, x5, x6, x7;
105*495ae853SAndroid Build Coastguard Worker     WORD16 *pi2_src_ptr, *pi2_out_ptr;
106*495ae853SAndroid Build Coastguard Worker     WORD32 *pi4_tmp_ptr;
107*495ae853SAndroid Build Coastguard Worker     WORD32 rnd_fact = (u4_qp_div_6 < 6) ? (1 << (5 - u4_qp_div_6)) : 0;
108*495ae853SAndroid Build Coastguard Worker 
109*495ae853SAndroid Build Coastguard Worker     pi4_tmp_ptr = pi4_tmp;
110*495ae853SAndroid Build Coastguard Worker     pi2_src_ptr = pi2_src;
111*495ae853SAndroid Build Coastguard Worker     pi2_out_ptr = pi2_out;
112*495ae853SAndroid Build Coastguard Worker 
113*495ae853SAndroid Build Coastguard Worker     /* horizontal transform */
114*495ae853SAndroid Build Coastguard Worker     for(i = 0; i < SUB_BLK_WIDTH_4x4; i++)
115*495ae853SAndroid Build Coastguard Worker     {
116*495ae853SAndroid Build Coastguard Worker         x4 = pi2_src_ptr[0];
117*495ae853SAndroid Build Coastguard Worker         x5 = pi2_src_ptr[1];
118*495ae853SAndroid Build Coastguard Worker         x6 = pi2_src_ptr[2];
119*495ae853SAndroid Build Coastguard Worker         x7 = pi2_src_ptr[3];
120*495ae853SAndroid Build Coastguard Worker 
121*495ae853SAndroid Build Coastguard Worker         x0 = x4 + x7;
122*495ae853SAndroid Build Coastguard Worker         x1 = x5 + x6;
123*495ae853SAndroid Build Coastguard Worker         x2 = x5 - x6;
124*495ae853SAndroid Build Coastguard Worker         x3 = x4 - x7;
125*495ae853SAndroid Build Coastguard Worker 
126*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[0] = x0 + x1;
127*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[1] = x2 + x3;
128*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[2] = x0 - x1;
129*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[3] = x3 - x2;
130*495ae853SAndroid Build Coastguard Worker 
131*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr += SUB_BLK_WIDTH_4x4;
132*495ae853SAndroid Build Coastguard Worker         pi2_src_ptr += SUB_BLK_WIDTH_4x4;
133*495ae853SAndroid Build Coastguard Worker     }
134*495ae853SAndroid Build Coastguard Worker 
135*495ae853SAndroid Build Coastguard Worker     /* vertical transform */
136*495ae853SAndroid Build Coastguard Worker     pi4_tmp_ptr = pi4_tmp;
137*495ae853SAndroid Build Coastguard Worker     for(i = 0; i < SUB_BLK_WIDTH_4x4; i++)
138*495ae853SAndroid Build Coastguard Worker     {
139*495ae853SAndroid Build Coastguard Worker         x4 = pi4_tmp_ptr[0];
140*495ae853SAndroid Build Coastguard Worker         x5 = pi4_tmp_ptr[4];
141*495ae853SAndroid Build Coastguard Worker         x6 = pi4_tmp_ptr[8];
142*495ae853SAndroid Build Coastguard Worker         x7 = pi4_tmp_ptr[12];
143*495ae853SAndroid Build Coastguard Worker 
144*495ae853SAndroid Build Coastguard Worker         x0 = x4 + x7;
145*495ae853SAndroid Build Coastguard Worker         x1 = x5 + x6;
146*495ae853SAndroid Build Coastguard Worker         x2 = x5 - x6;
147*495ae853SAndroid Build Coastguard Worker         x3 = x4 - x7;
148*495ae853SAndroid Build Coastguard Worker 
149*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[0] = x0 + x1;
150*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[4] = x2 + x3;
151*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[8] = x0 - x1;
152*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr[12] = x3 - x2;
153*495ae853SAndroid Build Coastguard Worker 
154*495ae853SAndroid Build Coastguard Worker         pi4_tmp_ptr++;
155*495ae853SAndroid Build Coastguard Worker     }
156*495ae853SAndroid Build Coastguard Worker     pi4_tmp_ptr = pi4_tmp;
157*495ae853SAndroid Build Coastguard Worker 
158*495ae853SAndroid Build Coastguard Worker     /* scaling */
159*495ae853SAndroid Build Coastguard Worker     for(i = 0; i < (SUB_BLK_WIDTH_4x4 * SUB_BLK_WIDTH_4x4); i++)
160*495ae853SAndroid Build Coastguard Worker     {
161*495ae853SAndroid Build Coastguard Worker         INV_QUANT(pi4_tmp_ptr[i], pu2_iscal_mat[0], pu2_weigh_mat[0],
162*495ae853SAndroid Build Coastguard Worker                   u4_qp_div_6, rnd_fact, 6);
163*495ae853SAndroid Build Coastguard Worker         pi2_out_ptr[i] = pi4_tmp_ptr[i];
164*495ae853SAndroid Build Coastguard Worker     }
165*495ae853SAndroid Build Coastguard Worker }
166*495ae853SAndroid Build Coastguard Worker 
167*495ae853SAndroid Build Coastguard Worker /**
168*495ae853SAndroid Build Coastguard Worker ********************************************************************************
169*495ae853SAndroid Build Coastguard Worker *
170*495ae853SAndroid Build Coastguard Worker * @brief This function performs a 2x2 inverse hadamard transform on the chroma
171*495ae853SAndroid Build Coastguard Worker * DC coefficients and then performs scaling.
172*495ae853SAndroid Build Coastguard Worker *
173*495ae853SAndroid Build Coastguard Worker * @par Description:
174*495ae853SAndroid Build Coastguard Worker *  The DC coefficients pass through a 2-stage inverse hadamard transform.
175*495ae853SAndroid Build Coastguard Worker *  This inverse transformed content is scaled to based on Qp value.
176*495ae853SAndroid Build Coastguard Worker *
177*495ae853SAndroid Build Coastguard Worker * @param[in] pi2_src
178*495ae853SAndroid Build Coastguard Worker *  input 2x2 block of DC coefficients
179*495ae853SAndroid Build Coastguard Worker *
180*495ae853SAndroid Build Coastguard Worker * @param[out] pi2_out
181*495ae853SAndroid Build Coastguard Worker *  output 2x2 block
182*495ae853SAndroid Build Coastguard Worker *
183*495ae853SAndroid Build Coastguard Worker * @param[in] pu2_iscal_mat
184*495ae853SAndroid Build Coastguard Worker *  pointer to scaling list
185*495ae853SAndroid Build Coastguard Worker *
186*495ae853SAndroid Build Coastguard Worker * @param[in] pu2_weigh_mat
187*495ae853SAndroid Build Coastguard Worker *  pointer to weight matrix
188*495ae853SAndroid Build Coastguard Worker *
189*495ae853SAndroid Build Coastguard Worker * @param[in] u4_qp_div_6
190*495ae853SAndroid Build Coastguard Worker *  Floor (qp/6)
191*495ae853SAndroid Build Coastguard Worker *
192*495ae853SAndroid Build Coastguard Worker * @param[in] pi4_tmp
193*495ae853SAndroid Build Coastguard Worker *  temporary buffer of size 1*16
194*495ae853SAndroid Build Coastguard Worker *
195*495ae853SAndroid Build Coastguard Worker * @returns none
196*495ae853SAndroid Build Coastguard Worker *
197*495ae853SAndroid Build Coastguard Worker * @remarks none
198*495ae853SAndroid Build Coastguard Worker *
199*495ae853SAndroid Build Coastguard Worker *******************************************************************************
200*495ae853SAndroid Build Coastguard Worker */
ih264_ihadamard_scaling_2x2_uv(WORD16 * pi2_src,WORD16 * pi2_out,const UWORD16 * pu2_iscal_mat,const UWORD16 * pu2_weigh_mat,UWORD32 u4_qp_div_6,WORD32 * pi4_tmp)201*495ae853SAndroid Build Coastguard Worker void ih264_ihadamard_scaling_2x2_uv(WORD16* pi2_src,
202*495ae853SAndroid Build Coastguard Worker                                     WORD16* pi2_out,
203*495ae853SAndroid Build Coastguard Worker                                     const UWORD16 *pu2_iscal_mat,
204*495ae853SAndroid Build Coastguard Worker                                     const UWORD16 *pu2_weigh_mat,
205*495ae853SAndroid Build Coastguard Worker                                     UWORD32 u4_qp_div_6,
206*495ae853SAndroid Build Coastguard Worker                                     WORD32* pi4_tmp)
207*495ae853SAndroid Build Coastguard Worker {
208*495ae853SAndroid Build Coastguard Worker     WORD32 i4_x0, i4_x1, i4_x2, i4_x3, i4_x4, i4_x5, i4_x6, i4_x7;
209*495ae853SAndroid Build Coastguard Worker     WORD32 i4_y0, i4_y1, i4_y2, i4_y3, i4_y4, i4_y5, i4_y6, i4_y7;
210*495ae853SAndroid Build Coastguard Worker 
211*495ae853SAndroid Build Coastguard Worker     UNUSED(pi4_tmp);
212*495ae853SAndroid Build Coastguard Worker 
213*495ae853SAndroid Build Coastguard Worker     /* U Plane */
214*495ae853SAndroid Build Coastguard Worker     i4_x4 = pi2_src[0];
215*495ae853SAndroid Build Coastguard Worker     i4_x5 = pi2_src[1];
216*495ae853SAndroid Build Coastguard Worker     i4_x6 = pi2_src[2];
217*495ae853SAndroid Build Coastguard Worker     i4_x7 = pi2_src[3];
218*495ae853SAndroid Build Coastguard Worker 
219*495ae853SAndroid Build Coastguard Worker     i4_x0 = i4_x4 + i4_x5;
220*495ae853SAndroid Build Coastguard Worker     i4_x1 = i4_x4 - i4_x5;
221*495ae853SAndroid Build Coastguard Worker     i4_x2 = i4_x6 + i4_x7;
222*495ae853SAndroid Build Coastguard Worker     i4_x3 = i4_x6 - i4_x7;
223*495ae853SAndroid Build Coastguard Worker 
224*495ae853SAndroid Build Coastguard Worker     i4_x4 = i4_x0 + i4_x2;
225*495ae853SAndroid Build Coastguard Worker     i4_x5 = i4_x1 + i4_x3;
226*495ae853SAndroid Build Coastguard Worker     i4_x6 = i4_x0 - i4_x2;
227*495ae853SAndroid Build Coastguard Worker     i4_x7 = i4_x1 - i4_x3;
228*495ae853SAndroid Build Coastguard Worker 
229*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_x4, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
230*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_x5, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
231*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_x6, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
232*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_x7, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
233*495ae853SAndroid Build Coastguard Worker 
234*495ae853SAndroid Build Coastguard Worker     pi2_out[0] = i4_x4;
235*495ae853SAndroid Build Coastguard Worker     pi2_out[1] = i4_x5;
236*495ae853SAndroid Build Coastguard Worker     pi2_out[2] = i4_x6;
237*495ae853SAndroid Build Coastguard Worker     pi2_out[3] = i4_x7;
238*495ae853SAndroid Build Coastguard Worker 
239*495ae853SAndroid Build Coastguard Worker     /* V Plane */
240*495ae853SAndroid Build Coastguard Worker     i4_y4 = pi2_src[4];
241*495ae853SAndroid Build Coastguard Worker     i4_y5 = pi2_src[5];
242*495ae853SAndroid Build Coastguard Worker     i4_y6 = pi2_src[6];
243*495ae853SAndroid Build Coastguard Worker     i4_y7 = pi2_src[7];
244*495ae853SAndroid Build Coastguard Worker 
245*495ae853SAndroid Build Coastguard Worker     i4_y0 = i4_y4 + i4_y5;
246*495ae853SAndroid Build Coastguard Worker     i4_y1 = i4_y4 - i4_y5;
247*495ae853SAndroid Build Coastguard Worker     i4_y2 = i4_y6 + i4_y7;
248*495ae853SAndroid Build Coastguard Worker     i4_y3 = i4_y6 - i4_y7;
249*495ae853SAndroid Build Coastguard Worker 
250*495ae853SAndroid Build Coastguard Worker     i4_y4 = i4_y0 + i4_y2;
251*495ae853SAndroid Build Coastguard Worker     i4_y5 = i4_y1 + i4_y3;
252*495ae853SAndroid Build Coastguard Worker     i4_y6 = i4_y0 - i4_y2;
253*495ae853SAndroid Build Coastguard Worker     i4_y7 = i4_y1 - i4_y3;
254*495ae853SAndroid Build Coastguard Worker 
255*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_y4, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
256*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_y5, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
257*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_y6, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
258*495ae853SAndroid Build Coastguard Worker     INV_QUANT(i4_y7, pu2_iscal_mat[0], pu2_weigh_mat[0], u4_qp_div_6, 0, 5);
259*495ae853SAndroid Build Coastguard Worker 
260*495ae853SAndroid Build Coastguard Worker     pi2_out[4] = i4_y4;
261*495ae853SAndroid Build Coastguard Worker     pi2_out[5] = i4_y5;
262*495ae853SAndroid Build Coastguard Worker     pi2_out[6] = i4_y6;
263*495ae853SAndroid Build Coastguard Worker     pi2_out[7] = i4_y7;
264*495ae853SAndroid Build Coastguard Worker }
265