summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Isely <devnull@localhost>2006-01-09 06:54:46 +0000
committerMike Isely <devnull@localhost>2006-01-09 06:54:46 +0000
commit2f999c230688131f47f938e3184982d425d19637 (patch)
treef6b041fd9c4f9f4b6ae3f32e2d4a9a418b99a077
parent4c4fffc05ca33429a5927f46a66e4569a11c9ad8 (diff)
downloadmediapointer-dvb-s2-2f999c230688131f47f938e3184982d425d19637.tar.gz
mediapointer-dvb-s2-2f999c230688131f47f938e3184982d425d19637.tar.bz2
Make the pvrusb2 driver more tolerant of USB streaming errors
From: Mike Isely <isely@pobox.com> Signed-off-by: Mike Isely <isely@pobox.com>
-rw-r--r--v4l/ChangeLog18
-rw-r--r--v4l_experimental/pvrusb2/pvrusb2-debug.h3
-rw-r--r--v4l_experimental/pvrusb2/pvrusb2-hdw.c27
-rw-r--r--v4l_experimental/pvrusb2/pvrusb2-io.c30
-rw-r--r--v4l_experimental/pvrusb2/pvrusb2-io.h5
-rw-r--r--v4l_experimental/pvrusb2/pvrusb2-main.c3
6 files changed, 76 insertions, 10 deletions
diff --git a/v4l/ChangeLog b/v4l/ChangeLog
index 2626d66cb..ca7e23ba9 100644
--- a/v4l/ChangeLog
+++ b/v4l/ChangeLog
@@ -1,3 +1,21 @@
+2006-01-09 06:50 mcisely
+
+ * v4l_experimental/pvrusb2/pvrusb2-debug.h:
+ * v4l_experimental/pvrusb2/pvrusb2-hdw.c:
+ (get_default_error_tolerance), (pvr2_hdw_setup_low),
+ (pvr2_hdw_render_useless_unlocked):
+ * v4l_experimental/pvrusb2/pvrusb2-io.c: (buffer_complete),
+ (pvr2_stream_setup):
+ * v4l_experimental/pvrusb2/pvrusb2-io.h:
+ * v4l_experimental/pvrusb2/pvrusb2-main.c:
+
+ - Implement new feature in pvrusb2 (which must be enabled via a
+ module option) that permits the streaming logic to tolerate a
+ specified level of USB errors. This change makes it possible to
+ still function in environments with flakey USB hardware.
+
+ Signed-off-by: Mike Isely <isely@pobox.com>
+
2006-01-09 06:42 mcisely
* v4l_experimental/pvrusb2/pvrusb2-hdw.c:
diff --git a/v4l_experimental/pvrusb2/pvrusb2-debug.h b/v4l_experimental/pvrusb2/pvrusb2-debug.h
index 3f58eef94..b0616e6f4 100644
--- a/v4l_experimental/pvrusb2/pvrusb2-debug.h
+++ b/v4l_experimental/pvrusb2/pvrusb2-debug.h
@@ -1,5 +1,5 @@
/*
- * $Id: pvrusb2-debug.h,v 1.3 2006/01/09 06:24:23 mcisely Exp $
+ * $Id: pvrusb2-debug.h,v 1.4 2006/01/09 06:54:46 mcisely Exp $
*
* Copyright (C) 2005 Mike Isely <isely@pobox.com>
*
@@ -28,6 +28,7 @@ extern int debug;
increasing noise level. */
#define PVR2_TRACE_INFO (1 << 0) // Normal messages
#define PVR2_TRACE_ERROR_LEGS (1 << 1) // error messages
+#define PVR2_TRACE_TOLERANCE (1 << 2) // track tolerance-affected errors
#define PVR2_TRACE_TRAP (1 << 3) // Trap & report misbehavior from app
#define PVR2_TRACE_INIT (1 << 4) // misc initialization steps
#define PVR2_TRACE_START_STOP (1 << 5) // Streaming start / stop
diff --git a/v4l_experimental/pvrusb2/pvrusb2-hdw.c b/v4l_experimental/pvrusb2/pvrusb2-hdw.c
index 15969ac46..2c6bfc949 100644
--- a/v4l_experimental/pvrusb2/pvrusb2-hdw.c
+++ b/v4l_experimental/pvrusb2/pvrusb2-hdw.c
@@ -1,6 +1,6 @@
/*
*
- * $Id: pvrusb2-hdw.c,v 1.9 2006/01/09 06:45:51 mcisely Exp $
+ * $Id: pvrusb2-hdw.c,v 1.10 2006/01/09 06:54:46 mcisely Exp $
*
* Copyright (C) 2005 Mike Isely <isely@pobox.com>
*
@@ -44,6 +44,7 @@ static int ctlchg = 0;
static int initusbreset = 1;
static int procreload = 0;
static int tuner[PVR_NUM] = { [0 ... PVR_NUM-1] = -1 };
+static int tolerance[PVR_NUM] = { [0 ... PVR_NUM-1] = 0 };
module_param(ctlchg, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(ctlchg, "0=optimize ctl change 1=always accept new ctl value");
@@ -58,6 +59,8 @@ module_param(width, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(width, "video width : 720,480,352");
module_param_array(tuner, int, NULL, 0444);
MODULE_PARM_DESC(tuner,"specify installed tuner type");
+module_param_array(tolerance, int, NULL, 0444);
+MODULE_PARM_DESC(tolerance,"specify stream error tolerance");
#define PVR2_CTL_WRITE_ENDPOINT 0x01
#define PVR2_CTL_READ_ENDPOINT 0x81
@@ -944,6 +947,17 @@ static int get_default_tuner_type(struct pvr2_hdw *hdw)
}
+static unsigned int get_default_error_tolerance(struct pvr2_hdw *hdw)
+{
+ int unit_number = hdw->unit_number;
+ int tp = 0;
+ if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
+ tp = tolerance[unit_number];
+ }
+ return tp;
+}
+
+
static void pvr2_hdw_setup_low(struct pvr2_hdw *hdw)
{
unsigned int idx;
@@ -1005,8 +1019,15 @@ static void pvr2_hdw_setup_low(struct pvr2_hdw *hdw)
pvr2_trace(PVR2_TRACE_INIT,
"pvr2_hdw_setup: video stream is %p",hdw->vid_stream);
if (hdw->vid_stream) {
+ idx = get_default_error_tolerance(hdw);
+ if (idx) {
+ pvr2_trace(PVR2_TRACE_INIT,
+ "pvr2_hdw_setup: video stream %p"
+ " setting tolerance %u",
+ hdw->vid_stream,idx);
+ }
pvr2_stream_setup(hdw->vid_stream,hdw->usb_dev,
- PVR2_VID_ENDPOINT);
+ PVR2_VID_ENDPOINT,idx);
}
if (!pvr2_hdw_dev_ok(hdw)) return;
@@ -2129,7 +2150,7 @@ void pvr2_hdw_render_useless_unlocked(struct pvr2_hdw *hdw)
pvr2_trace(PVR2_TRACE_INIT,"render_useless");
hdw->flag_ok = 0;
if (hdw->vid_stream) {
- pvr2_stream_setup(hdw->vid_stream,0,0);
+ pvr2_stream_setup(hdw->vid_stream,0,0,0);
}
hdw->flag_streaming_enabled = 0;
hdw->subsys_enabled_mask = 0;
diff --git a/v4l_experimental/pvrusb2/pvrusb2-io.c b/v4l_experimental/pvrusb2/pvrusb2-io.c
index 935978a14..c170bede0 100644
--- a/v4l_experimental/pvrusb2/pvrusb2-io.c
+++ b/v4l_experimental/pvrusb2/pvrusb2-io.c
@@ -1,6 +1,6 @@
/*
*
- * $Id: pvrusb2-io.c,v 1.1 2005/11/14 13:31:24 mchehab Exp $
+ * $Id: pvrusb2-io.c,v 1.2 2006/01/09 06:54:46 mcisely Exp $
*
* Copyright (C) 2005 Mike Isely <isely@pobox.com>
*
@@ -86,6 +86,9 @@ struct pvr2_stream {
/* Overhead for mutex enforcement */
spinlock_t list_lock;
struct semaphore sem;
+ /* Tracking state for tolerating errors */
+ unsigned int fail_count;
+ unsigned int fail_tolerance;
};
struct pvr2_buffer {
@@ -437,19 +440,38 @@ static void buffer_complete(struct urb *urb, struct pt_regs *regs)
{
struct pvr2_buffer *bp = urb->context;
struct pvr2_stream *sp;
+ unsigned long irq_flags;
BUFFER_CHECK(bp);
sp = bp->stream;
bp->used_count = 0;
+ bp->status = 0;
pvr2_trace(PVR2_TRACE_BUF_FLOW,
"/*---TRACE_FLOW---*/ bufferComplete %p stat=%d cnt=%d",
bp,urb->status,urb->actual_length);
+ spin_lock_irqsave(&sp->list_lock,irq_flags);
if ((!(urb->status)) ||
(urb->status == -ENOENT) ||
(urb->status == -ECONNRESET) ||
(urb->status == -ESHUTDOWN)) {
bp->used_count = urb->actual_length;
+ if (sp->fail_count) {
+ pvr2_trace(PVR2_TRACE_TOLERANCE,
+ "stream %p transfer ok"
+ " - fail count reset",sp);
+ sp->fail_count = 0;
+ }
+ } else if (sp->fail_count < sp->fail_tolerance) {
+ // We can tolerate this error, because we're below the
+ // threshold...
+ (sp->fail_count)++;
+ pvr2_trace(PVR2_TRACE_TOLERANCE,
+ "stream %p ignoring error %d"
+ " - fail count increased to %u",
+ sp,urb->status,sp->fail_count);
+ } else {
+ bp->status = urb->status;
}
- bp->status = urb->status;
+ spin_unlock_irqrestore(&sp->list_lock,irq_flags);
pvr2_buffer_set_ready(bp);
if (sp && sp->callback_func) {
sp->callback_func(sp->callback_data);
@@ -477,12 +499,14 @@ void pvr2_stream_destroy(struct pvr2_stream *sp)
void pvr2_stream_setup(struct pvr2_stream *sp,
struct usb_device *dev,
- int endpoint)
+ int endpoint,
+ unsigned int tolerance)
{
down(&sp->sem); do {
pvr2_stream_internal_flush(sp);
sp->dev = dev;
sp->endpoint = endpoint;
+ sp->fail_tolerance = tolerance;
} while(0); up(&sp->sem);
}
diff --git a/v4l_experimental/pvrusb2/pvrusb2-io.h b/v4l_experimental/pvrusb2/pvrusb2-io.h
index 17e01345b..5dc72b1ef 100644
--- a/v4l_experimental/pvrusb2/pvrusb2-io.h
+++ b/v4l_experimental/pvrusb2/pvrusb2-io.h
@@ -1,6 +1,6 @@
/*
*
- * $Id: pvrusb2-io.h,v 1.1 2005/11/14 13:31:24 mchehab Exp $
+ * $Id: pvrusb2-io.h,v 1.2 2006/01/09 06:54:46 mcisely Exp $
*
* Copyright (C) 2005 Mike Isely <isely@pobox.com>
*
@@ -42,7 +42,8 @@ const char *pvr2_buffer_state_decode(enum pvr2_buffer_state);
struct pvr2_stream *pvr2_stream_create(void);
void pvr2_stream_destroy(struct pvr2_stream *);
void pvr2_stream_setup(struct pvr2_stream *,
- struct usb_device *dev,int endpoint);
+ struct usb_device *dev,int endpoint,
+ unsigned int tolerance);
void pvr2_stream_set_callback(struct pvr2_stream *,
pvr2_stream_callback func,
void *data);
diff --git a/v4l_experimental/pvrusb2/pvrusb2-main.c b/v4l_experimental/pvrusb2/pvrusb2-main.c
index ffaaa4409..aa6fa7c9d 100644
--- a/v4l_experimental/pvrusb2/pvrusb2-main.c
+++ b/v4l_experimental/pvrusb2/pvrusb2-main.c
@@ -1,6 +1,6 @@
/*
*
- * $Id: pvrusb2-main.c,v 1.3 2006/01/01 08:26:03 mcisely Exp $
+ * $Id: pvrusb2-main.c,v 1.4 2006/01/09 06:54:46 mcisely Exp $
*
* Copyright (C) 2005 Mike Isely <isely@pobox.com>
* Copyright (C) 2004 Aurelien Alleaume <slts@free.fr>
@@ -43,6 +43,7 @@
#define DEFAULT_DEBUG_MASK (PVR2_TRACE_ERROR_LEGS| \
PVR2_TRACE_INFO| \
+ PVR2_TRACE_TOLERANCE| \
PVR2_TRACE_TRAP| \
PVR2_TRACE_FIRMWARE| \
PVR2_TRACE_EEPROM | \