Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 277115
b: refs/heads/master
c: 07d106d
h: refs/heads/master
i:
  277113: 91663cf
  277111: 3dd0289
v: v3
  • Loading branch information
Linus Torvalds committed Jan 5, 2012
1 parent ad3be31 commit 58269e7
Show file tree
Hide file tree
Showing 5 changed files with 27 additions and 57 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 805a6af8dba5dfdd35ec35dc52ec0122400b2610
refs/heads/master: 07d106d0a33d6063d2061305903deb02489eba20
26 changes: 22 additions & 4 deletions trunk/block/ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,26 @@ int __blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode,
*/
EXPORT_SYMBOL_GPL(__blkdev_driver_ioctl);

/*
* Is it an unrecognized ioctl? The correct returns are either
* ENOTTY (final) or ENOIOCTLCMD ("I don't know this one, try a
* fallback"). ENOIOCTLCMD gets turned into ENOTTY by the ioctl
* code before returning.
*
* Confused drivers sometimes return EINVAL, which is wrong. It
* means "I understood the ioctl command, but the parameters to
* it were wrong".
*
* We should aim to just fix the broken drivers, the EINVAL case
* should go away.
*/
static inline int is_unrecognized_ioctl(int ret)
{
return ret == -EINVAL ||
ret == -ENOTTY ||
ret == -ENOIOCTLCMD;
}

/*
* always keep this in sync with compat_blkdev_ioctl()
*/
Expand All @@ -196,8 +216,7 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd,
return -EACCES;

ret = __blkdev_driver_ioctl(bdev, mode, cmd, arg);
/* -EINVAL to handle old uncorrected drivers */
if (ret != -EINVAL && ret != -ENOTTY)
if (!is_unrecognized_ioctl(ret))
return ret;

fsync_bdev(bdev);
Expand All @@ -206,8 +225,7 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd,

case BLKROSET:
ret = __blkdev_driver_ioctl(bdev, mode, cmd, arg);
/* -EINVAL to handle old uncorrected drivers */
if (ret != -EINVAL && ret != -ENOTTY)
if (!is_unrecognized_ioctl(ret))
return ret;
if (!capable(CAP_SYS_ADMIN))
return -EACCES;
Expand Down
38 changes: 2 additions & 36 deletions trunk/fs/compat_ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -1506,35 +1506,6 @@ static long do_ioctl_trans(int fd, unsigned int cmd,
return -ENOIOCTLCMD;
}

static void compat_ioctl_error(struct file *filp, unsigned int fd,
unsigned int cmd, unsigned long arg)
{
char buf[10];
char *fn = "?";
char *path;

/* find the name of the device. */
path = (char *)__get_free_page(GFP_KERNEL);
if (path) {
fn = d_path(&filp->f_path, path, PAGE_SIZE);
if (IS_ERR(fn))
fn = "?";
}

sprintf(buf,"'%c'", (cmd>>_IOC_TYPESHIFT) & _IOC_TYPEMASK);
if (!isprint(buf[1]))
sprintf(buf, "%02x", buf[1]);
compat_printk("ioctl32(%s:%d): Unknown cmd fd(%d) "
"cmd(%08x){t:%s;sz:%u} arg(%08x) on %s\n",
current->comm, current->pid,
(int)fd, (unsigned int)cmd, buf,
(cmd >> _IOC_SIZESHIFT) & _IOC_SIZEMASK,
(unsigned int)arg, fn);

if (path)
free_page((unsigned long)path);
}

static int compat_ioctl_check_table(unsigned int xcmd)
{
int i;
Expand Down Expand Up @@ -1621,13 +1592,8 @@ asmlinkage long compat_sys_ioctl(unsigned int fd, unsigned int cmd,
goto found_handler;

error = do_ioctl_trans(fd, cmd, arg, filp);
if (error == -ENOIOCTLCMD) {
static int count;

if (++count <= 50)
compat_ioctl_error(filp, fd, cmd, arg);
error = -EINVAL;
}
if (error == -ENOIOCTLCMD)
error = -ENOTTY;

goto out_fput;

Expand Down
2 changes: 1 addition & 1 deletion trunk/fs/ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ static long vfs_ioctl(struct file *filp, unsigned int cmd,

error = filp->f_op->unlocked_ioctl(filp, cmd, arg);
if (error == -ENOIOCTLCMD)
error = -EINVAL;
error = -ENOTTY;
out:
return error;
}
Expand Down
16 changes: 1 addition & 15 deletions trunk/net/socket.c
Original file line number Diff line number Diff line change
Expand Up @@ -2883,7 +2883,7 @@ static int bond_ioctl(struct net *net, unsigned int cmd,

return dev_ioctl(net, cmd, uifr);
default:
return -EINVAL;
return -ENOIOCTLCMD;
}
}

Expand Down Expand Up @@ -3210,20 +3210,6 @@ static int compat_sock_ioctl_trans(struct file *file, struct socket *sock,
return sock_do_ioctl(net, sock, cmd, arg);
}

/* Prevent warning from compat_sys_ioctl, these always
* result in -EINVAL in the native case anyway. */
switch (cmd) {
case SIOCRTMSG:
case SIOCGIFCOUNT:
case SIOCSRARP:
case SIOCGRARP:
case SIOCDRARP:
case SIOCSIFLINK:
case SIOCGIFSLAVE:
case SIOCSIFSLAVE:
return -EINVAL;
}

return -ENOIOCTLCMD;
}

Expand Down

0 comments on commit 58269e7

Please sign in to comment.