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

Commit 60c66b6f authored by Hans Verkuil's avatar Hans Verkuil Committed by Mauro Carvalho Chehab
Browse files

[media] tlg2300: allow multiple opens



Due to a poor administration of the driver state it wasn't possible to open
a video or vbi device multiple times.

Signed-off-by: default avatarHans Verkuil <hans.verkuil@cisco.com>
Acked-by: default avatarHuang Shijie <shijie8@gmail.com>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@redhat.com>
parent d4de6e40
Loading
Loading
Loading
Loading
+0 −1
Original line number Diff line number Diff line
@@ -26,7 +26,6 @@
#define POSEIDON_STATE_ANALOG		(0x0001)
#define POSEIDON_STATE_FM		(0x0002)
#define POSEIDON_STATE_DVBT		(0x0004)
#define POSEIDON_STATE_VBI		(0x0008)
#define POSEIDON_STATE_DISCONNECT	(0x0080)

#define PM_SUSPEND_DELAY	3
+15 −25
Original line number Diff line number Diff line
@@ -1352,12 +1352,14 @@ static int pd_video_open(struct file *file)
	mutex_lock(&pd->lock);
	usb_autopm_get_interface(pd->interface);

	if (vfd->vfl_type == VFL_TYPE_GRABBER
		&& !(pd->state & POSEIDON_STATE_ANALOG)) {
	if (pd->state && !(pd->state & POSEIDON_STATE_ANALOG)) {
		ret = -EBUSY;
		goto out;
	}
	front = kzalloc(sizeof(struct front_face), GFP_KERNEL);
	if (!front)
		goto out;

	if (vfd->vfl_type == VFL_TYPE_GRABBER) {
		pd->cur_transfer_mode	= usb_transfer_mode;/* bulk or iso */
		init_video_context(&pd->video_data.context);

@@ -1368,7 +1370,6 @@ static int pd_video_open(struct file *file)
			goto out;
		}

		pd->state		|= POSEIDON_STATE_ANALOG;
		front->type		= V4L2_BUF_TYPE_VIDEO_CAPTURE;
		pd->video_data.users++;
		set_debug_mode(vfd, debug_mode);
@@ -1379,13 +1380,7 @@ static int pd_video_open(struct file *file)
				V4L2_FIELD_INTERLACED,/* video is interlacd */
				sizeof(struct videobuf_buffer),/*it's enough*/
				front, NULL);
	} else if (vfd->vfl_type == VFL_TYPE_VBI
		&& !(pd->state & POSEIDON_STATE_VBI)) {
		front = kzalloc(sizeof(struct front_face), GFP_KERNEL);
		if (!front)
			goto out;

		pd->state	|= POSEIDON_STATE_VBI;
	} else {
		front->type	= V4L2_BUF_TYPE_VBI_CAPTURE;
		pd->vbi_data.front = front;
		pd->vbi_data.users++;
@@ -1396,13 +1391,9 @@ static int pd_video_open(struct file *file)
				V4L2_FIELD_NONE, /* vbi is NONE mode */
				sizeof(struct videobuf_buffer),
				front, NULL);
	} else {
		/* maybe add FM support here */
		log("other ");
		ret = -EINVAL;
		goto out;
	}

	pd->state |= POSEIDON_STATE_ANALOG;
	front->pd = pd;
	front->curr_frame = NULL;
	INIT_LIST_HEAD(&front->active);
@@ -1429,8 +1420,6 @@ static int pd_video_release(struct file *file)
	mutex_lock(&pd->lock);

	if (front->type	== V4L2_BUF_TYPE_VIDEO_CAPTURE) {
		pd->state &= ~POSEIDON_STATE_ANALOG;

		/* stop the device, and free the URBs */
		usb_transfer_stop(&pd->video_data);
		free_all_urb(&pd->video_data);
@@ -1442,10 +1431,11 @@ static int pd_video_release(struct file *file)
		pd->file_for_stream = NULL;
		pd->video_data.users--;
	} else if (front->type	== V4L2_BUF_TYPE_VBI_CAPTURE) {
		pd->state &= ~POSEIDON_STATE_VBI;
		pd->vbi_data.front = NULL;
		pd->vbi_data.users--;
	}
	if (!pd->vbi_data.users && !pd->video_data.users)
		pd->state &= ~POSEIDON_STATE_ANALOG;
	videobuf_stop(&front->q);
	videobuf_mmap_free(&front->q);