1
0
Fork 0

[media] atmel-isi: prepare for the support of preview path

Atmel ISI support a preview path which can output RGB data.

So this patch introduces a bool variable to choose which path is
enabled currently. And also we need setup corresponding path registers.

By default the preview path is disabled. We only use Codec path.

Signed-off-by: Josh Wu <josh.wu@atmel.com>
Signed-off-by: Guennadi Liakhovetski <g.liakhovetski@gmx.de>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
hifive-unleashed-5.1
Josh Wu 2015-11-03 03:45:09 -02:00 committed by Mauro Carvalho Chehab
parent ba0422bf56
commit 0fb725750b
1 changed files with 49 additions and 23 deletions

View File

@ -79,6 +79,7 @@ struct atmel_isi {
dma_addr_t fb_descriptors_phys;
struct list_head dma_desc_head;
struct isi_dma_desc dma_desc[MAX_BUFFER_NUM];
bool enable_preview_path;
struct completion complete;
/* ISI peripherial clock */
@ -195,11 +196,19 @@ static irqreturn_t atmel_isi_handle_streaming(struct atmel_isi *isi)
/* start next dma frame. */
isi->active = list_entry(isi->video_buffer_list.next,
struct frame_buffer, list);
isi_writel(isi, ISI_DMA_C_DSCR,
(u32)isi->active->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_C_CTRL,
ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_C_CH);
if (!isi->enable_preview_path) {
isi_writel(isi, ISI_DMA_C_DSCR,
(u32)isi->active->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_C_CTRL,
ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_C_CH);
} else {
isi_writel(isi, ISI_DMA_P_DSCR,
(u32)isi->active->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_P_CTRL,
ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_P_CH);
}
}
return IRQ_HANDLED;
}
@ -226,7 +235,8 @@ static irqreturn_t isi_interrupt(int irq, void *dev_id)
isi_writel(isi, ISI_INTDIS, ISI_CTRL_DIS);
ret = IRQ_HANDLED;
} else {
if (likely(pending & ISI_SR_CXFR_DONE))
if (likely(pending & ISI_SR_CXFR_DONE) ||
likely(pending & ISI_SR_PXFR_DONE))
ret = atmel_isi_handle_streaming(isi);
}
@ -371,21 +381,35 @@ static void start_dma(struct atmel_isi *isi, struct frame_buffer *buffer)
ISI_SR_CXFR_DONE | ISI_SR_PXFR_DONE);
/* Check if already in a frame */
if (isi_readl(isi, ISI_STATUS) & ISI_CTRL_CDC) {
dev_err(isi->soc_host.icd->parent, "Already in frame handling.\n");
return;
}
if (!isi->enable_preview_path) {
if (isi_readl(isi, ISI_STATUS) & ISI_CTRL_CDC) {
dev_err(isi->soc_host.icd->parent, "Already in frame handling.\n");
return;
}
isi_writel(isi, ISI_DMA_C_DSCR, (u32)buffer->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_C_CTRL, ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_C_CH);
isi_writel(isi, ISI_DMA_C_DSCR,
(u32)buffer->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_C_CTRL,
ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_C_CH);
} else {
isi_writel(isi, ISI_DMA_P_DSCR,
(u32)buffer->p_dma_desc->fbd_phys);
isi_writel(isi, ISI_DMA_P_CTRL,
ISI_DMA_CTRL_FETCH | ISI_DMA_CTRL_DONE);
isi_writel(isi, ISI_DMA_CHER, ISI_DMA_CHSR_P_CH);
}
cfg1 &= ~ISI_CFG1_FRATE_DIV_MASK;
/* Enable linked list */
cfg1 |= isi->pdata.frate | ISI_CFG1_DISCR;
/* Enable codec path and ISI */
ctrl = ISI_CTRL_CDC | ISI_CTRL_EN;
/* Enable ISI */
ctrl = ISI_CTRL_EN;
if (!isi->enable_preview_path)
ctrl |= ISI_CTRL_CDC;
isi_writel(isi, ISI_CTRL, ctrl);
isi_writel(isi, ISI_CFG1, cfg1);
}
@ -462,15 +486,17 @@ static void stop_streaming(struct vb2_queue *vq)
}
spin_unlock_irq(&isi->lock);
timeout = jiffies + FRAME_INTERVAL_MILLI_SEC * HZ;
/* Wait until the end of the current frame. */
while ((isi_readl(isi, ISI_STATUS) & ISI_CTRL_CDC) &&
time_before(jiffies, timeout))
msleep(1);
if (!isi->enable_preview_path) {
timeout = jiffies + FRAME_INTERVAL_MILLI_SEC * HZ;
/* Wait until the end of the current frame. */
while ((isi_readl(isi, ISI_STATUS) & ISI_CTRL_CDC) &&
time_before(jiffies, timeout))
msleep(1);
if (time_after(jiffies, timeout))
dev_err(icd->parent,
"Timeout waiting for finishing codec request\n");
if (time_after(jiffies, timeout))
dev_err(icd->parent,
"Timeout waiting for finishing codec request\n");
}
/* Disable interrupts */
isi_writel(isi, ISI_INTDIS,