summaryrefslogtreecommitdiff
path: root/drivers/media/pci
diff options
context:
space:
mode:
authorArnd Bergmann <arnd@arndb.de>2018-08-27 15:56:25 -0400
committerMauro Carvalho Chehab <mchehab+samsung@kernel.org>2018-09-12 11:00:51 -0400
commit04b72322e85dd7987085a4d29a29ebc1a5ad5dd2 (patch)
tree0265a01fe624c143df6a4d4355fb6c8bba7b9bb4 /drivers/media/pci
parent8a24280b11ea49ed13d384c7426419201600c3a9 (diff)
media: dvb: move compat handlers into drivers
The VIDEO_STILLPICTURE is only implemented by one driver, while VIDEO_GET_EVENT has two users in tree. In both cases, it is fairly easy to handle the compat ioctls in the native handler rather than relying on translation in fs/compat_ioctls. In effect, this means that now the drivers implement both structure layouts in both native and compat mode, but I don't see anything wrong with that. Signed-off-by: Arnd Bergmann <arnd@arndb.de> Signed-off-by: Mauro Carvalho Chehab <mchehab+samsung@kernel.org>
Diffstat (limited to 'drivers/media/pci')
-rw-r--r--drivers/media/pci/ivtv/ivtv-ioctl.c34
-rw-r--r--drivers/media/pci/ttpci/av7110_av.c56
2 files changed, 87 insertions, 3 deletions
diff --git a/drivers/media/pci/ivtv/ivtv-ioctl.c b/drivers/media/pci/ivtv/ivtv-ioctl.c
index edb85ca9c0c2..a66f8b872520 100644
--- a/drivers/media/pci/ivtv/ivtv-ioctl.c
+++ b/drivers/media/pci/ivtv/ivtv-ioctl.c
@@ -36,6 +36,7 @@
#include <media/tveeprom.h>
#include <media/v4l2-event.h>
#ifdef CONFIG_VIDEO_IVTV_DEPRECATED_IOCTLS
+#include <linux/compat.h>
#include <linux/dvb/audio.h>
#include <linux/dvb/video.h>
#endif
@@ -1627,6 +1628,21 @@ static __inline__ void warn_deprecated_ioctl(const char *name)
pr_warn_once("warning: the %s ioctl is deprecated. Don't use it, as it will be removed soon\n",
name);
}
+
+#ifdef CONFIG_COMPAT
+struct compat_video_event {
+ __s32 type;
+ /* unused, make sure to use atomic time for y2038 if it ever gets used */
+ compat_long_t timestamp;
+ union {
+ video_size_t size;
+ unsigned int frame_rate; /* in frames per 1000sec */
+ unsigned char vsync_field; /* unknown/odd/even/progressive */
+ } u;
+};
+#define VIDEO_GET_EVENT32 _IOR('o', 28, struct compat_video_event)
+#endif
+
#endif
static int ivtv_decoder_ioctls(struct file *filp, unsigned int cmd, void *arg)
@@ -1749,7 +1765,13 @@ static int ivtv_decoder_ioctls(struct file *filp, unsigned int cmd, void *arg)
return ivtv_video_command(itv, id, dc, try);
}
+#ifdef CONFIG_COMPAT
+ case VIDEO_GET_EVENT32:
+#endif
case VIDEO_GET_EVENT: {
+#ifdef CONFIG_COMPAT
+ struct compat_video_event *ev32 = arg;
+#endif
struct video_event *ev = arg;
DEFINE_WAIT(wait);
@@ -1763,14 +1785,22 @@ static int ivtv_decoder_ioctls(struct file *filp, unsigned int cmd, void *arg)
if (test_and_clear_bit(IVTV_F_I_EV_DEC_STOPPED, &itv->i_flags))
ev->type = VIDEO_EVENT_DECODER_STOPPED;
else if (test_and_clear_bit(IVTV_F_I_EV_VSYNC, &itv->i_flags)) {
+ unsigned char vsync_field;
+
ev->type = VIDEO_EVENT_VSYNC;
- ev->u.vsync_field = test_bit(IVTV_F_I_EV_VSYNC_FIELD, &itv->i_flags) ?
+ vsync_field = test_bit(IVTV_F_I_EV_VSYNC_FIELD, &itv->i_flags) ?
VIDEO_VSYNC_FIELD_ODD : VIDEO_VSYNC_FIELD_EVEN;
if (itv->output_mode == OUT_UDMA_YUV &&
(itv->yuv_info.lace_mode & IVTV_YUV_MODE_MASK) ==
IVTV_YUV_MODE_PROGRESSIVE) {
- ev->u.vsync_field = VIDEO_VSYNC_FIELD_PROGRESSIVE;
+ vsync_field = VIDEO_VSYNC_FIELD_PROGRESSIVE;
}
+#ifdef CONFIG_COMPAT
+ if (cmd == VIDEO_GET_EVENT32)
+ ev32->u.vsync_field = vsync_field;
+ else
+#endif
+ ev->u.vsync_field = vsync_field;
}
if (ev->type)
return 0;
diff --git a/drivers/media/pci/ttpci/av7110_av.c b/drivers/media/pci/ttpci/av7110_av.c
index e738b2cef6f6..1073e4671b68 100644
--- a/drivers/media/pci/ttpci/av7110_av.c
+++ b/drivers/media/pci/ttpci/av7110_av.c
@@ -932,7 +932,6 @@ static int dvb_video_get_event (struct av7110 *av7110, struct video_event *event
return 0;
}
-
/******************************************************************************
* DVB device file operations
******************************************************************************/
@@ -1095,6 +1094,42 @@ static int play_iframe(struct av7110 *av7110, char __user *buf, unsigned int len
return 0;
}
+#ifdef CONFIG_COMPAT
+struct compat_video_still_picture {
+ compat_uptr_t iFrame;
+ int32_t size;
+};
+#define VIDEO_STILLPICTURE32 _IOW('o', 30, struct compat_video_still_picture)
+
+struct compat_video_event {
+ __s32 type;
+ /* unused, make sure to use atomic time for y2038 if it ever gets used */
+ compat_long_t timestamp;
+ union {
+ video_size_t size;
+ unsigned int frame_rate; /* in frames per 1000sec */
+ unsigned char vsync_field; /* unknown/odd/even/progressive */
+ } u;
+};
+#define VIDEO_GET_EVENT32 _IOR('o', 28, struct compat_video_event)
+
+static int dvb_compat_video_get_event(struct av7110 *av7110,
+ struct compat_video_event *event, int flags)
+{
+ struct video_event ev;
+ int ret;
+
+ ret = dvb_video_get_event(av7110, &ev, flags);
+
+ *event = (struct compat_video_event) {
+ .type = ev.type,
+ .timestamp = ev.timestamp,
+ .u.size = ev.u.size,
+ };
+
+ return ret;
+}
+#endif
static int dvb_video_ioctl(struct file *file,
unsigned int cmd, void *parg)
@@ -1184,6 +1219,12 @@ static int dvb_video_ioctl(struct file *file,
memcpy(parg, &av7110->videostate, sizeof(struct video_status));
break;
+#ifdef CONFIG_COMPAT
+ case VIDEO_GET_EVENT32:
+ ret = dvb_compat_video_get_event(av7110, parg, file->f_flags);
+ break;
+#endif
+
case VIDEO_GET_EVENT:
ret = dvb_video_get_event(av7110, parg, file->f_flags);
break;
@@ -1226,6 +1267,19 @@ static int dvb_video_ioctl(struct file *file,
1, (u16) arg);
break;
+#ifdef CONFIG_COMPAT
+ case VIDEO_STILLPICTURE32:
+ {
+ struct compat_video_still_picture *pic =
+ (struct compat_video_still_picture *) parg;
+ av7110->videostate.stream_source = VIDEO_SOURCE_MEMORY;
+ dvb_ringbuffer_flush_spinlock_wakeup(&av7110->avout);
+ ret = play_iframe(av7110, compat_ptr(pic->iFrame),
+ pic->size, file->f_flags & O_NONBLOCK);
+ break;
+ }
+#endif
+
case VIDEO_STILLPICTURE:
{
struct video_still_picture *pic =