Skip to content

Commit

Permalink
target: simplify backend driver registration
Browse files Browse the repository at this point in the history
Rewrite the backend driver registration based on what we did to the fabric
drivers:  introduce a read-only struct target_bakckend_ops that the driver
registers, which is then instanciate as a struct target_backend by the
core.  This allows the ops vector to be smaller and allows us to mark it
const.  At the same time the registration function can set up the
configfs attributes, avoiding the need to add additional boilerplate code
for that to the drivers.

Signed-off-by: Christoph Hellwig <[email protected]>
Signed-off-by: Nicholas Bellinger <[email protected]>
  • Loading branch information
Christoph Hellwig authored and nablio3000 committed Jun 1, 2015
1 parent 4624773 commit 0a06d43
Show file tree
Hide file tree
Showing 11 changed files with 135 additions and 158 deletions.
68 changes: 36 additions & 32 deletions drivers/target/target_core_configfs.c
Original file line number Diff line number Diff line change
Expand Up @@ -51,15 +51,26 @@
#include "target_core_xcopy.h"

#define TB_CIT_SETUP(_name, _item_ops, _group_ops, _attrs) \
static void target_core_setup_##_name##_cit(struct se_subsystem_api *sa) \
static void target_core_setup_##_name##_cit(struct target_backend *tb) \
{ \
struct target_backend_cits *tbc = &sa->tb_cits; \
struct config_item_type *cit = &tbc->tb_##_name##_cit; \
struct config_item_type *cit = &tb->tb_##_name##_cit; \
\
cit->ct_item_ops = _item_ops; \
cit->ct_group_ops = _group_ops; \
cit->ct_attrs = _attrs; \
cit->ct_owner = sa->owner; \
cit->ct_owner = tb->ops->owner; \
pr_debug("Setup generic %s\n", __stringify(_name)); \
}

#define TB_CIT_SETUP_DRV(_name, _item_ops, _group_ops) \
static void target_core_setup_##_name##_cit(struct target_backend *tb) \
{ \
struct config_item_type *cit = &tb->tb_##_name##_cit; \
\
cit->ct_item_ops = _item_ops; \
cit->ct_group_ops = _group_ops; \
cit->ct_attrs = tb->ops->tb_##_name##_attrs; \
cit->ct_owner = tb->ops->owner; \
pr_debug("Setup generic %s\n", __stringify(_name)); \
}

Expand Down Expand Up @@ -469,7 +480,7 @@ static struct configfs_item_operations target_core_dev_attrib_ops = {
.store_attribute = target_core_dev_attrib_attr_store,
};

TB_CIT_SETUP(dev_attrib, &target_core_dev_attrib_ops, NULL, NULL);
TB_CIT_SETUP_DRV(dev_attrib, &target_core_dev_attrib_ops, NULL);

/* End functions for struct config_item_type tb_dev_attrib_cit */

Expand Down Expand Up @@ -1174,13 +1185,13 @@ TB_CIT_SETUP(dev_pr, &target_core_dev_pr_ops, NULL, target_core_dev_pr_attrs);
static ssize_t target_core_show_dev_info(void *p, char *page)
{
struct se_device *dev = p;
struct se_subsystem_api *t = dev->transport;
int bl = 0;
ssize_t read_bytes = 0;

transport_dump_dev_state(dev, page, &bl);
read_bytes += bl;
read_bytes += t->show_configfs_dev_params(dev, page+read_bytes);
read_bytes += dev->transport->show_configfs_dev_params(dev,
page+read_bytes);
return read_bytes;
}

Expand All @@ -1198,9 +1209,8 @@ static ssize_t target_core_store_dev_control(
size_t count)
{
struct se_device *dev = p;
struct se_subsystem_api *t = dev->transport;

return t->set_configfs_dev_params(dev, page, count);
return dev->transport->set_configfs_dev_params(dev, page, count);
}

