Skip to content

Commit

Permalink
dm target: remove struct tt_internal
Browse files Browse the repository at this point in the history
The tt_internal is really just a list_head to manage registered target_type
in a double linked list,

Here embed the list_head into target_type directly,
1. to avoid kmalloc/kfree;
2. then tt_internal is really unneeded;

Cc: stable@kernel.org
Signed-off-by: Cheng Renquan <crquan@gmail.com>
Signed-off-by: Alasdair G Kergon <agk@redhat.com>
Reviewed-by: Alasdair G Kergon <agk@redhat.com>
  • Loading branch information
Cheng Renquan authored and Alasdair G Kergon committed Apr 2, 2009
1 parent 570b9d9 commit 45194e4
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 61 deletions.
90 changes: 30 additions & 60 deletions drivers/md/dm-target.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,40 +14,34 @@

#define DM_MSG_PREFIX "target"

struct tt_internal {
struct target_type tt;

struct list_head list;
};

static LIST_HEAD(_targets);
static DECLARE_RWSEM(_lock);

#define DM_MOD_NAME_SIZE 32

static inline struct tt_internal *__find_target_type(const char *name)
static inline struct target_type *__find_target_type(const char *name)
{
struct tt_internal *ti;
struct target_type *tt;

list_for_each_entry (ti, &_targets, list)
if (!strcmp(name, ti->tt.name))
return ti;
list_for_each_entry(tt, &_targets, list)
if (!strcmp(name, tt->name))
return tt;

return NULL;
}

static struct tt_internal *get_target_type(const char *name)
static struct target_type *get_target_type(const char *name)
{
struct tt_internal *ti;
struct target_type *tt;

down_read(&_lock);

ti = __find_target_type(name);
if (ti && !try_module_get(ti->tt.module))
ti = NULL;
tt = __find_target_type(name);
if (tt && !try_module_get(tt->module))
tt = NULL;

up_read(&_lock);
return ti;
return tt;
}

static void load_module(const char *name)
Expand All @@ -57,83 +51,59 @@ static void load_module(const char *name)

struct target_type *dm_get_target_type(const char *name)
{
struct tt_internal *ti = get_target_type(name);
struct target_type *tt = get_target_type(name);

if (!ti) {
if (!tt) {
load_module(name);
ti = get_target_type(name);
tt = get_target_type(name);
}

return ti ? &ti->tt : NULL;
return tt;
}

void dm_put_target_type(struct target_type *t)
void dm_put_target_type(struct target_type *tt)
{
struct tt_internal *ti = (struct tt_internal *) t;

down_read(&_lock);
module_put(ti->tt.module);
module_put(tt->module);
up_read(&_lock);

return;
}

static struct tt_internal *alloc_target(struct target_type *t)
{
struct tt_internal *ti = kzalloc(sizeof(*ti), GFP_KERNEL);

if (ti)
ti->tt = *t;

return ti;
}


int dm_target_iterate(void (*iter_func)(struct target_type *tt,
void *param), void *param)
{
struct tt_internal *ti;
struct target_type *tt;

down_read(&_lock);
list_for_each_entry (ti, &_targets, list)
iter_func(&ti->tt, param);
list_for_each_entry(tt, &_targets, list)
iter_func(tt, param);
up_read(&_lock);

return 0;
}

int dm_register_target(struct target_type *t)
int dm_register_target(struct target_type *tt)
{
int rv = 0;
struct tt_internal *ti = alloc_target(t);

if (!ti)
return -ENOMEM;

down_write(&_lock);
if (__find_target_type(t->name))
if (__find_target_type(tt->name))
rv = -EEXIST;
else
list_add(&ti->list, &_targets);
list_add(&tt->list, &_targets);

up_write(&_lock);
if (rv)
kfree(ti);
return rv;
}

void dm_unregister_target(struct target_type *t)
void dm_unregister_target(struct target_type *tt)
{
struct tt_internal *ti;

down_write(&_lock);
if (!(ti = __find_target_type(t->name))) {
DMCRIT("Unregistering unrecognised target: %s", t->name);
if (!__find_target_type(tt->name)) {
DMCRIT("Unregistering unrecognised target: %s", tt->name);
BUG();
}

list_del(&ti->list);
kfree(ti);
list_del(&tt->list);

up_write(&_lock);
}
Expand All @@ -142,17 +112,17 @@ void dm_unregister_target(struct target_type *t)
* io-err: always fails an io, useful for bringing
* up LVs that have holes in them.
*/
static int io_err_ctr(struct dm_target *ti, unsigned int argc, char **args)
static int io_err_ctr(struct dm_target *tt, unsigned int argc, char **args)
{
return 0;
}

static void io_err_dtr(struct dm_target *ti)
static void io_err_dtr(struct dm_target *tt)
{
/* empty */
}

static int io_err_map(struct dm_target *ti, struct bio *bio,
static int io_err_map(struct dm_target *tt, struct bio *bio,
union map_info *map_context)
{
return -EIO;
Expand Down
2 changes: 1 addition & 1 deletion drivers/md/dm.h
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ int dm_table_barrier_ok(struct dm_table *t);
int dm_target_init(void);
void dm_target_exit(void);
struct target_type *dm_get_target_type(const char *name);
void dm_put_target_type(struct target_type *t);
void dm_put_target_type(struct target_type *tt);
int dm_target_iterate(void (*iter_func)(struct target_type *tt,
void *param), void *param);

Expand Down
3 changes: 3 additions & 0 deletions include/linux/device-mapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,9 @@ struct target_type {
dm_ioctl_fn ioctl;
dm_merge_fn merge;
dm_busy_fn busy;

/* For internal device-mapper use. */
struct list_head list;
};

struct io_restrictions {
Expand Down

0 comments on commit 45194e4

Please sign in to comment.