diff options
author | Christoph Hellwig <hch@lst.de> | 2015-04-08 14:01:35 -0400 |
---|---|---|
committer | Nicholas Bellinger <nab@linux-iscsi.org> | 2015-04-14 15:28:41 -0400 |
commit | 9ac8928e6a3e1ed02e632e45aa766129fe6b1802 (patch) | |
tree | ea516680cc5f811df862966bb43cfbe3e34dfb26 /drivers/vhost/scsi.c | |
parent | 2c336e3a2e1728d9b3116422655832184dc7046c (diff) |
target: simplify the target template registration API
Instead of calling target_fabric_configfs_init() +
target_fabric_configfs_register() / target_fabric_configfs_deregister()
target_fabric_configfs_free() from every target driver, rewrite the API
so that we have simple register/unregister functions that operate on
a const operations vector.
This patch also fixes a memory leak in several target drivers. Several
target drivers namely called target_fabric_configfs_deregister()
without calling target_fabric_configfs_free().
A large part of this patch is based on earlier changes from
Bart Van Assche <bart.vanassche@sandisk.com>.
(v2: Add a new TF_CIT_SETUP_DRV macro so that the core configfs code
can declare attributes as either core only or for drivers)
Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
Diffstat (limited to 'drivers/vhost/scsi.c')
-rw-r--r-- | drivers/vhost/scsi.c | 76 |
1 files changed, 13 insertions, 63 deletions
diff --git a/drivers/vhost/scsi.c b/drivers/vhost/scsi.c index 27ed9642cc21..e8c88b453f79 100644 --- a/drivers/vhost/scsi.c +++ b/drivers/vhost/scsi.c | |||
@@ -216,9 +216,7 @@ struct vhost_scsi { | |||
216 | int vs_events_nr; /* num of pending events, protected by vq->mutex */ | 216 | int vs_events_nr; /* num of pending events, protected by vq->mutex */ |
217 | }; | 217 | }; |
218 | 218 | ||
219 | /* Local pointer to allocated TCM configfs fabric module */ | 219 | static struct target_core_fabric_ops vhost_scsi_ops; |
220 | static struct target_fabric_configfs *vhost_scsi_fabric_configfs; | ||
221 | |||
222 | static struct workqueue_struct *vhost_scsi_workqueue; | 220 | static struct workqueue_struct *vhost_scsi_workqueue; |
223 | 221 | ||
224 | /* Global spinlock to protect vhost_scsi TPG list for vhost IOCTL access */ | 222 | /* Global spinlock to protect vhost_scsi TPG list for vhost IOCTL access */ |
@@ -2205,7 +2203,7 @@ vhost_scsi_make_tpg(struct se_wwn *wwn, | |||
2205 | tpg->tport = tport; | 2203 | tpg->tport = tport; |
2206 | tpg->tport_tpgt = tpgt; | 2204 | tpg->tport_tpgt = tpgt; |
2207 | 2205 | ||
2208 | ret = core_tpg_register(&vhost_scsi_fabric_configfs->tf_ops, wwn, | 2206 | ret = core_tpg_register(&vhost_scsi_ops, wwn, |
2209 | &tpg->se_tpg, tpg, TRANSPORT_TPG_TYPE_NORMAL); | 2207 | &tpg->se_tpg, tpg, TRANSPORT_TPG_TYPE_NORMAL); |
2210 | if (ret < 0) { | 2208 | if (ret < 0) { |
2211 | kfree(tpg); | 2209 | kfree(tpg); |
@@ -2327,6 +2325,8 @@ static struct configfs_attribute *vhost_scsi_wwn_attrs[] = { | |||
2327 | }; | 2325 | }; |
2328 | 2326 | ||
2329 | static struct target_core_fabric_ops vhost_scsi_ops = { | 2327 | static struct target_core_fabric_ops vhost_scsi_ops = { |
2328 | .module = THIS_MODULE, | ||
2329 | .name = "vhost", | ||
2330 | .get_fabric_name = vhost_scsi_get_fabric_name, | 2330 | .get_fabric_name = vhost_scsi_get_fabric_name, |
2331 | .get_fabric_proto_ident = vhost_scsi_get_fabric_proto_ident, | 2331 | .get_fabric_proto_ident = vhost_scsi_get_fabric_proto_ident, |
2332 | .tpg_get_wwn = vhost_scsi_get_fabric_wwn, | 2332 | .tpg_get_wwn = vhost_scsi_get_fabric_wwn, |
@@ -2371,70 +2371,20 @@ static struct target_core_fabric_ops vhost_scsi_ops = { | |||
2371 | .fabric_drop_np = NULL, | 2371 | .fabric_drop_np = NULL, |
2372 | .fabric_make_nodeacl = vhost_scsi_make_nodeacl, | 2372 | .fabric_make_nodeacl = vhost_scsi_make_nodeacl, |
2373 | .fabric_drop_nodeacl = vhost_scsi_drop_nodeacl, | 2373 | .fabric_drop_nodeacl = vhost_scsi_drop_nodeacl, |
2374 | |||
2375 | .tfc_wwn_attrs = vhost_scsi_wwn_attrs, | ||
2376 | .tfc_tpg_base_attrs = vhost_scsi_tpg_attrs, | ||
2377 | .tfc_tpg_attrib_attrs = vhost_scsi_tpg_attrib_attrs, | ||
2374 | }; | 2378 | }; |
2375 | 2379 | ||
2376 | static int vhost_scsi_register_configfs(void) | 2380 | static int __init vhost_scsi_init(void) |
2377 | { | 2381 | { |
2378 | struct target_fabric_configfs *fabric; | 2382 | int ret = -ENOMEM; |
2379 | int ret; | ||
2380 | 2383 | ||
2381 | pr_debug("vhost-scsi fabric module %s on %s/%s" | 2384 | pr_debug("TCM_VHOST fabric module %s on %s/%s" |
2382 | " on "UTS_RELEASE"\n", VHOST_SCSI_VERSION, utsname()->sysname, | 2385 | " on "UTS_RELEASE"\n", VHOST_SCSI_VERSION, utsname()->sysname, |
2383 | utsname()->machine); | 2386 | utsname()->machine); |
2384 | /* | ||
2385 | * Register the top level struct config_item_type with TCM core | ||
2386 | */ | ||
2387 | fabric = target_fabric_configfs_init(THIS_MODULE, "vhost"); | ||
2388 | if (IS_ERR(fabric)) { | ||
2389 | pr_err("target_fabric_configfs_init() failed\n"); | ||
2390 | return PTR_ERR(fabric); | ||
2391 | } | ||
2392 | /* | ||
2393 | * Setup fabric->tf_ops from our local vhost_scsi_ops | ||
2394 | */ | ||
2395 | fabric->tf_ops = vhost_scsi_ops; | ||
2396 | /* | ||
2397 | * Setup default attribute lists for various fabric->tf_cit_tmpl | ||
2398 | */ | ||
2399 | fabric->tf_cit_tmpl.tfc_wwn_cit.ct_attrs = vhost_scsi_wwn_attrs; | ||
2400 | fabric->tf_cit_tmpl.tfc_tpg_base_cit.ct_attrs = vhost_scsi_tpg_attrs; | ||
2401 | fabric->tf_cit_tmpl.tfc_tpg_attrib_cit.ct_attrs = vhost_scsi_tpg_attrib_attrs; | ||
2402 | fabric->tf_cit_tmpl.tfc_tpg_param_cit.ct_attrs = NULL; | ||
2403 | fabric->tf_cit_tmpl.tfc_tpg_np_base_cit.ct_attrs = NULL; | ||
2404 | fabric->tf_cit_tmpl.tfc_tpg_nacl_base_cit.ct_attrs = NULL; | ||
2405 | fabric->tf_cit_tmpl.tfc_tpg_nacl_attrib_cit.ct_attrs = NULL; | ||
2406 | fabric->tf_cit_tmpl.tfc_tpg_nacl_auth_cit.ct_attrs = NULL; | ||
2407 | fabric->tf_cit_tmpl.tfc_tpg_nacl_param_cit.ct_attrs = NULL; | ||
2408 | /* | ||
2409 | * Register the fabric for use within TCM | ||
2410 | */ | ||
2411 | ret = target_fabric_configfs_register(fabric); | ||
2412 | if (ret < 0) { | ||
2413 | pr_err("target_fabric_configfs_register() failed" | ||
2414 | " for TCM_VHOST\n"); | ||
2415 | return ret; | ||
2416 | } | ||
2417 | /* | ||
2418 | * Setup our local pointer to *fabric | ||
2419 | */ | ||
2420 | vhost_scsi_fabric_configfs = fabric; | ||
2421 | pr_debug("TCM_VHOST[0] - Set fabric -> vhost_scsi_fabric_configfs\n"); | ||
2422 | return 0; | ||
2423 | }; | ||
2424 | |||
2425 | static void vhost_scsi_deregister_configfs(void) | ||
2426 | { | ||
2427 | if (!vhost_scsi_fabric_configfs) | ||
2428 | return; | ||
2429 | |||
2430 | target_fabric_configfs_deregister(vhost_scsi_fabric_configfs); | ||
2431 | vhost_scsi_fabric_configfs = NULL; | ||
2432 | pr_debug("TCM_VHOST[0] - Cleared vhost_scsi_fabric_configfs\n"); | ||
2433 | }; | ||
2434 | 2387 | ||
2435 | static int __init vhost_scsi_init(void) | ||
2436 | { | ||
2437 | int ret = -ENOMEM; | ||
2438 | /* | 2388 | /* |
2439 | * Use our own dedicated workqueue for submitting I/O into | 2389 | * Use our own dedicated workqueue for submitting I/O into |
2440 | * target core to avoid contention within system_wq. | 2390 | * target core to avoid contention within system_wq. |
@@ -2447,7 +2397,7 @@ static int __init vhost_scsi_init(void) | |||
2447 | if (ret < 0) | 2397 | if (ret < 0) |
2448 | goto out_destroy_workqueue; | 2398 | goto out_destroy_workqueue; |
2449 | 2399 | ||
2450 | ret = vhost_scsi_register_configfs(); | 2400 | ret = target_register_template(&vhost_scsi_ops); |
2451 | if (ret < 0) | 2401 | if (ret < 0) |
2452 | goto out_vhost_scsi_deregister; | 2402 | goto out_vhost_scsi_deregister; |
2453 | 2403 | ||
@@ -2463,7 +2413,7 @@ out: | |||
2463 | 2413 | ||
2464 | static void vhost_scsi_exit(void) | 2414 | static void vhost_scsi_exit(void) |
2465 | { | 2415 | { |
2466 | vhost_scsi_deregister_configfs(); | 2416 | target_unregister_template(&vhost_scsi_ops); |
2467 | vhost_scsi_deregister(); | 2417 | vhost_scsi_deregister(); |
2468 | destroy_workqueue(vhost_scsi_workqueue); | 2418 | destroy_workqueue(vhost_scsi_workqueue); |
2469 | }; | 2419 | }; |