Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 53460c53 authored by Devin Heitmueller's avatar Devin Heitmueller Committed by Mauro Carvalho Chehab
Browse files

[media] au0828: Add timer to restart TS stream if no data arrives on bulk endpoint



For reasons unclear, we intermittently see a case where the tune
is successful but the bulk stream fails to deliver any packets.

Add a timer to automatically stop/start the data pump if we
encounter such a case.

Signed-off-by: default avatarDevin Heitmueller <dheitmueller@kernellabs.com>
Signed-off-by: default avatarHans Verkuil <hans.verkuil@cisco.com>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@s-opensource.com>
parent d7590b57
Loading
Loading
Loading
Loading
+30 −0
Original line number Diff line number Diff line
@@ -105,6 +105,15 @@ static struct tda18271_config hauppauge_woodbury_tunerconfig = {

static void au0828_restart_dvb_streaming(struct work_struct *work);

static void au0828_bulk_timeout(unsigned long data)
{
	struct au0828_dev *dev = (struct au0828_dev *) data;

	dprintk(1, "%s called\n", __func__);
	dev->bulk_timeout_running = 0;
	schedule_work(&dev->restart_streaming);
}

/*-------------------------------------------------------------------*/
static void urb_completion(struct urb *purb)
{
@@ -138,6 +147,13 @@ static void urb_completion(struct urb *purb)
			ptr[0], purb->actual_length);
		schedule_work(&dev->restart_streaming);
		return;
	} else if (dev->bulk_timeout_running == 1) {
		/* The URB handler has fired, so cancel timer which would
		 * restart endpoint if we hadn't
		 */
		dprintk(1, "%s cancelling bulk timeout\n", __func__);
		dev->bulk_timeout_running = 0;
		del_timer(&dev->bulk_timeout);
	}

	/* Feed the transport payload into the kernel demux */
@@ -160,6 +176,11 @@ static int stop_urb_transfer(struct au0828_dev *dev)
	if (!dev->urb_streaming)
		return 0;

	if (dev->bulk_timeout_running == 1) {
		dev->bulk_timeout_running = 0;
		del_timer(&dev->bulk_timeout);
	}

	dev->urb_streaming = false;
	for (i = 0; i < URB_COUNT; i++) {
		if (dev->urbs[i]) {
@@ -232,6 +253,11 @@ static int start_urb_transfer(struct au0828_dev *dev)
	}

	dev->urb_streaming = true;

	/* If we don't valid data within 1 second, restart stream */
	mod_timer(&dev->bulk_timeout, jiffies + (HZ));
	dev->bulk_timeout_running = 1;

	return 0;
}

@@ -622,6 +648,10 @@ int au0828_dvb_register(struct au0828_dev *dev)
		return ret;
	}

	dev->bulk_timeout.function = au0828_bulk_timeout;
	dev->bulk_timeout.data = (unsigned long) dev;
	init_timer(&dev->bulk_timeout);

	return 0;
}

+2 −0
Original line number Diff line number Diff line
@@ -195,6 +195,8 @@ struct au0828_dev {
	/* Digital */
	struct au0828_dvb		dvb;
	struct work_struct              restart_streaming;
	struct timer_list               bulk_timeout;
	int                             bulk_timeout_running;

#ifdef CONFIG_VIDEO_AU0828_V4L2
	/* Analog */