summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHartmut Hackmann <hartmut.hackmann@t-online.de>2008-03-02 02:41:06 +0100
committerHartmut Hackmann <hartmut.hackmann@t-online.de>2008-03-02 02:41:06 +0100
commite2f6f6c5ed1355bc0d7f06dbf83fe335efaf25a2 (patch)
treed524cc6397ea03863f5a868fa66a4f6dfcf9a427
parenta6d070732dd73977030e19c3bae51fc1c90a5a6c (diff)
downloadmediapointer-dvb-s2-e2f6f6c5ed1355bc0d7f06dbf83fe335efaf25a2.tar.gz
mediapointer-dvb-s2-e2f6f6c5ed1355bc0d7f06dbf83fe335efaf25a2.tar.bz2
saa7134: clear audio DSP interface after access error
From: Hartmut Hackmann <hartmut.hackmann@t-online.de> In the case of an access error to the high latency registers of the audio DSP, the interface needs to be cleared, otherwise a cascade of errors occurs. This patch is closely modeled after a proposal by Mirek Slugen Signed-off-by: Hartmut Hackmann <hartmut.hackmann@t-online.de>
-rw-r--r--linux/drivers/media/video/saa7134/saa7134-reg.h3
-rw-r--r--linux/drivers/media/video/saa7134/saa7134-tvaudio.c15
2 files changed, 16 insertions, 2 deletions
diff --git a/linux/drivers/media/video/saa7134/saa7134-reg.h b/linux/drivers/media/video/saa7134/saa7134-reg.h
index ac6431ba4..86f5eefdb 100644
--- a/linux/drivers/media/video/saa7134/saa7134-reg.h
+++ b/linux/drivers/media/video/saa7134/saa7134-reg.h
@@ -365,6 +365,9 @@
#define SAA7135_DSP_RWSTATE_RDB (1 << 1)
#define SAA7135_DSP_RWSTATE_WRR (1 << 0)
+#define SAA7135_DSP_RWCLEAR 0x586
+#define SAA7135_DSP_RWCLEAR_RERR 1
+
/* ------------------------------------------------------------------ */
/*
* Local variables:
diff --git a/linux/drivers/media/video/saa7134/saa7134-tvaudio.c b/linux/drivers/media/video/saa7134/saa7134-tvaudio.c
index 91d57ea5f..0d24ab598 100644
--- a/linux/drivers/media/video/saa7134/saa7134-tvaudio.c
+++ b/linux/drivers/media/video/saa7134/saa7134-tvaudio.c
@@ -681,6 +681,17 @@ static char *stdres[0x20] = {
#define DSP_RETRY 32
#define DSP_DELAY 16
+#define SAA7135_DSP_RWCLEAR_RERR 1
+
+static inline int saa_dsp_reset_error_bit(struct saa7134_dev *dev)
+{
+ int state = saa_readb(SAA7135_DSP_RWSTATE);
+ if (unlikely(state & SAA7135_DSP_RWSTATE_ERR)) {
+ d2printk("%s: resetting error bit\n", dev->name);
+ saa_writeb(SAA7135_DSP_RWCLEAR, SAA7135_DSP_RWCLEAR_RERR);
+ }
+ return 0;
+}
static inline int saa_dsp_wait_bit(struct saa7134_dev *dev, int bit)
{
@@ -688,8 +699,8 @@ static inline int saa_dsp_wait_bit(struct saa7134_dev *dev, int bit)
state = saa_readb(SAA7135_DSP_RWSTATE);
if (unlikely(state & SAA7135_DSP_RWSTATE_ERR)) {
- printk("%s: dsp access error\n",dev->name);
- /* FIXME: send ack ... */
+ printk(KERN_WARNING "%s: dsp access error\n", dev->name);
+ saa_dsp_reset_error_bit(dev);
return -EIO;
}
while (0 == (state & bit)) {