diff --git a/drivers/media/platform/rockchip/vpss/stream_v20.c b/drivers/media/platform/rockchip/vpss/stream_v20.c index 3dd25b48356a..a14861e4ad01 100644 --- a/drivers/media/platform/rockchip/vpss/stream_v20.c +++ b/drivers/media/platform/rockchip/vpss/stream_v20.c @@ -967,8 +967,13 @@ static void scl_config_mi(struct rkvpss_stream *stream) if (fmt->fmt_type == FMT_FBC) val = 0; - else - val = out_fmt->plane_fmt[0].bytesperline; + else { + /* If 16-aligned, use stride; otherwise set to 0 */ + if (IS_ALIGNED(out_fmt->plane_fmt[0].bytesperline, 16)) + val = out_fmt->plane_fmt[0].bytesperline; + else + val = 0; + } reg = stream->config->mi.stride; rkvpss_unite_write(dev, reg, val); @@ -2264,6 +2269,34 @@ static int rkvpss_set_fmt(struct rkvpss_stream *stream, } } + /* Add format alignment checks */ + v4l2_dbg(1, rkvpss_debug, &dev->v4l2_dev, + "format alignment check: width=%d, height=%d, fourcc=0x%x\n", + pixm->width, pixm->height, fmt->fourcc); + if (fmt->fourcc == V4L2_PIX_FMT_FBC0 || + fmt->fourcc == V4L2_PIX_FMT_FBC2) { + if (!IS_ALIGNED(pixm->width, 64)) { + v4l2_err(&dev->v4l2_dev, + "stream:%d fbc output width %d is not 64 aligned\n", + stream->id, pixm->width); + return -EINVAL; + } + if (!IS_ALIGNED(pixm->height, 4)) { + v4l2_err(&dev->v4l2_dev, + "stream:%d fbc output height %d is not 4 aligned\n", + stream->id, pixm->height); + return -EINVAL; + } + } else { + /* Check width alignment for non-FBC formats */ + if (!IS_ALIGNED(pixm->width, 4)) { + v4l2_err(&dev->v4l2_dev, + "stream:%d output width %d is not 4 aligned\n", + stream->id, pixm->width); + return -EINVAL; + } + } + pixm->num_planes = fmt->mplanes; pixm->field = V4L2_FIELD_NONE; if (!pixm->quantization) diff --git a/drivers/media/platform/rockchip/vpss/vpss_offline_v20.c b/drivers/media/platform/rockchip/vpss/vpss_offline_v20.c index 97b8647a8f71..119da7518eda 100644 --- a/drivers/media/platform/rockchip/vpss/vpss_offline_v20.c +++ b/drivers/media/platform/rockchip/vpss/vpss_offline_v20.c @@ -1537,7 +1537,11 @@ static int write_config(struct rkvpss_offline_dev *ofl, rkvpss_hw_write(hw, reg + i * 0x100, val); reg = RKVPSS_MI_CHN0_WR_Y_STRIDE; - val = cfg->output[i].stride; + /* If 16-aligned, use stride; otherwise set to 0 */ + if (IS_ALIGNED(cfg->output[i].stride, 16)) + val = cfg->output[i].stride; + else + val = 0; rkvpss_hw_write(hw, reg + i * 0x100, val); reg = RKVPSS_MI_CHN0_WR_Y_SIZE;