summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChen Liangjun <b36089@freescale.com>2012-10-31 17:27:23 +0800
committerChen Liangjun <b36089@freescale.com>2012-11-06 13:43:41 +0800
commit29d7200e2f5a07452a5c13799a57772097e4a8d6 (patch)
tree83681091268c0a480861d3fd9a99837b8afd8fef
parent5ec89ed17be50b3ad815836d497f340568ce9a58 (diff)
ENGR00231773-8 ASRC: prevent user app from processing input/output processing
To finish a buffer convert in ASRC, user should 1. prepare input buffer, 2. prepare output buffer 3. wait for output buffer's completion 4.wait for input buffer's comletion. The flow make user application ugly. In this patch, pack steps above to 1 stop: ASRC_CONVERT. Signed-off-by: Chen Liangjun <b36089@freescale.com>
-rw-r--r--drivers/mxc/asrc/mxc_asrc.c95
-rw-r--r--include/linux/mxc_asrc.h14
2 files changed, 66 insertions, 43 deletions
diff --git a/drivers/mxc/asrc/mxc_asrc.c b/drivers/mxc/asrc/mxc_asrc.c
index d9888a483de2..d16d7166ed5a 100644
--- a/drivers/mxc/asrc/mxc_asrc.c
+++ b/drivers/mxc/asrc/mxc_asrc.c
@@ -886,11 +886,26 @@ static unsigned int asrc_get_output_FIFO_size(enum asrc_pair_index index)
>> ASRC_ASRFSTX_OUTPUT_FIFO_OFFSET;
}
+static unsigned int asrc_get_input_FIFO_size(enum asrc_pair_index index)
+{
+ u32 reg;
+
+ reg = __raw_readl(g_asrc->vaddr + ASRC_ASRFSTA_REG + (index << 3));
+ return (reg & ASRC_ASRFSTX_INPUT_FIFO_MASK) >>
+ ASRC_ASRFSTX_INPUT_FIFO_OFFSET;
+}
+
+
static u32 asrc_read_one_from_output_FIFO(enum asrc_pair_index index)
{
return __raw_readl(g_asrc->vaddr + ASRC_ASRDOA_REG + (index << 3));
}
+static void asrc_write_one_to_output_FIFO(enum asrc_pair_index index, u32 value)
+{
+ __raw_writel(value, g_asrc->vaddr + ASRC_ASRDIA_REG + (index << 3));
+}
+
static void asrc_read_output_FIFO_S16(struct asrc_pair_params *params)
{
u32 size, i, j, reg, t_size;
@@ -1335,6 +1350,37 @@ int mxc_asrc_process_input_buffer(struct asrc_pair_params *params,
return 0;
}
+static void mxc_asrc_submit_dma(struct asrc_pair_params *params)
+{
+ enum asrc_pair_index index;
+ u32 size, i, j;
+ index = params->index;
+
+ /* read all data in OUTPUT FIFO*/
+ size = asrc_get_output_FIFO_size(params->index);
+ while (size) {
+ for (j = 0; j < size; j++) {
+ for (i = 0; i < params->channel_nums; i++)
+ asrc_read_one_from_output_FIFO(params->index);
+ }
+ mdelay(1);
+ size = asrc_get_output_FIFO_size(params->index);
+ }
+
+ /* Fill the input FIFO until reach the stall level */
+ size = asrc_get_input_FIFO_size(params->index);
+ while (size < 3) {
+ for (i = 0; i < params->channel_nums; i++)
+ asrc_write_one_to_output_FIFO(params->index, 0);
+ size = asrc_get_input_FIFO_size(params->index);
+ }
+
+ /* submit dma request */
+ dmaengine_submit(params->desc_in);
+ dmaengine_submit(params->desc_out);
+ sdma_set_event_pending(params->input_dma_channel);
+
+}
/*!
* asrc interface - function
@@ -1477,7 +1523,7 @@ static long asrc_ioctl(struct file *file,
params->pair_hold = 0;
break;
}
- case ASRC_Q_INBUF:
+ case ASRC_CONVERT:
{
struct asrc_convert_buffer buf;
if (copy_from_user
@@ -1488,43 +1534,27 @@ static long asrc_ioctl(struct file *file,
}
err = mxc_asrc_prepare_input_buffer(params, &buf);
+ if (err)
+ break;
- break;
- }
- case ASRC_DQ_INBUF:{
- struct asrc_convert_buffer buf;
- if (copy_from_user
- (&buf, (void __user *)arg,
- sizeof(struct asrc_convert_buffer))) {
- err = -EFAULT;
+ err = mxc_asrc_prepare_output_buffer(params, &buf);
+ if (err)
break;
- }
- err = mxc_asrc_process_input_buffer(params, &buf);
+ mxc_asrc_submit_dma(params);
- break;
- }
- case ASRC_Q_OUTBUF:{
- struct asrc_convert_buffer buf;
- if (copy_from_user
- (&buf, (void __user *)arg,
- sizeof(struct asrc_convert_buffer))) {
- err = -EFAULT;
+ err = mxc_asrc_process_output_buffer(params, &buf);
+ if (err)
break;
- }
- err = mxc_asrc_prepare_output_buffer(params, &buf);
- break;
- }
- case ASRC_DQ_OUTBUF:{
- struct asrc_convert_buffer buf;
- if (copy_from_user
- (&buf, (void __user *)arg,
- sizeof(struct asrc_convert_buffer))) {
- err = -EFAULT;
+ err = mxc_asrc_process_input_buffer(params, &buf);
+ if (err)
break;
- }
- err = mxc_asrc_process_output_buffer(params, &buf);
+
+ if (copy_to_user
+ ((void __user *)arg, &buf,
+ sizeof(struct asrc_convert_buffer)))
+ err = -EFAULT;
break;
}
@@ -1538,9 +1568,6 @@ static long asrc_ioctl(struct file *file,
}
params->asrc_active = 1;
- dmaengine_submit(params->desc_in);
- dmaengine_submit(params->desc_out);
-
asrc_start_conv(index);
break;
diff --git a/include/linux/mxc_asrc.h b/include/linux/mxc_asrc.h
index d1b313699477..8c0c45d86cfd 100644
--- a/include/linux/mxc_asrc.h
+++ b/include/linux/mxc_asrc.h
@@ -27,15 +27,11 @@
#define ASRC_REQ_PAIR _IOWR(ASRC_IOC_MAGIC, 0, struct asrc_req)
#define ASRC_CONFIG_PAIR _IOWR(ASRC_IOC_MAGIC, 1, struct asrc_config)
#define ASRC_RELEASE_PAIR _IOW(ASRC_IOC_MAGIC, 2, enum asrc_pair_index)
-#define ASRC_Q_INBUF _IOW(ASRC_IOC_MAGIC, 4, struct asrc_buffer)
-#define ASRC_DQ_INBUF _IOW(ASRC_IOC_MAGIC, 5, struct asrc_buffer)
-#define ASRC_Q_OUTBUF _IOW(ASRC_IOC_MAGIC, 6, struct asrc_buffer)
-#define ASRC_DQ_OUTBUF _IOW(ASRC_IOC_MAGIC, 7, struct asrc_buffer)
-#define ASRC_START_CONV _IOW(ASRC_IOC_MAGIC, 8, enum asrc_pair_index)
-#define ASRC_STOP_CONV _IOW(ASRC_IOC_MAGIC, 9, enum asrc_pair_index)
-#define ASRC_STATUS _IOW(ASRC_IOC_MAGIC, 10, struct asrc_status_flags)
-#define ASRC_FLUSH _IOW(ASRC_IOC_MAGIC, 11, enum asrc_pair_index)
-
+#define ASRC_CONVERT _IOW(ASRC_IOC_MAGIC, 3, struct asrc_convert_buffer)
+#define ASRC_START_CONV _IOW(ASRC_IOC_MAGIC, 4, enum asrc_pair_index)
+#define ASRC_STOP_CONV _IOW(ASRC_IOC_MAGIC, 5, enum asrc_pair_index)
+#define ASRC_STATUS _IOW(ASRC_IOC_MAGIC, 6, struct asrc_status_flags)
+#define ASRC_FLUSH _IOW(ASRC_IOC_MAGIC, 7, enum asrc_pair_index)
enum asrc_pair_index {
ASRC_PAIR_A,