static struct target_core_configfs_attribute target_core_attr_dev_control = {
Expand Down Expand Up @@ -2477,9 +2487,9 @@ static struct config_group *target_core_make_subdev(
const char *name)
{
struct t10_alua_tg_pt_gp *tg_pt_gp;
struct se_subsystem_api *t;
struct config_item *hba_ci = &group->cg_item;
struct se_hba *hba = item_to_hba(hba_ci);
struct target_backend *tb = hba->backend;
struct se_device *dev;
struct config_group *dev_cg = NULL, *tg_pt_gp_cg = NULL;
struct config_group *dev_stat_grp = NULL;
Expand All @@ -2488,10 +2498,6 @@ static struct config_group *target_core_make_subdev(
ret = mutex_lock_interruptible(&hba->hba_access_mutex);
if (ret)
return ERR_PTR(ret);
/*
* Locate the struct se_subsystem_api from parent's struct se_hba.
*/
t = hba->transport;

dev = target_alloc_device(hba, name);
if (!dev)
Expand All @@ -2504,17 +2510,17 @@ static struct config_group *target_core_make_subdev(
if (!dev_cg->default_groups)
goto out_free_device;

config_group_init_type_name(dev_cg, name, &t->tb_cits.tb_dev_cit);
config_group_init_type_name(dev_cg, name, &tb->tb_dev_cit);
config_group_init_type_name(&dev->dev_attrib.da_group, "attrib",
&t->tb_cits.tb_dev_attrib_cit);
&tb->tb_dev_attrib_cit);
config_group_init_type_name(&dev->dev_pr_group, "pr",
&t->tb_cits.tb_dev_pr_cit);
&tb->tb_dev_pr_cit);
config_group_init_type_name(&dev->t10_wwn.t10_wwn_group, "wwn",
&t->tb_cits.tb_dev_wwn_cit);
&tb->tb_dev_wwn_cit);
config_group_init_type_name(&dev->t10_alua.alua_tg_pt_gps_group,
"alua", &t->tb_cits.tb_dev_alua_tg_pt_gps_cit);
"alua", &tb->tb_dev_alua_tg_pt_gps_cit);
config_group_init_type_name(&dev->dev_stat_grps.stat_group,
"statistics", &t->tb_cits.tb_dev_stat_cit);
"statistics", &tb->tb_dev_stat_cit);

dev_cg->default_groups[0] = &dev->dev_attrib.da_group;
dev_cg->default_groups[1] = &dev->dev_pr_group;
Expand Down Expand Up @@ -2644,7 +2650,7 @@ static ssize_t target_core_hba_show_attr_hba_info(
char *page)
{
return sprintf(page, "HBA Index: %d plugin: %s version: %s\n",
hba->hba_id, hba->transport->name,
hba->hba_id, hba->backend->ops->name,
TARGET_CORE_CONFIGFS_VERSION);
}

