1 /******************************************************************************
2  *
3  * Copyright (C) 2015 The Android Open Source Project
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at:
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  *****************************************************************************
18  * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20 
21 /**
22  *******************************************************************************
23  * @file
24  *  ih264e_deblk.c
25  *
26  * @brief
27  *  This file contains functions that are associated with deblocking
28  *
29  * @author
30  *  ittiam
31  *
32  * @par List of Functions:
33  *  - ih264e_fill_bs_1mv_1ref_non_mbaff
34  *  - ih264e_calculate_csbp
35  *  - ih264e_compute_bs
36  *  - ih264e_filter_top_edge
37  *  - ih264e_filter_left_edge
38  *  - ih264e_deblock_mb
39  *
40  * @remarks
41  *  None
42  *
43  *******************************************************************************
44  */
45 
46 /*****************************************************************************/
47 /* File Includes                                                             */
48 /*****************************************************************************/
49 
50 /* System include files */
51 #include <stdio.h>
52 #include <string.h>
53 #include <assert.h>
54 
55 /* User include files */
56 #include "ih264e_config.h"
57 #include "ih264_typedefs.h"
58 #include "iv2.h"
59 #include "ive2.h"
60 #include "ih264_macros.h"
61 #include "ih264_defs.h"
62 #include "ih264e_defs.h"
63 #include "ih264e_error.h"
64 #include "ih264e_bitstream.h"
65 #include "ime_distortion_metrics.h"
66 #include "ime_defs.h"
67 #include "ime_structs.h"
68 #include "ih264_structs.h"
69 #include "ih264_trans_quant_itrans_iquant.h"
70 #include "ih264_inter_pred_filters.h"
71 #include "ih264_mem_fns.h"
72 #include "ih264_padding.h"
73 #include "ih264_intra_pred_filters.h"
74 #include "ih264_deblk_edge_filters.h"
75 #include "ih264_cabac_tables.h"
76 #include "irc_cntrl_param.h"
77 #include "irc_frame_info_collector.h"
78 #include "ih264e_rate_control.h"
79 #include "ih264e_cabac_structs.h"
80 #include "ih264e_structs.h"
81 #include "ih264_trans_data.h"
82 #include "ih264_deblk_tables.h"
83 #include "ih264e_deblk.h"
84 
85 
86 /*****************************************************************************/
87 /* Extern global definitions                                                 */
88 /*****************************************************************************/
89 
90 /**
91 ******************************************************************************
92 * @brief  BS Table Lookup
93 * input  :
94 * output :
95 * @remarks none
96 ******************************************************************************
97 */
98 static const UWORD32 gu4_bs_table[][16] =
99 {
100     {
101         0x00000000, 0x02000000, 0x00020000, 0x02020000,
102         0x00000200, 0x02000200, 0x00020200, 0x02020200,
103         0x00000002, 0x02000002, 0x00020002, 0x02020002,
104         0x00000202, 0x02000202, 0x00020202, 0x02020202
105     },
106     {
107         0x01010101, 0x02010101, 0x01020101, 0x02020101,
108         0x01010201, 0x02010201, 0x01020201, 0x02020201,
109         0x01010102, 0x02010102, 0x01020102, 0x02020102,
110         0x01010202, 0x02010202, 0x01020202, 0x02020202
111     }
112 };
113 
114 /**
115 ******************************************************************************
116 * @brief  Transpose Matrix used in BS
117 * input  :
118 * output :
119 * @remarks none
120 ******************************************************************************
121 */
122 static const UWORD16  ih264e_gu2_4x4_v2h_reorder[16] =
123 {
124     0x0000, 0x0001, 0x0010, 0x0011,
125     0x0100, 0x0101, 0x0110, 0x0111,
126     0x1000, 0x1001, 0x1010, 0x1011,
127     0x1100, 0x1101, 0x1110, 0x1111
128 };
129 
130 
131 /*****************************************************************************/
132 /* Function Definitions                                                      */
133 /*****************************************************************************/
134 
135 /**
136 *******************************************************************************
137 *
138 * @brief Fill BS value for all the edges of an mb
139 *
140 * @par Description:
141 *  Fill BS value for all the edges of an mb
142 *
143 * @param[in] pu4_horz_bs
144 *  Base pointer of horizontal BS table
145 *
146 * @param[in] pu4_vert_bs
147 *  Base pointer of vertical BS table
148 *
149 * @param[in] u4_left_mb_csbp
150 *  coded sub block pattern of left mb
151 *
152 * @param[in] u4_left_mb_csbp
153 *  coded sub block pattern of top mb
154 *
155 * @param[in] ps_left_pu
156 *  PU for left MB
157 *
158 * @param[in] ps_top_pu
159 *  PU for top MB
160 *
161 * @param[in] ps_curr_pu
162 *  PU for current MB
163 *
164 *
165 * @returns  none
166 *
167 * @remarks  none
168 *
169 *******************************************************************************
170 */
ih264e_fill_bs_1mv_1ref_non_mbaff(UWORD32 * pu4_horz_bs,UWORD32 * pu4_vert_bs,UWORD32 u4_left_mb_csbp,UWORD32 u4_top_mb_csbp,UWORD32 u4_cur_mb_csbp,enc_pu_t * ps_left_pu,enc_pu_t * ps_top_pu,enc_pu_t * ps_curr_pu)171 static void ih264e_fill_bs_1mv_1ref_non_mbaff(UWORD32 *pu4_horz_bs,
172                                               UWORD32 *pu4_vert_bs,
173                                               UWORD32 u4_left_mb_csbp,
174                                               UWORD32 u4_top_mb_csbp,
175                                               UWORD32 u4_cur_mb_csbp,
176                                               enc_pu_t *ps_left_pu,
177                                               enc_pu_t *ps_top_pu,
178                                               enc_pu_t *ps_curr_pu)
179 {
180     /* motion vectors of blks p & q */
181     WORD16 i16_qMvl0_x, i16_qMvl0_y, i16_pMvl0_x, i16_pMvl0_y;
182     WORD16 i16_qMvl1_x, i16_qMvl1_y, i16_pMvl1_x, i16_pMvl1_y;
183 
184     /* temp var */
185     UWORD32 u4_left_flag, u4_top_flag;
186     const UWORD32 *bs_map;
187     UWORD32 u4_reordered_vert_bs_enc, u4_temp;
188 
189     /* Coded Pattern for Horizontal Edge */
190     /*-----------------------------------------------------------------------*/
191     /*u4_nbr_horz_csbp=11C|10C|9C|8C|7C|6C|5C|4C|3C|2C|1C|0C|15T|14T|13T|12T */
192     /*-----------------------------------------------------------------------*/
193     UWORD32 u4_nbr_horz_csbp = (u4_cur_mb_csbp << 4) | (u4_top_mb_csbp >> 12);
194     UWORD32 u4_horz_bs_enc = u4_cur_mb_csbp | u4_nbr_horz_csbp;
195 
196     /* Coded Pattern for Vertical Edge */
197     /*-----------------------------------------------------------------------*/
198     /*u4_left_mb_masked_csbp = 15L|0|0|0|11L|0|0|0|7L|0|0|0|3L|0|0|0         */
199     /*-----------------------------------------------------------------------*/
200     UWORD32 u4_left_mb_masked_csbp = u4_left_mb_csbp & CSBP_RIGHT_BLOCK_MASK;
201 
202     /*-----------------------------------------------------------------------*/
203     /*u4_cur_mb_masked_csbp =14C|13C|12C|x|10C|9C|8C|x|6C|5C|4C|x|2C|1C|0C|x */
204     /*-----------------------------------------------------------------------*/
205     UWORD32 u4_cur_mb_masked_csbp = (u4_cur_mb_csbp << 1)
206                     & (~CSBP_LEFT_BLOCK_MASK);
207 
208     /*-----------------------------------------------------------------------*/
209     /*u4_nbr_vert_csbp=14C|13C|12C|15L|10C|9C|8C|11L|6C|5C|4C|7L|2C|1C|0C|3L */
210     /*-----------------------------------------------------------------------*/
211     UWORD32 u4_nbr_vert_csbp = (u4_cur_mb_masked_csbp)
212                     | (u4_left_mb_masked_csbp >> 3);
213     UWORD32 u4_vert_bs_enc = u4_cur_mb_csbp | u4_nbr_vert_csbp;
214 
215     /* BS Calculation for MB Boundary Edges */
216 
217     /* BS calculation for 1 2 3 horizontal boundary */
218     bs_map = gu4_bs_table[0];
219     pu4_horz_bs[1] = bs_map[(u4_horz_bs_enc >> 4) & 0xF];
220     pu4_horz_bs[2] = bs_map[(u4_horz_bs_enc >> 8) & 0xF];
221     pu4_horz_bs[3] = bs_map[(u4_horz_bs_enc >> 12) & 0xF];
222 
223     /* BS calculation for 5 6 7 vertical boundary */
224     /* Do 4x4 tranpose of u4_vert_bs_enc by using look up table for reorder */
225     u4_reordered_vert_bs_enc = ih264e_gu2_4x4_v2h_reorder[u4_vert_bs_enc & 0xF];
226 
227     u4_temp = ih264e_gu2_4x4_v2h_reorder[(u4_vert_bs_enc >> 4) & 0xF];
228     u4_reordered_vert_bs_enc |= (u4_temp << 1);
229 
230     u4_temp = ih264e_gu2_4x4_v2h_reorder[(u4_vert_bs_enc >> 8) & 0xF];
231     u4_reordered_vert_bs_enc |= (u4_temp << 2);
232 
233     u4_temp = ih264e_gu2_4x4_v2h_reorder[(u4_vert_bs_enc >> 12) & 0xF];
234     u4_reordered_vert_bs_enc |= (u4_temp << 3);
235 
236     pu4_vert_bs[1] = bs_map[(u4_reordered_vert_bs_enc >> 4) & 0xF];
237     pu4_vert_bs[2] = bs_map[(u4_reordered_vert_bs_enc >> 8) & 0xF];
238     pu4_vert_bs[3] = bs_map[(u4_reordered_vert_bs_enc >> 12) & 0xF];
239 
240 
241     /* BS Calculation for MB Boundary Edges */
242     if (ps_top_pu->b1_intra_flag)
243     {
244         pu4_horz_bs[0] = 0x04040404;
245     }
246     else
247     {
248         if (ps_curr_pu->b2_pred_mode != ps_top_pu->b2_pred_mode)
249         {
250             u4_top_flag = 1;
251         }
252         else if(ps_curr_pu->b2_pred_mode != 2)
253         {
254             i16_pMvl0_x = ps_top_pu->s_me_info[ps_top_pu->b2_pred_mode].s_mv.i2_mvx;
255             i16_pMvl0_y = ps_top_pu->s_me_info[ps_top_pu->b2_pred_mode].s_mv.i2_mvy;
256 
257             i16_qMvl0_x = ps_curr_pu->s_me_info[ps_curr_pu->b2_pred_mode].s_mv.i2_mvx;
258             i16_qMvl0_y = ps_curr_pu->s_me_info[ps_curr_pu->b2_pred_mode].s_mv.i2_mvy;
259 
260 
261             u4_top_flag =  (ABS((i16_pMvl0_x - i16_qMvl0_x)) >= 4)
262                          | (ABS((i16_pMvl0_y - i16_qMvl0_y)) >= 4);
263         }
264         else
265         {
266 
267             i16_pMvl0_x = ps_top_pu->s_me_info[PRED_L0].s_mv.i2_mvx;
268             i16_pMvl0_y = ps_top_pu->s_me_info[PRED_L0].s_mv.i2_mvy;
269             i16_pMvl1_x = ps_top_pu->s_me_info[PRED_L1].s_mv.i2_mvx;
270             i16_pMvl1_y = ps_top_pu->s_me_info[PRED_L1].s_mv.i2_mvy;
271 
272             i16_qMvl0_x = ps_curr_pu->s_me_info[PRED_L0].s_mv.i2_mvx;
273             i16_qMvl0_y = ps_curr_pu->s_me_info[PRED_L0].s_mv.i2_mvy;
274             i16_qMvl1_x = ps_curr_pu->s_me_info[PRED_L1].s_mv.i2_mvx;
275             i16_qMvl1_y = ps_curr_pu->s_me_info[PRED_L1].s_mv.i2_mvy;
276 
277 
278             u4_top_flag =  (ABS((i16_pMvl0_x - i16_qMvl0_x)) >= 4)
279                          | (ABS((i16_pMvl0_y - i16_qMvl0_y)) >= 4)
280                          | (ABS((i16_pMvl1_x - i16_qMvl1_x)) >= 4)
281                          | (ABS((i16_pMvl1_y - i16_qMvl1_y)) >= 4);
282         }
283 
284         bs_map = gu4_bs_table[!!u4_top_flag];
285         pu4_horz_bs[0] = bs_map[u4_horz_bs_enc & 0xF];
286     }
287 
288 
289     if (ps_left_pu->b1_intra_flag)
290     {
291         pu4_vert_bs[0] = 0x04040404;
292     }
293     else
294     {
295         if (ps_curr_pu->b2_pred_mode != ps_left_pu->b2_pred_mode)
296         {
297             u4_left_flag = 1;
298         }
299         else if(ps_curr_pu->b2_pred_mode != 2)/* Not bipred */
300         {
301             i16_pMvl0_x = ps_left_pu->s_me_info[ps_left_pu->b2_pred_mode].s_mv.i2_mvx;
302             i16_pMvl0_y = ps_left_pu->s_me_info[ps_left_pu->b2_pred_mode].s_mv.i2_mvy;
303 
304             i16_qMvl0_x = ps_curr_pu->s_me_info[ps_curr_pu->b2_pred_mode].s_mv.i2_mvx;
305             i16_qMvl0_y = ps_curr_pu->s_me_info[ps_curr_pu->b2_pred_mode].s_mv.i2_mvy;
306 
307 
308             u4_left_flag =  (ABS((i16_pMvl0_x - i16_qMvl0_x)) >= 4)
309                           | (ABS((i16_pMvl0_y - i16_qMvl0_y)) >= 4);
310         }
311         else
312         {
313 
314             i16_pMvl0_x = ps_left_pu->s_me_info[PRED_L0].s_mv.i2_mvx;
315             i16_pMvl0_y = ps_left_pu->s_me_info[PRED_L0].s_mv.i2_mvy;
316             i16_pMvl1_x = ps_left_pu->s_me_info[PRED_L1].s_mv.i2_mvx;
317             i16_pMvl1_y = ps_left_pu->s_me_info[PRED_L1].s_mv.i2_mvy;
318 
319             i16_qMvl0_x = ps_curr_pu->s_me_info[PRED_L0].s_mv.i2_mvx;
320             i16_qMvl0_y = ps_curr_pu->s_me_info[PRED_L0].s_mv.i2_mvy;
321             i16_qMvl1_x = ps_curr_pu->s_me_info[PRED_L1].s_mv.i2_mvx;
322             i16_qMvl1_y = ps_curr_pu->s_me_info[PRED_L1].s_mv.i2_mvy;
323 
324 
325             u4_left_flag =  (ABS((i16_pMvl0_x - i16_qMvl0_x)) >= 4)
326                           | (ABS((i16_pMvl0_y - i16_qMvl0_y)) >= 4)
327                           | (ABS((i16_pMvl1_x - i16_qMvl1_x)) >= 4)
328                           | (ABS((i16_pMvl1_y - i16_qMvl1_y)) >= 4);
329         }
330 
331         bs_map = gu4_bs_table[!!u4_left_flag];
332         pu4_vert_bs[0] = bs_map[u4_reordered_vert_bs_enc & 0xF];
333     }
334 }
335 
336 /**
337 *******************************************************************************
338 *
339 * @brief calculate coded subblock pattern from nnz
340 *
341 * @par Description:
342 *  calculate coded subblock pattern from nnz
343 *
344 * @param[in] ps_proc
345 *  process context
346 *
347 * @returns  csbp
348 *
349 * @remarks  none
350 *
351 *******************************************************************************
352 */
ih264e_calculate_csbp(process_ctxt_t * ps_proc)353 static UWORD32 ih264e_calculate_csbp(process_ctxt_t *ps_proc)
354 {
355     /* number of non zeros for each tx blk */
356     UWORD8 *pu1_curr_nnz = (UWORD8 *)ps_proc->au4_nnz;
357 
358     /* csbp */
359     UWORD32 u4_csbp = 0;
360 
361     /* temp var */
362     WORD32  i4_i;
363 
364     pu1_curr_nnz += 1;
365 
366     /* Creating Subblock pattern for current MB */
367     /* 15C|14C|13C|12C|11C|10C|9C|8C|7C|6C|5C|4C|3C|2C|1C|0C  */
368     for (i4_i = 0; i4_i < 16; i4_i++ )
369     {
370         u4_csbp |= ((!!*(pu1_curr_nnz + i4_i))<< i4_i);
371     }
372 
373     return u4_csbp;
374 }
375 
376 /**
377 *******************************************************************************
378 *
379 * @brief This function computes blocking strength for an mb
380 *
381 * @par Description:
382 *  This function computes blocking strength for an mb
383 *
384 * @param[in] ps_proc
385 *  process context
386 *
387 * @returns  none
388 *
389 * @remarks
390 *
391 *******************************************************************************
392 */
ih264e_compute_bs(process_ctxt_t * ps_proc)393 void ih264e_compute_bs(process_ctxt_t * ps_proc)
394 {
395     /* deblk bs context */
396     bs_ctxt_t *ps_bs = &(ps_proc->s_deblk_ctxt.s_bs_ctxt);
397 
398     /* vertical blocking strength */
399     UWORD32 *pu4_pic_vert_bs;
400 
401     /* horizontal blocking strength */
402     UWORD32 *pu4_pic_horz_bs;
403 
404     /* mb indices */
405     WORD32 i4_mb_x, i4_mb_y;
406 
407     /* is intra */
408     WORD32 i4_intra;
409 
410     /* temp var */
411     WORD32 i4_wd_mbs = ps_proc->i4_wd_mbs;
412 
413     /* init indices */
414     i4_mb_x = ps_bs->i4_mb_x;
415     i4_mb_y = ps_bs->i4_mb_y;
416 
417     /* init pointers */
418     pu4_pic_vert_bs = ps_bs->pu4_pic_vert_bs + ((i4_mb_y * i4_wd_mbs) + i4_mb_x) * 4;
419     pu4_pic_horz_bs = ps_bs->pu4_pic_horz_bs + ((i4_mb_y * i4_wd_mbs) + i4_mb_x) * 4;
420 
421     /* is intra? */
422     i4_intra = ps_proc->u4_is_intra;
423 
424     /* compute blocking strength */
425     if (i4_intra)
426     {
427         pu4_pic_vert_bs[0] = 0x04040404;
428         pu4_pic_vert_bs[1] = pu4_pic_vert_bs[2] = pu4_pic_vert_bs[3] = 0x03030303;
429 
430         pu4_pic_horz_bs[0] = 0x04040404;
431         pu4_pic_horz_bs[1] = pu4_pic_horz_bs[2] = pu4_pic_horz_bs[3] = 0x03030303;
432     }
433     else
434     {
435         /* left mb syntax info */
436         mb_info_t *ps_left_mb_syntax_ele = &ps_proc->s_left_mb_syntax_ele;
437 
438         /* top mb syntax info */
439         mb_info_t *ps_top_mb_syntax_ele = ps_proc->ps_top_row_mb_syntax_ele + i4_mb_x;
440 
441         /* top row motion vector info */
442         enc_pu_t *ps_top_row_pu = ps_proc->ps_top_row_pu + i4_mb_x;
443 
444         /* csbp for curr mb */
445         ps_proc->u4_csbp = ih264e_calculate_csbp(ps_proc);
446 
447         /* csbp for ngbrs */
448         if (i4_mb_x == 0)
449         {
450             ps_left_mb_syntax_ele->u4_csbp = 0;
451             ps_proc->s_left_mb_pu.b1_intra_flag = 0;
452             ps_proc->s_left_mb_pu.b2_pred_mode = ps_proc->ps_pu->b2_pred_mode;
453             ps_proc->s_left_mb_pu.s_me_info[0].s_mv = ps_proc->ps_pu->s_me_info[0].s_mv;
454             ps_proc->s_left_mb_pu.s_me_info[1].s_mv = ps_proc->ps_pu->s_me_info[1].s_mv;
455         }
456         if (i4_mb_y == 0)
457         {
458             ps_top_mb_syntax_ele->u4_csbp = 0;
459             ps_top_row_pu->b1_intra_flag = 0;
460             ps_top_row_pu->b2_pred_mode = ps_proc->ps_pu->b2_pred_mode;
461             ps_top_row_pu->s_me_info[0].s_mv = ps_proc->ps_pu->s_me_info[0].s_mv;
462             ps_top_row_pu->s_me_info[1].s_mv = ps_proc->ps_pu->s_me_info[1].s_mv;
463         }
464 
465         ih264e_fill_bs_1mv_1ref_non_mbaff(pu4_pic_horz_bs,
466                                           pu4_pic_vert_bs,
467                                           ps_left_mb_syntax_ele->u4_csbp,
468                                           ps_top_mb_syntax_ele->u4_csbp,
469                                           ps_proc->u4_csbp,
470                                           &ps_proc->s_left_mb_pu,
471                                           ps_top_row_pu,
472                                           ps_proc->ps_pu);
473     }
474 
475     return ;
476 }
477 
478 /**
479 *******************************************************************************
480 *
481 * @brief This function performs deblocking of top horizontal edge
482 *
483 * @par Description:
484 *  This function performs deblocking of top horizontal edge
485 *
486 * @param[in] ps_codec
487 *  pointer to codec context
488 *
489 * @param[in] ps_proc
490 *  pointer to proc context
491 *
492 * @param[in] pu1_mb_qp
493 *  pointer to mb quantization param
494 *
495 * @param[in] pu1_cur_pic_luma
496 *  pointer to recon buffer luma
497 *
498 * @param[in] pu1_cur_pic_chroma
499 *  pointer to recon buffer chroma
500 *
501 * @param[in] pu4_pic_horz_bs
502 *  pointer to horizontal blocking strength
503 *
504 * @returns  none
505 *
506 * @remarks none
507 *
508 *******************************************************************************
509 */
ih264e_filter_top_edge(codec_t * ps_codec,process_ctxt_t * ps_proc,UWORD8 * pu1_mb_qp,UWORD8 * pu1_cur_pic_luma,UWORD8 * pu1_cur_pic_chroma,UWORD32 * pu4_pic_horz_bs)510 static void ih264e_filter_top_edge(codec_t *ps_codec,
511                                    process_ctxt_t *ps_proc,
512                                    UWORD8 *pu1_mb_qp,
513                                    UWORD8 *pu1_cur_pic_luma,
514                                    UWORD8 *pu1_cur_pic_chroma,
515                                    UWORD32 *pu4_pic_horz_bs)
516 {
517     /* strd */
518     WORD32 i4_rec_strd = ps_proc->i4_rec_strd;
519 
520     /* deblk params */
521     UWORD32 u4_alpha_luma, u4_beta_luma, u4_qp_luma, u4_idx_A_luma, u4_idx_B_luma, u4_qp_p, u4_qp_q;
522     UWORD32 u4_alpha_chroma, u4_beta_chroma, u4_qp_chroma, u4_idx_A_chroma, u4_idx_B_chroma;
523 
524     /* collect qp of left & top mb */
525     u4_qp_p = pu1_mb_qp[-ps_proc->i4_wd_mbs];
526     u4_qp_q = pu1_mb_qp[0];
527 
528     /********/
529     /* luma */
530     /********/
531     u4_qp_luma = (u4_qp_p + u4_qp_q + 1) >> 1;
532 
533     /* filter offset A and filter offset B have to be received from slice header */
534     /* TODO : for now lets set these offsets as zero */
535 
536 
537     u4_idx_A_luma = MIN(51, u4_qp_luma + 0);
538     u4_idx_B_luma = MIN(51, u4_qp_luma + 0);
539 
540     /* alpha, beta computation */
541     u4_alpha_luma = gu1_ih264_alpha_table[u4_idx_A_luma];
542     u4_beta_luma = gu1_ih264_beta_table[u4_idx_B_luma];
543 
544     /**********/
545     /* chroma */
546     /**********/
547     u4_qp_chroma = (gu1_qpc_fqpi[u4_qp_p] + gu1_qpc_fqpi[u4_qp_q] + 1) >> 1;
548 
549     /* filter offset A and filter offset B have to be received from slice header */
550     /* TODO : for now lets set these offsets as zero */
551 
552 
553     u4_idx_A_chroma = MIN(51, u4_qp_chroma + 0);
554     u4_idx_B_chroma = MIN(51, u4_qp_chroma + 0);
555 
556     /* alpha, beta computation */
557     u4_alpha_chroma = gu1_ih264_alpha_table[u4_idx_A_chroma];
558     u4_beta_chroma = gu1_ih264_beta_table[u4_idx_B_chroma];
559 
560     /* deblk edge */
561     /* top Horizontal edge - allowed to be deblocked ? */
562     if (pu4_pic_horz_bs[0] == 0x04040404)
563     {
564         /* strong filter */
565         ps_codec->pf_deblk_luma_horz_bs4(pu1_cur_pic_luma, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
566         ps_codec->pf_deblk_chroma_horz_bs4(pu1_cur_pic_chroma, i4_rec_strd, u4_alpha_chroma, u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma);
567     }
568     else
569     {
570         /* normal filter */
571         ps_codec->pf_deblk_luma_horz_bslt4(pu1_cur_pic_luma, i4_rec_strd, u4_alpha_luma,
572                                                u4_beta_luma, pu4_pic_horz_bs[0],
573                                                gu1_ih264_clip_table[u4_idx_A_luma]);
574 
575         ps_codec->pf_deblk_chroma_horz_bslt4(pu1_cur_pic_chroma, i4_rec_strd, u4_alpha_chroma,
576                                              u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma, pu4_pic_horz_bs[0],
577                                              gu1_ih264_clip_table[u4_idx_A_chroma], gu1_ih264_clip_table[u4_idx_A_chroma]);
578     }
579 }
580 
581 /**
582 *******************************************************************************
583 *
584 * @brief This function performs deblocking of left vertical edge
585 *
586 * @par Description:
587 *  This function performs deblocking of top horizontal edge
588 *
589 * @param[in] ps_codec
590 *  pointer to codec context
591 *
592 * @param[in] ps_proc
593 *  pointer to proc context
594 *
595 * @param[in] pu1_mb_qp
596 *  pointer to mb quantization param
597 *
598 * @param[in] pu1_cur_pic_luma
599 *  pointer to recon buffer luma
600 *
601 * @param[in] pu1_cur_pic_chroma
602 *  pointer to recon buffer chroma
603 *
604 * @param[in] pu4_pic_vert_bs
605 *  pointer to vertical blocking strength
606 *
607 * @returns  none
608 *
609 * @remarks none
610 *
611 *******************************************************************************
612 */
ih264e_filter_left_edge(codec_t * ps_codec,process_ctxt_t * ps_proc,UWORD8 * pu1_mb_qp,UWORD8 * pu1_cur_pic_luma,UWORD8 * pu1_cur_pic_chroma,UWORD32 * pu4_pic_vert_bs)613 static void ih264e_filter_left_edge(codec_t *ps_codec,
614                                     process_ctxt_t *ps_proc,
615                                     UWORD8 *pu1_mb_qp,
616                                     UWORD8 *pu1_cur_pic_luma,
617                                     UWORD8 *pu1_cur_pic_chroma,
618                                     UWORD32 *pu4_pic_vert_bs)
619 {
620     /* strd */
621     WORD32 i4_rec_strd = ps_proc->i4_rec_strd;
622 
623     /* deblk params */
624     UWORD32 u4_alpha_luma, u4_beta_luma, u4_qp_luma, u4_idx_A_luma, u4_idx_B_luma, u4_qp_p, u4_qp_q;
625     UWORD32 u4_alpha_chroma, u4_beta_chroma, u4_qp_chroma, u4_idx_A_chroma, u4_idx_B_chroma;
626 
627     /* collect qp of left & curr mb */
628     u4_qp_p = pu1_mb_qp[-1];
629     u4_qp_q = pu1_mb_qp[0];
630 
631     /********/
632     /* luma */
633     /********/
634     u4_qp_luma = (u4_qp_p + u4_qp_q + 1) >> 1;
635 
636     /* filter offset A and filter offset B have to be received from slice header */
637     /* TODO : for now lets set these offsets as zero */
638 
639 
640     u4_idx_A_luma = MIN(51, u4_qp_luma + 0);
641     u4_idx_B_luma = MIN(51, u4_qp_luma + 0);
642 
643     /* alpha, beta computation */
644     u4_alpha_luma = gu1_ih264_alpha_table[u4_idx_A_luma];
645     u4_beta_luma = gu1_ih264_beta_table[u4_idx_B_luma];
646 
647     /**********/
648     /* chroma */
649     /**********/
650     u4_qp_chroma = (gu1_qpc_fqpi[u4_qp_p] + gu1_qpc_fqpi[u4_qp_q] + 1) >> 1;
651 
652     /* filter offset A and filter offset B have to be received from slice header */
653     /* TODO : for now lets set these offsets as zero */
654 
655 
656     u4_idx_A_chroma = MIN(51, u4_qp_chroma + 0);
657     u4_idx_B_chroma = MIN(51, u4_qp_chroma + 0);
658 
659     /* alpha, beta computation */
660     u4_alpha_chroma = gu1_ih264_alpha_table[u4_idx_A_chroma];
661     u4_beta_chroma = gu1_ih264_beta_table[u4_idx_B_chroma];
662 
663     /* deblk edge */
664     if (pu4_pic_vert_bs[0] == 0x04040404)
665     {
666         /* strong filter */
667         ps_codec->pf_deblk_luma_vert_bs4(pu1_cur_pic_luma, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
668         ps_codec->pf_deblk_chroma_vert_bs4(pu1_cur_pic_chroma, i4_rec_strd, u4_alpha_chroma, u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma);
669     }
670     else
671     {
672         /* normal filter */
673         ps_codec->pf_deblk_luma_vert_bslt4(pu1_cur_pic_luma, i4_rec_strd,
674                                            u4_alpha_luma, u4_beta_luma,
675                                            pu4_pic_vert_bs[0],
676                                            gu1_ih264_clip_table[u4_idx_A_luma]);
677 
678         ps_codec->pf_deblk_chroma_vert_bslt4(pu1_cur_pic_chroma, i4_rec_strd, u4_alpha_chroma,
679                                              u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma, pu4_pic_vert_bs[0],
680                                              gu1_ih264_clip_table[u4_idx_A_chroma], gu1_ih264_clip_table[u4_idx_A_chroma]);
681     }
682 }
683 
684 /**
685 *******************************************************************************
686 *
687 * @brief This function performs deblocking on an mb
688 *
689 * @par Description:
690 *  This function performs deblocking on an mb
691 *
692 * @param[in] ps_proc
693 *  process context corresponding to the job
694 *
695 * @param[in] ps_deblk
696 *  pointer to deblock context
697 *
698 * @returns  none
699 *
700 * @remarks none
701 *
702 *******************************************************************************
703 */
ih264e_deblock_mb(process_ctxt_t * ps_proc,deblk_ctxt_t * ps_deblk)704 void ih264e_deblock_mb(process_ctxt_t *ps_proc, deblk_ctxt_t * ps_deblk)
705 {
706     /* codec ctxt */
707     codec_t *ps_codec = ps_proc->ps_codec;
708 
709     /* ngbr availability */
710     UWORD8  u1_mb_a, u1_mb_b;
711 
712     /* mb indices */
713     WORD32  i4_mb_x = ps_deblk->i4_mb_x, i4_mb_y = ps_deblk->i4_mb_y;
714 
715     /* pic qp ptr */
716     UWORD8  *pu1_pic_qp = ps_deblk->s_bs_ctxt.pu1_pic_qp;
717 
718     /* vertical blocking strength */
719     UWORD32 *pu4_pic_vert_bs = ps_deblk->s_bs_ctxt.pu4_pic_vert_bs;
720 
721     /* horizontal blocking strength */
722     UWORD32 *pu4_pic_horz_bs = ps_deblk->s_bs_ctxt.pu4_pic_horz_bs;
723 
724     /* src buffers luma */
725     UWORD8  *pu1_cur_pic_luma = ps_deblk->pu1_cur_pic_luma;
726 
727     /* src buffers chroma */
728     UWORD8  *pu1_cur_pic_chroma = ps_deblk->pu1_cur_pic_chroma;
729 
730     /* strd */
731     WORD32 i4_rec_strd = ps_proc->i4_rec_strd;
732 
733     /* deblk params */
734     UWORD32 u4_alpha_luma, u4_beta_luma, u4_qp_luma, u4_idx_A_luma, u4_idx_B_luma;
735     UWORD32 u4_alpha_chroma, u4_beta_chroma, u4_qp_chroma, u4_idx_A_chroma, u4_idx_B_chroma;
736 
737     /* temp var */
738     UWORD32 push_ptr = (i4_mb_y * ps_proc->i4_wd_mbs) + i4_mb_x;
739 
740     /* derive neighbor availability */
741     /* In slice mode the edges of mbs that lie on the slice boundary are not deblocked */
742     /* deblocking filter idc '2' */
743     if (ps_codec->s_cfg.e_slice_mode != IVE_SLICE_MODE_NONE)
744     {
745         /* slice index */
746         UWORD8  *pu1_slice_idx = ps_deblk->pu1_slice_idx;
747 
748         pu1_slice_idx += (i4_mb_y * ps_proc->i4_wd_mbs);
749         /* left macroblock availability */
750         u1_mb_a = (i4_mb_x == 0 ||
751                         (pu1_slice_idx[i4_mb_x - 1 ] != pu1_slice_idx[i4_mb_x]))? 0 : 1;
752         /* top macroblock availability */
753         u1_mb_b = (i4_mb_y == 0 ||
754                         (pu1_slice_idx[i4_mb_x-ps_proc->i4_wd_mbs] != pu1_slice_idx[i4_mb_x]))? 0 : 1;
755     }
756     else
757     {
758         /* left macroblock availability */
759         u1_mb_a = (i4_mb_x == 0)? 0 : 1;
760         /* top macroblock availability */
761         u1_mb_b = (i4_mb_y == 0)? 0 : 1;
762     }
763 
764     pu1_pic_qp += push_ptr;
765     pu4_pic_vert_bs += push_ptr * 4;
766     pu4_pic_horz_bs += push_ptr * 4;
767 
768     /********/
769     /* luma */
770     /********/
771     u4_qp_luma = pu1_pic_qp[0];
772 
773     /* filter offset A and filter offset B have to be received from slice header */
774     /* TODO : for now lets set these offsets as zero */
775 
776 
777     u4_idx_A_luma = MIN(51, u4_qp_luma + 0);
778     u4_idx_B_luma = MIN(51, u4_qp_luma + 0);
779 
780     /* alpha, beta computation */
781     u4_alpha_luma = gu1_ih264_alpha_table[u4_idx_A_luma];
782     u4_beta_luma = gu1_ih264_beta_table[u4_idx_B_luma];
783 
784     /**********/
785     /* chroma */
786     /**********/
787     u4_qp_chroma = gu1_qpc_fqpi[u4_qp_luma];
788 
789     /* filter offset A and filter offset B have to be received from slice header */
790     /* TODO : for now lets set these offsets as zero */
791 
792 
793     u4_idx_A_chroma = MIN(51, u4_qp_chroma + 0);
794     u4_idx_B_chroma = MIN(51, u4_qp_chroma + 0);
795 
796     /* alpha, beta computation */
797     u4_alpha_chroma = gu1_ih264_alpha_table[u4_idx_A_chroma];
798     u4_beta_chroma = gu1_ih264_beta_table[u4_idx_B_chroma];
799 
800     /* Deblock vertical edges */
801     /* left vertical edge 0 - allowed to be deblocked ? */
802     if (u1_mb_a)
803     {
804         ih264e_filter_left_edge(ps_codec, ps_proc, pu1_pic_qp, pu1_cur_pic_luma, pu1_cur_pic_chroma, pu4_pic_vert_bs);
805     }
806 
807     /* vertical edge 1 */
808     if (pu4_pic_vert_bs[1] == 0x04040404)
809     {
810         /* strong filter */
811         ps_codec->pf_deblk_luma_vert_bs4(pu1_cur_pic_luma + 4, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
812     }
813     else
814     {
815         /* normal filter */
816         ps_codec->pf_deblk_luma_vert_bslt4(pu1_cur_pic_luma + 4, i4_rec_strd,
817                                            u4_alpha_luma, u4_beta_luma,
818                                            pu4_pic_vert_bs[1],
819                                            gu1_ih264_clip_table[u4_idx_A_luma]);
820     }
821 
822     /* vertical edge 2 */
823     if (pu4_pic_vert_bs[2] == 0x04040404)
824     {
825         /* strong filter */
826         ps_codec->pf_deblk_luma_vert_bs4(pu1_cur_pic_luma + 8, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
827         ps_codec->pf_deblk_chroma_vert_bs4(pu1_cur_pic_chroma + 8, i4_rec_strd, u4_alpha_chroma, u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma);
828     }
829     else
830     {
831         /* normal filter */
832         ps_codec->pf_deblk_luma_vert_bslt4(pu1_cur_pic_luma + 8, i4_rec_strd, u4_alpha_luma,
833                                            u4_beta_luma, pu4_pic_vert_bs[2],
834                                            gu1_ih264_clip_table[u4_idx_A_luma]);
835 
836         ps_codec->pf_deblk_chroma_vert_bslt4(pu1_cur_pic_chroma + 8, i4_rec_strd, u4_alpha_chroma,
837                                              u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma, pu4_pic_vert_bs[2],
838                                              gu1_ih264_clip_table[u4_idx_A_chroma], gu1_ih264_clip_table[u4_idx_A_chroma]);
839     }
840 
841     /* vertical edge 3 */
842     if (pu4_pic_vert_bs[3] == 0x04040404)
843     {
844         /* strong filter */
845         ps_codec->pf_deblk_luma_vert_bs4(pu1_cur_pic_luma + 12, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
846     }
847     else
848     {
849         /* normal filter */
850         ps_codec->pf_deblk_luma_vert_bslt4(pu1_cur_pic_luma + 12, i4_rec_strd, u4_alpha_luma,
851                                            u4_beta_luma, pu4_pic_vert_bs[3],
852                                            gu1_ih264_clip_table[u4_idx_A_luma]);
853     }
854 
855     /* Deblock Horizontal edges */
856     /* Horizontal edge 0 */
857     if (u1_mb_b)
858     {
859         ih264e_filter_top_edge(ps_codec, ps_proc, pu1_pic_qp, pu1_cur_pic_luma, pu1_cur_pic_chroma, pu4_pic_horz_bs);
860     }
861 
862     /* horizontal edge 1 */
863     if (pu4_pic_horz_bs[1] == 0x04040404)
864     {
865         /* strong filter */
866         ps_codec->pf_deblk_luma_horz_bs4(pu1_cur_pic_luma + 4 * i4_rec_strd, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
867     }
868     else
869     {
870         /* normal filter */
871         ps_codec->pf_deblk_luma_horz_bslt4(pu1_cur_pic_luma + 4 * i4_rec_strd, i4_rec_strd, u4_alpha_luma,
872                                            u4_beta_luma, pu4_pic_horz_bs[1],
873                                            gu1_ih264_clip_table[u4_idx_A_luma]);
874     }
875 
876     /* horizontal edge 2 */
877     if (pu4_pic_horz_bs[2] == 0x04040404)
878     {
879         /* strong filter */
880         ps_codec->pf_deblk_luma_horz_bs4(pu1_cur_pic_luma + 8 * i4_rec_strd, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
881         ps_codec->pf_deblk_chroma_horz_bs4(pu1_cur_pic_chroma + 4 * i4_rec_strd, i4_rec_strd, u4_alpha_chroma, u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma);
882     }
883     else
884     {
885         /* normal filter */
886         ps_codec->pf_deblk_luma_horz_bslt4(pu1_cur_pic_luma + 8 * i4_rec_strd, i4_rec_strd, u4_alpha_luma,
887                                            u4_beta_luma, pu4_pic_horz_bs[2],
888                                            gu1_ih264_clip_table[u4_idx_A_luma]);
889 
890         ps_codec->pf_deblk_chroma_horz_bslt4(pu1_cur_pic_chroma + 4 * i4_rec_strd, i4_rec_strd, u4_alpha_chroma,
891                                              u4_beta_chroma, u4_alpha_chroma, u4_beta_chroma, pu4_pic_horz_bs[2],
892                                              gu1_ih264_clip_table[u4_idx_A_chroma], gu1_ih264_clip_table[u4_idx_A_chroma]);
893     }
894 
895     /* horizontal edge 3 */
896     if (pu4_pic_horz_bs[3] == 0x04040404)
897     {
898         /* strong filter */
899         ps_codec->pf_deblk_luma_horz_bs4(pu1_cur_pic_luma + 12 * i4_rec_strd, i4_rec_strd, u4_alpha_luma, u4_beta_luma);
900     }
901     else
902     {
903         /* normal filter */
904         ps_codec->pf_deblk_luma_horz_bslt4(pu1_cur_pic_luma + 12 * i4_rec_strd, i4_rec_strd, u4_alpha_luma,
905                                            u4_beta_luma, pu4_pic_horz_bs[3],
906                                            gu1_ih264_clip_table[u4_idx_A_luma]);
907     }
908 
909     return ;
910 }
911