summaryrefslogtreecommitdiffstats
path: root/drivers/block/rbd.c
diff options
context:
space:
mode:
authorAlex Elder <elder@inktank.com>2013-04-26 16:44:36 -0400
committerSage Weil <sage@inktank.com>2013-05-02 00:19:49 -0400
commit124afba25d58e2b52d7d4bad993065572a28d57f (patch)
tree3384e0905f24cee6dc06c04df25fa096e5ea49bb /drivers/block/rbd.c
parentb5156e76da01c23e14e962594553f1735b1db298 (diff)
rbd: encapsulate probing for parent devices
Encapsulate the code that probes for an rbd device's parent images into a new function, rbd_dev_probe_parent(). Signed-off-by: Alex Elder <elder@inktank.com> Reviewed-by: Josh Durgin <josh.durgin@inktank.com>
Diffstat (limited to 'drivers/block/rbd.c')
-rw-r--r--drivers/block/rbd.c82
1 files changed, 44 insertions, 38 deletions
diff --git a/drivers/block/rbd.c b/drivers/block/rbd.c
index b6024a2d7b86..c80fc1a3a604 100644
--- a/drivers/block/rbd.c
+++ b/drivers/block/rbd.c
@@ -4702,11 +4702,49 @@ out_err:
4702 return ret; 4702 return ret;
4703} 4703}
4704 4704
4705static int rbd_dev_probe_finish(struct rbd_device *rbd_dev) 4705static int rbd_dev_probe_parent(struct rbd_device *rbd_dev)
4706{ 4706{
4707 struct rbd_device *parent = NULL; 4707 struct rbd_device *parent = NULL;
4708 struct rbd_spec *parent_spec = NULL; 4708 struct rbd_spec *parent_spec;
4709 struct rbd_client *rbdc = NULL; 4709 struct rbd_client *rbdc;
4710 int ret;
4711
4712 if (!rbd_dev->parent_spec)
4713 return 0;
4714 /*
4715 * We need to pass a reference to the client and the parent
4716 * spec when creating the parent rbd_dev. Images related by
4717 * parent/child relationships always share both.
4718 */
4719 parent_spec = rbd_spec_get(rbd_dev->parent_spec);
4720 rbdc = __rbd_get_client(rbd_dev->rbd_client);
4721
4722 ret = -ENOMEM;
4723 parent = rbd_dev_create(rbdc, parent_spec);
4724 if (!parent)
4725 goto out_err;
4726
4727 ret = rbd_dev_image_probe(parent);
4728 if (ret < 0)
4729 goto out_err;
4730 rbd_dev->parent = parent;
4731
4732 return 0;
4733out_err:
4734 if (parent) {
4735 rbd_spec_put(rbd_dev->parent_spec);
4736 kfree(rbd_dev->header_name);
4737 rbd_dev_destroy(parent);
4738 } else {
4739 rbd_put_client(rbdc);
4740 rbd_spec_put(parent_spec);
4741 }
4742
4743 return ret;
4744}
4745
4746static int rbd_dev_probe_finish(struct rbd_device *rbd_dev)
4747{
4710 int ret; 4748 int ret;
4711 4749
4712 /* no need to lock here, as rbd_dev is not registered yet */ 4750 /* no need to lock here, as rbd_dev is not registered yet */
@@ -4747,34 +4785,9 @@ static int rbd_dev_probe_finish(struct rbd_device *rbd_dev)
4747 if (ret) 4785 if (ret)
4748 goto err_out_disk; 4786 goto err_out_disk;
4749 4787
4750 /* 4788 ret = rbd_dev_probe_parent(rbd_dev);
4751 * At this point cleanup in the event of an error is the job 4789 if (ret)
4752 * of the sysfs code (initiated by rbd_bus_del_dev()). 4790 goto err_out_bus;
4753 */
4754 /* Probe the parent if there is one */
4755
4756 if (rbd_dev->parent_spec) {
4757 /*
4758 * We need to pass a reference to the client and the
4759 * parent spec when creating the parent rbd_dev.
4760 * Images related by parent/child relationships
4761 * always share both.
4762 */
4763 parent_spec = rbd_spec_get(rbd_dev->parent_spec);
4764 rbdc = __rbd_get_client(rbd_dev->rbd_client);
4765
4766 parent = rbd_dev_create(rbdc, parent_spec);
4767 if (!parent) {
4768 ret = -ENOMEM;
4769 goto err_out_spec;
4770 }
4771 rbdc = NULL; /* parent now owns reference */
4772 parent_spec = NULL; /* parent now owns reference */
4773 ret = rbd_dev_image_probe(parent);
4774 if (ret < 0)
4775 goto err_out_parent;
4776 rbd_dev->parent = parent;
4777 }
4778 4791
4779 ret = rbd_dev_header_watch_sync(rbd_dev, 1); 4792 ret = rbd_dev_header_watch_sync(rbd_dev, 1);
4780 if (ret) 4793 if (ret)
@@ -4791,13 +4804,6 @@ static int rbd_dev_probe_finish(struct rbd_device *rbd_dev)
4791 4804
4792 return ret; 4805 return ret;
4793 4806
4794err_out_parent:
4795 rbd_spec_put(rbd_dev->parent_spec);
4796 kfree(rbd_dev->header_name);
4797 rbd_dev_destroy(parent);
4798err_out_spec:
4799 rbd_spec_put(parent_spec);
4800 rbd_put_client(rbdc);
4801err_out_bus: 4807err_out_bus:
4802 /* this will also clean up rest of rbd_dev stuff */ 4808 /* this will also clean up rest of rbd_dev stuff */
4803 4809