Expand All @@ -2664,11 +2670,10 @@ static ssize_t target_core_hba_show_attr_hba_mode(struct se_hba *hba,
static ssize_t target_core_hba_store_attr_hba_mode(struct se_hba *hba,
const char *page, size_t count)
{
struct se_subsystem_api *transport = hba->transport;
unsigned long mode_flag;
int ret;

if (transport->pmode_enable_hba == NULL)
if (hba->backend->ops->pmode_enable_hba == NULL)
return -EINVAL;

ret = kstrtoul(page, 0, &mode_flag);
Expand All @@ -2682,7 +2687,7 @@ static ssize_t target_core_hba_store_attr_hba_mode(struct se_hba *hba,
return -EINVAL;
}

ret = transport->pmode_enable_hba(hba, mode_flag);
ret = hba->backend->ops->pmode_enable_hba(hba, mode_flag);
if (ret < 0)
return -EINVAL;
if (ret > 0)
Expand Down Expand Up @@ -2808,16 +2813,15 @@ static struct config_item_type target_core_cit = {

/* Stop functions for struct config_item_type target_core_hba_cit */

void target_core_setup_sub_cits(struct se_subsystem_api *sa)
void target_setup_backend_cits(struct target_backend *tb)
{
target_core_setup_dev_cit(sa);
target_core_setup_dev_attrib_cit(sa);
target_core_setup_dev_pr_cit(sa);
target_core_setup_dev_wwn_cit(sa);
target_core_setup_dev_alua_tg_pt_gps_cit(sa);
target_core_setup_dev_stat_cit(sa);
target_core_setup_dev_cit(tb);
target_core_setup_dev_attrib_cit(tb);
target_core_setup_dev_pr_cit(tb);
target_core_setup_dev_wwn_cit(tb);
target_core_setup_dev_alua_tg_pt_gps_cit(tb);
target_core_setup_dev_stat_cit(tb);
}
EXPORT_SYMBOL(target_core_setup_sub_cits);

static int __init target_core_init_configfs(void)
{
Expand Down
6 changes: 3 additions & 3 deletions drivers/target/target_core_device.c
Original file line number Diff line number Diff line change
Expand Up @@ -1367,13 +1367,13 @@ struct se_device *target_alloc_device(struct se_hba *hba, const char *name)
struct se_device *dev;
struct se_lun *xcopy_lun;

dev = hba->transport->alloc_device(hba, name);
dev = hba->backend->ops->alloc_device(hba, name);
if (!dev)
return NULL;

dev->dev_link_magic = SE_DEV_LINK_MAGIC;
dev->se_hba = hba;
dev->transport = hba->transport;
dev->transport = hba->backend->ops;
dev->prot_length = sizeof(struct se_dif_v1_tuple);

INIT_LIST_HEAD(&dev->dev_list);
Expand Down Expand Up @@ -1571,7 +1571,7 @@ int core_dev_setup_virtual_lun0(void)
goto out_free_hba;
}

hba->transport->set_configfs_dev_params(dev, buf, sizeof(buf));
hba->backend->ops->set_configfs_dev_params(dev, buf, sizeof(buf));

ret = target_configure_device(dev);
if (ret)
Expand Down
16 changes: 4 additions & 12 deletions drivers/target/target_core_file.c
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,6 @@ static inline struct fd_dev *FD_DEV(struct se_device *dev)
return container_of(dev, struct fd_dev, dev);
}

/* fd_attach_hba(): (Part of se_subsystem_api_t template)
*
*
*/
static int fd_attach_hba(struct se_hba *hba, u32 host_id)
{
struct fd_host *fd_host;
Expand Down Expand Up @@ -881,7 +877,7 @@ static struct configfs_attribute *fileio_backend_dev_attrs[] = {
NULL,
};

static struct se_subsystem_api fileio_template = {
static const struct target_backend_ops fileio_ops = {
.name = "fileio",
.inquiry_prod = "FILEIO",
.inquiry_rev = FD_VERSION,
Expand All @@ -899,21 +895,17 @@ static struct se_subsystem_api fileio_template = {
.init_prot = fd_init_prot,
.format_prot = fd_format_prot,
.free_prot = fd_free_prot,
.tb_dev_attrib_attrs = fileio_backend_dev_attrs,
};

static int __init fileio_module_init(void)
{
struct target_backend_cits *tbc = &fileio_template.tb_cits;

target_core_setup_sub_cits(&fileio_template);
tbc->tb_dev_attrib_cit.ct_attrs = fileio_backend_dev_attrs;

return transport_subsystem_register(&fileio_template);
return transport_backend_register(&fileio_ops);
}

static void __exit fileio_module_exit(void)
{
transport_subsystem_release(&fileio_template);
target_backend_unregister(&fileio_ops);
}

MODULE_DESCRIPTION("TCM FILEIO subsystem plugin");
Expand Down
96 changes: 54 additions & 42 deletions drivers/target/target_core_hba.c
Original file line number Diff line number Diff line change
Expand Up @@ -39,63 +39,75 @@

#include "target_core_internal.h"

static LIST_HEAD(subsystem_list);
static DEFINE_MUTEX(subsystem_mutex);
static LIST_HEAD(backend_list);
static DEFINE_MUTEX(backend_mutex);

static u32 hba_id_counter;

static DEFINE_SPINLOCK(hba_lock);
static LIST_HEAD(hba_list);

int transport_subsystem_register(struct se_subsystem_api *sub_api)
{
struct se_subsystem_api *s;

INIT_LIST_HEAD(&sub_api->sub_api_list);

mutex_lock(&subsystem_mutex);
list_for_each_entry(s, &subsystem_list, sub_api_list) {
if (!strcmp(s->name, sub_api->name)) {
pr_err("%p is already registered with"
" duplicate name %s, unable to process"
" request\n", s, s->name);
mutex_unlock(&subsystem_mutex);
int transport_backend_register(const struct target_backend_ops *ops)
{
struct target_backend *tb, *old;

tb = kzalloc(sizeof(*tb), GFP_KERNEL);
if (!tb)
return -ENOMEM;
tb->ops = ops;

mutex_lock(&backend_mutex);
list_for_each_entry(old, &backend_list, list) {
if (!strcmp(old->ops->name, ops->name)) {
pr_err("backend %s already registered.\n", ops->name);
mutex_unlock(&backend_mutex);
kfree(tb);
return -EEXIST;
}
}
list_add_tail(&sub_api->sub_api_list, &subsystem_list);
mutex_unlock(&subsystem_mutex);
target_setup_backend_cits(tb);
list_add_tail(&tb->list, &backend_list);
mutex_unlock(&backend_mutex);

pr_debug("TCM: Registered subsystem plugin: %s struct module:"
" %p\n", sub_api->name, sub_api->owner);
pr_debug("TCM: Registered subsystem plugin: %s struct module: %p\n",
ops->name, ops->owner);
return 0;
}
EXPORT_SYMBOL(transport_subsystem_register);
EXPORT_SYMBOL(transport_backend_register);

void transport_subsystem_release(struct se_subsystem_api *sub_api)
void target_backend_unregister(const struct target_backend_ops *ops)
{
mutex_lock(&subsystem_mutex);
list_del(&sub_api->sub_api_list);
mutex_unlock(&subsystem_mutex);
struct target_backend *tb;

mutex_lock(&backend_mutex);
list_for_each_entry(tb, &backend_list, list) {
if (tb->ops == ops) {
list_del(&tb->list);
kfree(tb);
break;
}
}
mutex_unlock(&backend_mutex);
}
EXPORT_SYMBOL(transport_subsystem_release);
EXPORT_SYMBOL(target_backend_unregister);

static struct se_subsystem_api *core_get_backend(const char *sub_name)
static struct target_backend *core_get_backend(const char *name)
{
struct se_subsystem_api *s;
struct target_backend *tb;

mutex_lock(&subsystem_mutex);
list_for_each_entry(s, &subsystem_list, sub_api_list) {
if (!strcmp(s->name, sub_name))
mutex_lock(&backend_mutex);
list_for_each_entry(tb, &backend_list, list) {
if (!strcmp(tb->ops->name, name))
goto found;
}
mutex_unlock(&subsystem_mutex);
mutex_unlock(&backend_mutex);
return NULL;
found:
if (s->owner && !try_module_get(s->owner))
s = NULL;
mutex_unlock(&subsystem_mutex);
return s;
if (tb->ops->owner && !try_module_get(tb->ops->owner))
tb = NULL;
mutex_unlock(&backend_mutex);
return tb;
}

struct se_hba *
Expand All @@ -116,13 +128,13 @@ core_alloc_hba(const char *plugin_name, u32 plugin_dep_id, u32 hba_flags)
hba->hba_index = scsi_get_new_index(SCSI_INST_INDEX);
hba->hba_flags |= hba_flags;

hba->transport = core_get_backend(plugin_name);
if (!hba->transport) {
hba->backend = core_get_backend(plugin_name);
if (!hba->backend) {
ret = -EINVAL;
goto out_free_hba;
}

ret = hba->transport->attach_hba(hba, plugin_dep_id);
ret = hba->backend->ops->attach_hba(hba, plugin_dep_id);
if (ret < 0)
goto out_module_put;

Expand All @@ -137,8 +149,8 @@ core_alloc_hba(const char *plugin_name, u32 plugin_dep_id, u32 hba_flags)
return hba;

out_module_put:
module_put(hba->transport->owner);
hba->transport = NULL;
module_put(hba->backend->ops->owner);
hba->backend = NULL;
out_free_hba:
kfree(hba);
return ERR_PTR(ret);
Expand All @@ -149,7 +161,7 @@ core_delete_hba(struct se_hba *hba)
{
WARN_ON(hba->dev_count);

hba->transport->detach_hba(hba);
hba->backend->ops->detach_hba(hba);

spin_lock(&hba_lock);
list_del(&hba->hba_node);
Expand All @@ -158,9 +170,9 @@ core_delete_hba(struct se_hba *hba)
pr_debug("CORE_HBA[%d] - Detached HBA from Generic Target"
" Core\n", hba->hba_id);

module_put(hba->transport->owner);
module_put(hba->backend->ops->owner);

hba->transport = NULL;
hba->backend = NULL;
kfree(hba);
return 0;
}
Loading

0 comments on commit 0a06d43

Please sign in to comment.