On Mon, Nov 05, 2007, Johannes Stezenbach wrote:
> 
> Of course you can have variable length args to ioctl(). It's
> just that you can't let dvb_usercopy() do the work anymore but
> have to call copy_from_user() yourself, but I would favor a simple,
> generic API anytime over one with unnecessary, arbitrary
> limits, so IMHO it's worth the little extra effort.
> 
> #define DVB_TUNE _IOC(_IOC_WRITE,'o',82,0)
> 
> plus

Here's a better patch, still untested but without
obvious bugs, I hope ;-) :

diff -r 1acfe4149714 linux/drivers/media/dvb/dvb-core/dvbdev.c
--- a/linux/drivers/media/dvb/dvb-core/dvbdev.c Mon Nov 05 10:30:39 2007 -0200
+++ b/linux/drivers/media/dvb/dvb-core/dvbdev.c Mon Nov 05 18:41:43 2007 +0100
@@ -362,9 +362,11 @@ int dvb_usercopy(struct inode *inode, st
        case _IOC_READ: /* some v4l ioctls are marked wrong ... */
        case _IOC_WRITE:
        case (_IOC_WRITE | _IOC_READ):
-               if (_IOC_SIZE(cmd) <= sizeof(sbuf)) {
+               if (_IOC_SIZE(cmd) == 0)
+                       parg = arg;
+               else if (_IOC_SIZE(cmd) <= sizeof(sbuf))
                        parg = sbuf;
-               } else {
+               else {
                        /* too big to allocate from stack */
                        mbuf = kmalloc(_IOC_SIZE(cmd),GFP_KERNEL);
                        if (NULL == mbuf)
@@ -373,7 +375,7 @@ int dvb_usercopy(struct inode *inode, st
                }
 
                err = -EFAULT;
-               if (copy_from_user(parg, (void __user *)arg, _IOC_SIZE(cmd)))
+               if (_IOC_SIZE(cmd) && copy_from_user(parg, (void __user *)arg, 
_IOC_SIZE(cmd)))
                        goto out;
                break;
        }
@@ -390,7 +392,7 @@ int dvb_usercopy(struct inode *inode, st
        {
        case _IOC_READ:
        case (_IOC_WRITE | _IOC_READ):
-               if (copy_to_user((void __user *)arg, parg, _IOC_SIZE(cmd)))
+               if (_IOC_SIZE(cmd) && copy_to_user((void __user *)arg, parg, 
_IOC_SIZE(cmd)))
                        err = -EFAULT;
                break;
        }


Johannes

_______________________________________________
linux-dvb mailing list
linux-dvb@linuxtv.org
http://www.linuxtv.org/cgi-bin/mailman/listinfo/linux-dvb

Reply via email to