mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-07 19:30:30 +09:00
media: platform: rockchip: cif: fix dvp sof event miss match
Signed-off-by: Allon Huang <allon.huang@rock-chips.com> Change-Id: Ie96851327335ca27cd978269df97d7c0e4aacb97
This commit is contained in:
@@ -262,6 +262,12 @@ static const struct cif_output_fmt out_fmts[] = {
|
||||
.mplanes = 1,
|
||||
.bpp = { 16 },
|
||||
.fmt_type = CIF_FMT_TYPE_RAW,
|
||||
}, {
|
||||
.fourcc = V4L2_PIX_FMT_GREY,
|
||||
.cplanes = 1,
|
||||
.mplanes = 1,
|
||||
.bpp = {8},
|
||||
.fmt_type = CIF_FMT_TYPE_RAW,
|
||||
}
|
||||
|
||||
/* TODO: We can support NV12M/NV21M/NV16M/NV61M too */
|
||||
@@ -2007,6 +2013,7 @@ static u32 rkcif_align_bits_per_pixel(const struct cif_output_fmt *fmt,
|
||||
case V4L2_PIX_FMT_YVYU:
|
||||
case V4L2_PIX_FMT_UYVY:
|
||||
case V4L2_PIX_FMT_VYUY:
|
||||
case V4L2_PIX_FMT_GREY:
|
||||
case V4L2_PIX_FMT_Y16:
|
||||
bpp = fmt->bpp[plane_index];
|
||||
break;
|
||||
@@ -2016,6 +2023,7 @@ static u32 rkcif_align_bits_per_pixel(const struct cif_output_fmt *fmt,
|
||||
case V4L2_PIX_FMT_SRGGB8:
|
||||
case V4L2_PIX_FMT_SGRBG8:
|
||||
case V4L2_PIX_FMT_SGBRG8:
|
||||
case V4L2_PIX_FMT_SBGGR8:
|
||||
case V4L2_PIX_FMT_SRGGB10:
|
||||
case V4L2_PIX_FMT_SGRBG10:
|
||||
case V4L2_PIX_FMT_SGBRG10:
|
||||
@@ -2335,6 +2343,7 @@ static int rkcif_stream_start(struct rkcif_stream *stream)
|
||||
|
||||
atomic_set(&sof_sd->frm_sync_seq, 0);
|
||||
stream->state = RKCIF_STATE_STREAMING;
|
||||
stream->cifdev->dvp_sof_in_oneframe = 0;
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -4698,14 +4707,21 @@ void rkcif_irq_pingpong(struct rkcif_device *cif_dev)
|
||||
lastpix = CIF_FETCH_Y_LAST_LINE(lastpix);
|
||||
ctl = rkcif_read_register(cif_dev, CIF_REG_DVP_CTRL);
|
||||
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTSTAT, intstat);
|
||||
|
||||
stream = &cif_dev->stream[RKCIF_STREAM_CIF];
|
||||
|
||||
if ((intstat & LINE_INT_END) && !(intstat & (FRAME_END))) {
|
||||
rkcif_dvp_event_inc_sof(cif_dev);
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTSTAT, intstat);
|
||||
int_en = rkcif_read_register(cif_dev, CIF_REG_DVP_INTEN);
|
||||
int_en &= ~LINE_INT_EN;
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTEN, int_en);
|
||||
if ((intstat & LINE_INT_END) && !(intstat & FRAME_END) &&
|
||||
(cif_dev->dvp_sof_in_oneframe == 0)) {
|
||||
if ((intstat & (PRE_INF_FRAME_END | PST_INF_FRAME_END)) == 0x0) {
|
||||
if ((intstat & INTSTAT_ERR) == 0x0) {
|
||||
rkcif_dvp_event_inc_sof(cif_dev);
|
||||
int_en = rkcif_read_register(cif_dev, CIF_REG_DVP_INTEN);
|
||||
int_en &= ~LINE_INT_EN;
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTEN, int_en);
|
||||
cif_dev->dvp_sof_in_oneframe = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (intstat & BUS_ERR) {
|
||||
@@ -4741,8 +4757,6 @@ void rkcif_irq_pingpong(struct rkcif_device *cif_dev)
|
||||
* a frame ready
|
||||
*/
|
||||
if ((intstat & PST_INF_FRAME_END)) {
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTSTAT,
|
||||
PST_INF_FRAME_END_CLR);
|
||||
|
||||
if (stream->stopping)
|
||||
/* To stop CIF ASAP, before FRAME_END irq */
|
||||
@@ -4753,12 +4767,10 @@ void rkcif_irq_pingpong(struct rkcif_device *cif_dev)
|
||||
if ((intstat & FRAME_END)) {
|
||||
struct vb2_v4l2_buffer *vb_done = NULL;
|
||||
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTSTAT,
|
||||
FRAME_END_CLR);
|
||||
|
||||
int_en = rkcif_read_register(cif_dev, CIF_REG_DVP_INTEN);
|
||||
int_en |= LINE_INT_EN;
|
||||
rkcif_write_register(cif_dev, CIF_REG_DVP_INTEN, int_en);
|
||||
cif_dev->dvp_sof_in_oneframe = 0;
|
||||
|
||||
if (stream->stopping) {
|
||||
rkcif_stream_stop(stream);
|
||||
@@ -4778,6 +4790,8 @@ void rkcif_irq_pingpong(struct rkcif_device *cif_dev)
|
||||
if (lastline != stream->pixm.height ||
|
||||
(!(cif_frmst & CIF_F0_READY) &&
|
||||
!(cif_frmst & CIF_F1_READY))) {
|
||||
|
||||
cif_dev->dvp_sof_in_oneframe = 1;
|
||||
v4l2_err(&cif_dev->v4l2_dev,
|
||||
"Bad frame, pp irq:0x%x frmst:0x%x size:%dx%d\n",
|
||||
intstat, cif_frmst, lastpix, lastline);
|
||||
|
||||
@@ -506,6 +506,7 @@ struct rkcif_device {
|
||||
unsigned int buf_wake_up_cnt;
|
||||
|
||||
bool iommu_en;
|
||||
unsigned int dvp_sof_in_oneframe;
|
||||
};
|
||||
|
||||
extern struct platform_driver rkcif_plat_drv;
|
||||
|
||||
@@ -311,20 +311,21 @@ enum cif_reg_index {
|
||||
#define FRAME_END_EN (0x1 << 0)
|
||||
#define BUS_ERR_EN (0x1 << 6)
|
||||
#define SCL_ERR_EN (0x1 << 7)
|
||||
#define PRE_INF_FRAME_END_EN (0x1 << 8)
|
||||
#define PST_INF_FRAME_END_EN (0x1 << 9)
|
||||
#define LINE_INT_EN (0x1 << 10)
|
||||
|
||||
/* CIF INTSTAT */
|
||||
#define INTSTAT_CLS (0x3FF)
|
||||
#define FRAME_END (0x01 << 0)
|
||||
#define LINE_ERR (0x1 << 2)
|
||||
#define PIX_ERR (0x1 << 3)
|
||||
#define IFIFO_OVERFLOW (0x1 << 4)
|
||||
#define DFIFO_OVERFLOW (0x1 << 5)
|
||||
#define BUS_ERR (0x1 << 6)
|
||||
#define LINE_ERR (0x01 << 2)
|
||||
#define PIX_ERR (0x01 << 3)
|
||||
#define IFIFO_OVERFLOW (0x01 << 4)
|
||||
#define DFIFO_OVERFLOW (0x01 << 5)
|
||||
#define BUS_ERR (0x01 << 6)
|
||||
#define PRE_INF_FRAME_END (0x01 << 8)
|
||||
#define PST_INF_FRAME_END (0x01 << 9)
|
||||
#define LINE_INT_END (0x1 << 10)
|
||||
#define LINE_INT_END (0x01 << 10)
|
||||
#define FRAME_END_CLR (0x01 << 0)
|
||||
#define PRE_INF_FRAME_END_CLR (0x01 << 8)
|
||||
#define PST_INF_FRAME_END_CLR (0x01 << 9)
|
||||
|
||||
Reference in New Issue
Block a user