aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/media/platform/exynos-gsc/gsc-core.h1
-rw-r--r--drivers/media/platform/exynos-gsc/gsc-m2m.c29
2 files changed, 17 insertions, 13 deletions
diff --git a/drivers/media/platform/exynos-gsc/gsc-core.h b/drivers/media/platform/exynos-gsc/gsc-core.h
index 76435d3bf62d..ef0a6564cef9 100644
--- a/drivers/media/platform/exynos-gsc/gsc-core.h
+++ b/drivers/media/platform/exynos-gsc/gsc-core.h
@@ -45,6 +45,7 @@
45#define GSC_DST_FMT (1 << 2) 45#define GSC_DST_FMT (1 << 2)
46#define GSC_CTX_M2M (1 << 3) 46#define GSC_CTX_M2M (1 << 3)
47#define GSC_CTX_STOP_REQ (1 << 6) 47#define GSC_CTX_STOP_REQ (1 << 6)
48#define GSC_CTX_ABORT (1 << 7)
48 49
49enum gsc_dev_flags { 50enum gsc_dev_flags {
50 /* for global */ 51 /* for global */
diff --git a/drivers/media/platform/exynos-gsc/gsc-m2m.c b/drivers/media/platform/exynos-gsc/gsc-m2m.c
index e576ff2de3de..810c3e13970c 100644
--- a/drivers/media/platform/exynos-gsc/gsc-m2m.c
+++ b/drivers/media/platform/exynos-gsc/gsc-m2m.c
@@ -46,6 +46,17 @@ static int gsc_m2m_ctx_stop_req(struct gsc_ctx *ctx)
46 return ret == 0 ? -ETIMEDOUT : ret; 46 return ret == 0 ? -ETIMEDOUT : ret;
47} 47}
48 48
49static void __gsc_m2m_job_abort(struct gsc_ctx *ctx)
50{
51 int ret;
52
53 ret = gsc_m2m_ctx_stop_req(ctx);
54 if ((ret == -ETIMEDOUT) || (ctx->state & GSC_CTX_ABORT)) {
55 gsc_ctx_state_lock_clear(GSC_CTX_STOP_REQ | GSC_CTX_ABORT, ctx);
56 gsc_m2m_job_finish(ctx, VB2_BUF_STATE_ERROR);
57 }
58}
59
49static int gsc_m2m_start_streaming(struct vb2_queue *q, unsigned int count) 60static int gsc_m2m_start_streaming(struct vb2_queue *q, unsigned int count)
50{ 61{
51 struct gsc_ctx *ctx = q->drv_priv; 62 struct gsc_ctx *ctx = q->drv_priv;
@@ -58,11 +69,8 @@ static int gsc_m2m_start_streaming(struct vb2_queue *q, unsigned int count)
58static int gsc_m2m_stop_streaming(struct vb2_queue *q) 69static int gsc_m2m_stop_streaming(struct vb2_queue *q)
59{ 70{
60 struct gsc_ctx *ctx = q->drv_priv; 71 struct gsc_ctx *ctx = q->drv_priv;
61 int ret;
62 72
63 ret = gsc_m2m_ctx_stop_req(ctx); 73 __gsc_m2m_job_abort(ctx);
64 if (ret == -ETIMEDOUT)
65 gsc_m2m_job_finish(ctx, VB2_BUF_STATE_ERROR);
66 74
67 pm_runtime_put(&ctx->gsc_dev->pdev->dev); 75 pm_runtime_put(&ctx->gsc_dev->pdev->dev);
68 76
@@ -91,15 +99,9 @@ void gsc_m2m_job_finish(struct gsc_ctx *ctx, int vb_state)
91 } 99 }
92} 100}
93 101
94
95static void gsc_m2m_job_abort(void *priv) 102static void gsc_m2m_job_abort(void *priv)
96{ 103{
97 struct gsc_ctx *ctx = priv; 104 __gsc_m2m_job_abort((struct gsc_ctx *)priv);
98 int ret;
99
100 ret = gsc_m2m_ctx_stop_req(ctx);
101 if (ret == -ETIMEDOUT)
102 gsc_m2m_job_finish(ctx, VB2_BUF_STATE_ERROR);
103} 105}
104 106
105static int gsc_get_bufs(struct gsc_ctx *ctx) 107static int gsc_get_bufs(struct gsc_ctx *ctx)
@@ -150,9 +152,10 @@ static void gsc_m2m_device_run(void *priv)
150 gsc->m2m.ctx = ctx; 152 gsc->m2m.ctx = ctx;
151 } 153 }
152 154
153 is_set = (ctx->state & GSC_CTX_STOP_REQ) ? 1 : 0; 155 is_set = ctx->state & GSC_CTX_STOP_REQ;
154 ctx->state &= ~GSC_CTX_STOP_REQ;
155 if (is_set) { 156 if (is_set) {
157 ctx->state &= ~GSC_CTX_STOP_REQ;
158 ctx->state |= GSC_CTX_ABORT;
156 wake_up(&gsc->irq_queue); 159 wake_up(&gsc->irq_queue);
157 goto put_device; 160 goto put_device;
158 } 161 }