From c9cf75775b3ab025d47ee47f14bc37aa4038ed7c Mon Sep 17 00:00:00 2001 From: Marko Viitanen Date: Wed, 9 Oct 2013 14:09:49 +0300 Subject: [PATCH] Deblocking fix: store block residual status and use it in deblocking --- src/encoder.c | 7 +++++-- src/filter.c | 3 ++- src/picture.c | 23 +++++++++++++++++++++++ src/picture.h | 3 +++ 4 files changed, 33 insertions(+), 3 deletions(-) diff --git a/src/encoder.c b/src/encoder.c index aecc598b..fca83193 100644 --- a/src/encoder.c +++ b/src/encoder.c @@ -1077,6 +1077,7 @@ void encode_coding_tree(encoder_control *encoder, uint16_t x_ctb, int16_t coeff_y[LCU_WIDTH*LCU_WIDTH*2]; int16_t coeff_u[LCU_WIDTH*LCU_WIDTH>>1]; int16_t coeff_v[LCU_WIDTH*LCU_WIDTH>>1]; + int8_t residual = 0; /* Initialize helper structure for transform */ transform_info ti; @@ -1109,12 +1110,14 @@ void encode_coding_tree(encoder_control *encoder, uint16_t x_ctb, ti.cb_top[1] = (ti.cb[0] & 0x2 || ti.cb[1] & 0x2 || ti.cb[2] & 0x2 || ti.cb[3] & 0x2)?1:0; ti.cb_top[2] = (ti.cb[0] & 0x4 || ti.cb[1] & 0x4 || ti.cb[2] & 0x4 || ti.cb[3] & 0x4)?1:0; + residual = ti.cb_top[0] | ti.cb_top[1] | ti.cb_top[2]; + picture_set_block_residual(encoder->in.cur_pic,x_ctb,y_ctb,depth,residual); cabac.ctx = &g_cu_qt_root_cbf_model; - CABAC_BIN(&cabac, ti.cb_top[0] | ti.cb_top[1] | ti.cb_top[2], "rqt_root_cbf"); + CABAC_BIN(&cabac, residual, "rqt_root_cbf"); // Code (possible) coeffs to bitstream ti.idx = 0; - if(ti.cb_top[0] | ti.cb_top[1] | ti.cb_top[2]) { + if(residual) { encode_transform_coeff(encoder, &ti,depth, 0); } } diff --git a/src/filter.c b/src/filter.c index 17cb0e15..056f8d6b 100644 --- a/src/filter.c +++ b/src/filter.c @@ -193,7 +193,8 @@ void filter_deblock_edge_luma(encoder_control *encoder, ((ypos>>MIN_SIZE)-(dir == EDGE_HOR)+(dir == EDGE_VER?block_idx/2:0)) * (encoder->in.width_in_lcu << MAX_DEPTH)]; // Filter strength strength = ((cu_q->type == CU_INTRA || cu_p->type == CU_INTRA) ? 2 : - (((abs(cu_q->inter.mv[0] - cu_p->inter.mv[0]) >= 4) || (abs(cu_q->inter.mv[1] - cu_p->inter.mv[1]) >= 4)) ? 1 : 0)); + (((abs(cu_q->inter.mv[0] - cu_p->inter.mv[0]) >= 4) || (abs(cu_q->inter.mv[1] - cu_p->inter.mv[1]) >= 4) || + cu_q->residual || cu_p->residual ) ? 1 : 0)); tc_index = CLIP(0, 51 + 2, (int32_t)(qp + 2*(strength - 1) + (tc_offset_div2 << 1))); tc = g_tc_table_8x8[tc_index] * bitdepth_scale; thr_cut = tc * 10; diff --git a/src/picture.c b/src/picture.c index b8b5dccd..49e41917 100644 --- a/src/picture.c +++ b/src/picture.c @@ -20,6 +20,29 @@ #define PSNRMAX (255.0 * 255.0) +/** + * \brief Set block residual status + * \param pic picture to use + * \param x_scu x SCU position (smallest CU) + * \param y_scu y SCU position (smallest CU) + * \param depth current CU depth + * \param residual residual status + */ +void picture_set_block_residual(picture *pic, uint32_t x_scu, uint32_t y_scu, + uint8_t depth, int8_t residual) +{ + uint32_t x, y; + int width_in_scu = pic->width_in_lcu << MAX_DEPTH; + int block_scu_width = (LCU_WIDTH >> depth) / (LCU_WIDTH >> MAX_DEPTH); + + for (y = y_scu; y < y_scu + block_scu_width; ++y) { + int cu_row = y * width_in_scu; + for (x = x_scu; x < x_scu + block_scu_width; ++x) { + pic->cu_array[MAX_DEPTH][cu_row + x].residual = residual; + } + } +} + /** * \brief Set block coded status * \param pic picture to use diff --git a/src/picture.h b/src/picture.h index 5ab5af81..7daa9f59 100644 --- a/src/picture.h +++ b/src/picture.h @@ -55,6 +55,7 @@ typedef struct int8_t type; int8_t depth; int8_t coded; + int8_t residual; cu_info_intra intra; cu_info_inter inter; } cu_info; @@ -101,6 +102,8 @@ picture * picture_init(int32_t width, int32_t height, int picture_destroy(picture *pic); void picture_set_block_coded(picture *pic, uint32_t x_scu, uint32_t y_scu, uint8_t depth, int8_t coded); +void picture_set_block_residual(picture *pic, uint32_t x_scu, uint32_t y_scu, + uint8_t depth, int8_t residual); void picture_set_block_split(picture *pic, uint32_t x_scu, uint32_t y_scu, uint8_t depth, int8_t split);