dm.c (4328daa2e79ed904a42ce00a9f38b9c36b44b21a) dm.c (664820265d70a759dceca87b6eb200cd2b93cda8)
1/*
2 * Copyright (C) 2001, 2002 Sistina Software (UK) Limited.
3 * Copyright (C) 2004-2008 Red Hat, Inc. All rights reserved.
4 *
5 * This file is released under the GPL.
6 */
7
8#include "dm.h"

--- 543 unchanged lines hidden (view full) ---

552static int dm_blk_getgeo(struct block_device *bdev, struct hd_geometry *geo)
553{
554 struct mapped_device *md = bdev->bd_disk->private_data;
555
556 return dm_get_geometry(md, geo);
557}
558
559static int dm_get_live_table_for_ioctl(struct mapped_device *md,
1/*
2 * Copyright (C) 2001, 2002 Sistina Software (UK) Limited.
3 * Copyright (C) 2004-2008 Red Hat, Inc. All rights reserved.
4 *
5 * This file is released under the GPL.
6 */
7
8#include "dm.h"

--- 543 unchanged lines hidden (view full) ---

552static int dm_blk_getgeo(struct block_device *bdev, struct hd_geometry *geo)
553{
554 struct mapped_device *md = bdev->bd_disk->private_data;
555
556 return dm_get_geometry(md, geo);
557}
558
559static int dm_get_live_table_for_ioctl(struct mapped_device *md,
560 struct dm_target **tgt, struct block_device **bdev,
561 fmode_t *mode, int *srcu_idx)
560 struct block_device **bdev,
561 fmode_t *mode, int *srcu_idx)
562{
562{
563 struct dm_target *tgt;
563 struct dm_table *map;
564 int r;
565
566retry:
567 r = -ENOTTY;
568 map = dm_get_live_table(md, srcu_idx);
569 if (!map || !dm_table_get_size(map))
570 goto out;
571
572 /* We only support devices that have a single target */
573 if (dm_table_get_num_targets(map) != 1)
574 goto out;
575
564 struct dm_table *map;
565 int r;
566
567retry:
568 r = -ENOTTY;
569 map = dm_get_live_table(md, srcu_idx);
570 if (!map || !dm_table_get_size(map))
571 goto out;
572
573 /* We only support devices that have a single target */
574 if (dm_table_get_num_targets(map) != 1)
575 goto out;
576
576 *tgt = dm_table_get_target(map, 0);
577
578 if (!(*tgt)->type->prepare_ioctl)
577 tgt = dm_table_get_target(map, 0);
578 if (!tgt->type->prepare_ioctl)
579 goto out;
580
581 if (dm_suspended_md(md)) {
582 r = -EAGAIN;
583 goto out;
584 }
585
579 goto out;
580
581 if (dm_suspended_md(md)) {
582 r = -EAGAIN;
583 goto out;
584 }
585
586 r = (*tgt)->type->prepare_ioctl(*tgt, bdev, mode);
586 r = tgt->type->prepare_ioctl(tgt, bdev, mode);
587 if (r < 0)
588 goto out;
589
590 return r;
591
592out:
593 dm_put_live_table(md, *srcu_idx);
594 if (r == -ENOTCONN && !fatal_signal_pending(current)) {
595 msleep(10);
596 goto retry;
597 }
598 return r;
599}
600
601static int dm_blk_ioctl(struct block_device *bdev, fmode_t mode,
602 unsigned int cmd, unsigned long arg)
603{
604 struct mapped_device *md = bdev->bd_disk->private_data;
587 if (r < 0)
588 goto out;
589
590 return r;
591
592out:
593 dm_put_live_table(md, *srcu_idx);
594 if (r == -ENOTCONN && !fatal_signal_pending(current)) {
595 msleep(10);
596 goto retry;
597 }
598 return r;
599}
600
601static int dm_blk_ioctl(struct block_device *bdev, fmode_t mode,
602 unsigned int cmd, unsigned long arg)
603{
604 struct mapped_device *md = bdev->bd_disk->private_data;
605 struct dm_target *tgt;
606 struct block_device *tgt_bdev = NULL;
607 int srcu_idx, r;
608
605 int srcu_idx, r;
606
609 r = dm_get_live_table_for_ioctl(md, &tgt, &tgt_bdev, &mode, &srcu_idx);
607 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
610 if (r < 0)
611 return r;
612
613 if (r > 0) {
614 /*
615 * Target determined this ioctl is being issued against
616 * a logical partition of the parent bdev; so extra
617 * validation is needed.
618 */
619 r = scsi_verify_blk_ioctl(NULL, cmd);
620 if (r)
621 goto out;
622 }
623
608 if (r < 0)
609 return r;
610
611 if (r > 0) {
612 /*
613 * Target determined this ioctl is being issued against
614 * a logical partition of the parent bdev; so extra
615 * validation is needed.
616 */
617 r = scsi_verify_blk_ioctl(NULL, cmd);
618 if (r)
619 goto out;
620 }
621
624 r = __blkdev_driver_ioctl(tgt_bdev, mode, cmd, arg);
622 r = __blkdev_driver_ioctl(bdev, mode, cmd, arg);
625out:
626 dm_put_live_table(md, srcu_idx);
627 return r;
628}
629
630static struct dm_io *alloc_io(struct mapped_device *md)
631{
632 return mempool_alloc(md->io_pool, GFP_NOIO);

--- 2920 unchanged lines hidden (view full) ---

3553 kfree(pools);
3554}
3555
3556static int dm_pr_register(struct block_device *bdev, u64 old_key, u64 new_key,
3557 u32 flags)
3558{
3559 struct mapped_device *md = bdev->bd_disk->private_data;
3560 const struct pr_ops *ops;
623out:
624 dm_put_live_table(md, srcu_idx);
625 return r;
626}
627
628static struct dm_io *alloc_io(struct mapped_device *md)
629{
630 return mempool_alloc(md->io_pool, GFP_NOIO);

--- 2920 unchanged lines hidden (view full) ---

3551 kfree(pools);
3552}
3553
3554static int dm_pr_register(struct block_device *bdev, u64 old_key, u64 new_key,
3555 u32 flags)
3556{
3557 struct mapped_device *md = bdev->bd_disk->private_data;
3558 const struct pr_ops *ops;
3561 struct dm_target *tgt;
3562 fmode_t mode;
3563 int srcu_idx, r;
3564
3559 fmode_t mode;
3560 int srcu_idx, r;
3561
3565 r = dm_get_live_table_for_ioctl(md, &tgt, &bdev, &mode, &srcu_idx);
3562 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
3566 if (r < 0)
3567 return r;
3568
3569 ops = bdev->bd_disk->fops->pr_ops;
3570 if (ops && ops->pr_register)
3571 r = ops->pr_register(bdev, old_key, new_key, flags);
3572 else
3573 r = -EOPNOTSUPP;
3574
3575 dm_put_live_table(md, srcu_idx);
3576 return r;
3577}
3578
3579static int dm_pr_reserve(struct block_device *bdev, u64 key, enum pr_type type,
3580 u32 flags)
3581{
3582 struct mapped_device *md = bdev->bd_disk->private_data;
3583 const struct pr_ops *ops;
3563 if (r < 0)
3564 return r;
3565
3566 ops = bdev->bd_disk->fops->pr_ops;
3567 if (ops && ops->pr_register)
3568 r = ops->pr_register(bdev, old_key, new_key, flags);
3569 else
3570 r = -EOPNOTSUPP;
3571
3572 dm_put_live_table(md, srcu_idx);
3573 return r;
3574}
3575
3576static int dm_pr_reserve(struct block_device *bdev, u64 key, enum pr_type type,
3577 u32 flags)
3578{
3579 struct mapped_device *md = bdev->bd_disk->private_data;
3580 const struct pr_ops *ops;
3584 struct dm_target *tgt;
3585 fmode_t mode;
3586 int srcu_idx, r;
3587
3581 fmode_t mode;
3582 int srcu_idx, r;
3583
3588 r = dm_get_live_table_for_ioctl(md, &tgt, &bdev, &mode, &srcu_idx);
3584 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
3589 if (r < 0)
3590 return r;
3591
3592 ops = bdev->bd_disk->fops->pr_ops;
3593 if (ops && ops->pr_reserve)
3594 r = ops->pr_reserve(bdev, key, type, flags);
3595 else
3596 r = -EOPNOTSUPP;
3597
3598 dm_put_live_table(md, srcu_idx);
3599 return r;
3600}
3601
3602static int dm_pr_release(struct block_device *bdev, u64 key, enum pr_type type)
3603{
3604 struct mapped_device *md = bdev->bd_disk->private_data;
3605 const struct pr_ops *ops;
3585 if (r < 0)
3586 return r;
3587
3588 ops = bdev->bd_disk->fops->pr_ops;
3589 if (ops && ops->pr_reserve)
3590 r = ops->pr_reserve(bdev, key, type, flags);
3591 else
3592 r = -EOPNOTSUPP;
3593
3594 dm_put_live_table(md, srcu_idx);
3595 return r;
3596}
3597
3598static int dm_pr_release(struct block_device *bdev, u64 key, enum pr_type type)
3599{
3600 struct mapped_device *md = bdev->bd_disk->private_data;
3601 const struct pr_ops *ops;
3606 struct dm_target *tgt;
3607 fmode_t mode;
3608 int srcu_idx, r;
3609
3602 fmode_t mode;
3603 int srcu_idx, r;
3604
3610 r = dm_get_live_table_for_ioctl(md, &tgt, &bdev, &mode, &srcu_idx);
3605 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
3611 if (r < 0)
3612 return r;
3613
3614 ops = bdev->bd_disk->fops->pr_ops;
3615 if (ops && ops->pr_release)
3616 r = ops->pr_release(bdev, key, type);
3617 else
3618 r = -EOPNOTSUPP;
3619
3620 dm_put_live_table(md, srcu_idx);
3621 return r;
3622}
3623
3624static int dm_pr_preempt(struct block_device *bdev, u64 old_key, u64 new_key,
3625 enum pr_type type, bool abort)
3626{
3627 struct mapped_device *md = bdev->bd_disk->private_data;
3628 const struct pr_ops *ops;
3606 if (r < 0)
3607 return r;
3608
3609 ops = bdev->bd_disk->fops->pr_ops;
3610 if (ops && ops->pr_release)
3611 r = ops->pr_release(bdev, key, type);
3612 else
3613 r = -EOPNOTSUPP;
3614
3615 dm_put_live_table(md, srcu_idx);
3616 return r;
3617}
3618
3619static int dm_pr_preempt(struct block_device *bdev, u64 old_key, u64 new_key,
3620 enum pr_type type, bool abort)
3621{
3622 struct mapped_device *md = bdev->bd_disk->private_data;
3623 const struct pr_ops *ops;
3629 struct dm_target *tgt;
3630 fmode_t mode;
3631 int srcu_idx, r;
3632
3624 fmode_t mode;
3625 int srcu_idx, r;
3626
3633 r = dm_get_live_table_for_ioctl(md, &tgt, &bdev, &mode, &srcu_idx);
3627 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
3634 if (r < 0)
3635 return r;
3636
3637 ops = bdev->bd_disk->fops->pr_ops;
3638 if (ops && ops->pr_preempt)
3639 r = ops->pr_preempt(bdev, old_key, new_key, type, abort);
3640 else
3641 r = -EOPNOTSUPP;
3642
3643 dm_put_live_table(md, srcu_idx);
3644 return r;
3645}
3646
3647static int dm_pr_clear(struct block_device *bdev, u64 key)
3648{
3649 struct mapped_device *md = bdev->bd_disk->private_data;
3650 const struct pr_ops *ops;
3628 if (r < 0)
3629 return r;
3630
3631 ops = bdev->bd_disk->fops->pr_ops;
3632 if (ops && ops->pr_preempt)
3633 r = ops->pr_preempt(bdev, old_key, new_key, type, abort);
3634 else
3635 r = -EOPNOTSUPP;
3636
3637 dm_put_live_table(md, srcu_idx);
3638 return r;
3639}
3640
3641static int dm_pr_clear(struct block_device *bdev, u64 key)
3642{
3643 struct mapped_device *md = bdev->bd_disk->private_data;
3644 const struct pr_ops *ops;
3651 struct dm_target *tgt;
3652 fmode_t mode;
3653 int srcu_idx, r;
3654
3645 fmode_t mode;
3646 int srcu_idx, r;
3647
3655 r = dm_get_live_table_for_ioctl(md, &tgt, &bdev, &mode, &srcu_idx);
3648 r = dm_get_live_table_for_ioctl(md, &bdev, &mode, &srcu_idx);
3656 if (r < 0)
3657 return r;
3658
3659 ops = bdev->bd_disk->fops->pr_ops;
3660 if (ops && ops->pr_clear)
3661 r = ops->pr_clear(bdev, key);
3662 else
3663 r = -EOPNOTSUPP;

--- 43 unchanged lines hidden ---
3649 if (r < 0)
3650 return r;
3651
3652 ops = bdev->bd_disk->fops->pr_ops;
3653 if (ops && ops->pr_clear)
3654 r = ops->pr_clear(bdev, key);
3655 else
3656 r = -EOPNOTSUPP;

--- 43 unchanged lines hidden ---