ublk_drv: don't probe partitions if the ubq daemon isn't trusted
authorMing Lei <ming.lei@redhat.com>
Fri, 6 Jan 2023 04:17:07 +0000 (12:17 +0800)
committerJens Axboe <axboe@kernel.dk>
Sun, 29 Jan 2023 22:18:34 +0000 (15:18 -0700)
If any ubq daemon is unprivileged, the ublk char device is allowed
for unprivileged user actually, and we can't trust the current user,
so not probe partitions.

Fixes: 71f28f3136af ("ublk_drv: add io_uring based userspace block driver")
Reviewed-by: ZiyangZhang <ZiyangZhang@linux.alibaba.com>
Signed-off-by: Ming Lei <ming.lei@redhat.com>
Link: https://lore.kernel.org/r/20230106041711.914434-3-ming.lei@redhat.com
Signed-off-by: Jens Axboe <axboe@kernel.dk>
drivers/block/ublk_drv.c

index 4232089e372302e418f9203d62db03a5253d8ac5..8a6f38cc62db2eeb5a8983887cffdab52a6fa5c6 100644 (file)
@@ -159,6 +159,7 @@ struct ublk_device {
 
        struct completion       completion;
        unsigned int            nr_queues_ready;
+       unsigned int            nr_privileged_daemon;
 
        /*
         * Our ubq->daemon may be killed without any notification, so
@@ -1178,6 +1179,9 @@ static void ublk_mark_io_ready(struct ublk_device *ub, struct ublk_queue *ubq)
                ubq->ubq_daemon = current;
                get_task_struct(ubq->ubq_daemon);
                ub->nr_queues_ready++;
+
+               if (capable(CAP_SYS_ADMIN))
+                       ub->nr_privileged_daemon++;
        }
        if (ub->nr_queues_ready == ub->dev_info.nr_hw_queues)
                complete_all(&ub->completion);
@@ -1534,6 +1538,10 @@ static int ublk_ctrl_start_dev(struct io_uring_cmd *cmd)
        if (ret)
                goto out_put_disk;
 
+       /* don't probe partitions if any one ubq daemon is un-trusted */
+       if (ub->nr_privileged_daemon != ub->nr_queues_ready)
+               set_bit(GD_SUPPRESS_PART_SCAN, &disk->state);
+
        get_device(&ub->cdev_dev);
        ret = add_disk(disk);
        if (ret) {
@@ -1935,6 +1943,7 @@ static int ublk_ctrl_start_recovery(struct io_uring_cmd *cmd)
        /* set to NULL, otherwise new ubq_daemon cannot mmap the io_cmd_buf */
        ub->mm = NULL;
        ub->nr_queues_ready = 0;
+       ub->nr_privileged_daemon = 0;
        init_completion(&ub->completion);
        ret = 0;
  out_unlock: