From 66540f67e794fa58f7d32e8850e43676b471a312 Mon Sep 17 00:00:00 2001 From: Jason Chen Date: Mon, 7 Nov 2011 16:46:36 +0800 Subject: ENGR00161526 mxc v4l2 output: 720p ic bypass output may failed in block Repeat play with below cmdline: /unit_tests/mxc_v4l2_output.out -iw 1280 -ih 720 -ow 1280 -oh 720 -fr 10 -l 1 /unit_tests/720p.yuv Found the ipu update offset function cause this issue, it can be work-around by setting it only when value changed. Signed-off-by: Jason Chen --- drivers/mxc/ipu3/ipu_param_mem.h | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) (limited to 'drivers/mxc/ipu3') diff --git a/drivers/mxc/ipu3/ipu_param_mem.h b/drivers/mxc/ipu3/ipu_param_mem.h index 7fbd4e12d0fd..223a1cdf5fa4 100644 --- a/drivers/mxc/ipu3/ipu_param_mem.h +++ b/drivers/mxc/ipu3/ipu_param_mem.h @@ -653,6 +653,7 @@ static inline void _ipu_ch_offset_update(struct ipu_soc *ipu, { uint32_t u_offset = 0; uint32_t v_offset = 0; + uint32_t old_offset = 0; uint32_t u_fix = 0; uint32_t v_fix = 0; int32_t sub_ch = 0; @@ -788,14 +789,22 @@ static inline void _ipu_ch_offset_update(struct ipu_soc *ipu, dev_warn(ipu->dev, "IDMAC%d's V offset is not 8-byte aligned\n", ch); - ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, ch), 0, 46, 22, u_offset / 8); - ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, ch), 0, 68, 22, v_offset / 8); + old_offset = ipu_ch_param_read_field_io(ipu_ch_param_addr(ipu, ch), 0, 46, 22); + if (old_offset != u_offset / 8) + ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, ch), 0, 46, 22, u_offset / 8); + old_offset = ipu_ch_param_read_field_io(ipu_ch_param_addr(ipu, ch), 0, 68, 22); + if (old_offset != v_offset / 8) + ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, ch), 0, 68, 22, v_offset / 8); sub_ch = __ipu_ch_get_third_buf_cpmem_num(ch); if (sub_ch <= 0) return; - ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 46, 22, u_offset / 8); - ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 68, 22, v_offset / 8); + old_offset = ipu_ch_param_read_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 46, 22); + if (old_offset != u_offset / 8) + ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 46, 22, u_offset / 8); + old_offset = ipu_ch_param_read_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 68, 22); + if (old_offset != v_offset / 8) + ipu_ch_param_mod_field_io(ipu_ch_param_addr(ipu, sub_ch), 0, 68, 22, v_offset / 8); }; static inline void _ipu_ch_params_set_alpha_width(struct ipu_soc *ipu, uint32_t ch, int alpha_width) -- cgit v1.2.3