summaryrefslogtreecommitdiffstats
path: root/block/blk-mq-debugfs.c
diff options
context:
space:
mode:
authorOmar Sandoval <osandov@fb.com>2017-05-04 00:31:25 -0700
committerJens Axboe <axboe@fb.com>2017-05-04 08:23:16 -0600
commitc7e4145ae11b45931f117aa64c26be6cf58302df (patch)
treedd19aadf9aeca8a7ea558c8de30e9f02e21e8aff /block/blk-mq-debugfs.c
parent1a435111f8eb30b370e3891caebb1d1ca61f41ec (diff)
downloadlinux-0-day-c7e4145ae11b45931f117aa64c26be6cf58302df.tar.gz
linux-0-day-c7e4145ae11b45931f117aa64c26be6cf58302df.tar.xz
blk-mq-debugfs: error on long write to queue "state" file
blk_queue_flags_store() currently truncates and returns a short write if the operation being written is too long. This can give us weird results, like here: $ echo "run bar" echo: write error: invalid argument $ dmesg [ 1103.075435] blk_queue_flags_store: unsupported operation bar. Use either 'run' or 'start' Instead, return an error if the user does this. While we're here, make the argument names consistent with everywhere else in this file. Signed-off-by: Omar Sandoval <osandov@fb.com> Reviewed-by: Hannes Reinecke <hare@suse.com> Signed-off-by: Jens Axboe <axboe@fb.com>
Diffstat (limited to 'block/blk-mq-debugfs.c')
-rw-r--r--block/blk-mq-debugfs.c19
1 files changed, 12 insertions, 7 deletions
diff --git a/block/blk-mq-debugfs.c b/block/blk-mq-debugfs.c
index f58a116d6cca2..2a19237455d4a 100644
--- a/block/blk-mq-debugfs.c
+++ b/block/blk-mq-debugfs.c
@@ -107,14 +107,18 @@ static int blk_queue_flags_show(struct seq_file *m, void *v)
return 0;
}
-static ssize_t blk_queue_flags_store(struct file *file, const char __user *ubuf,
- size_t len, loff_t *offp)
+static ssize_t blk_queue_flags_store(struct file *file, const char __user *buf,
+ size_t count, loff_t *ppos)
{
struct request_queue *q = file_inode(file)->i_private;
char op[16] = { }, *s;
- len = min(len, sizeof(op) - 1);
- if (copy_from_user(op, ubuf, len))
+ if (count >= sizeof(op)) {
+ pr_err("%s: operation too long\n", __func__);
+ goto inval;
+ }
+
+ if (copy_from_user(op, buf, count))
return -EFAULT;
s = op;
strsep(&s, " \t\n"); /* strip trailing whitespace */
@@ -123,11 +127,12 @@ static ssize_t blk_queue_flags_store(struct file *file, const char __user *ubuf,
} else if (strcmp(op, "start") == 0) {
blk_mq_start_stopped_hw_queues(q, true);
} else {
- pr_err("%s: unsupported operation %s. Use either 'run' or 'start'\n",
- __func__, op);
+ pr_err("%s: unsupported operation '%s'\n", __func__, op);
+inval:
+ pr_err("%s: use either 'run' or 'start'\n", __func__);
return -EINVAL;
}
- return len;
+ return count;
}
static int blk_queue_flags_open(struct inode *inode, struct file *file)