mirror of
git://sourceware.org/git/lvm2.git
synced 2025-04-01 18:50:41 +03:00
o Added ref counting to tables
o Further changes to new fs interface
This commit is contained in:
parent
6913d8e995
commit
633b68b518
@ -167,7 +167,7 @@ static int dmfs_release(struct inode *inode, struct file *f)
|
||||
|
||||
/* free off the old table */
|
||||
if (table) {
|
||||
dm_table_destroy(table);
|
||||
dm_put_table(table);
|
||||
inode->u.generic_ip = 0;
|
||||
}
|
||||
|
||||
@ -201,7 +201,7 @@ void dmfs_put_inode(struct inode *inode)
|
||||
|
||||
} else {
|
||||
if (table)
|
||||
dm_table_destroy(table);
|
||||
dm_put_table(table);
|
||||
|
||||
}
|
||||
|
||||
|
@ -34,6 +34,9 @@ struct dm_table *dm_parse(extract_line_fn line_fn, void *l_private,
|
||||
void *context;
|
||||
int last_line_good = 1, was_error = 0;
|
||||
|
||||
if (table == NULL)
|
||||
return NULL;
|
||||
|
||||
#define PARSE_ERROR {last_line_good = 0; was_error = 1; continue;}
|
||||
|
||||
while (line_fn(&line, l_private)) {
|
||||
@ -114,7 +117,7 @@ struct dm_table *dm_parse(extract_line_fn line_fn, void *l_private,
|
||||
return table;
|
||||
}
|
||||
|
||||
dm_table_destroy(table);
|
||||
dm_put_table(table);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -127,6 +127,7 @@ struct dm_table *dm_table_create(void)
|
||||
|
||||
memset(t, 0, sizeof(*t));
|
||||
|
||||
atomic_set(&t->refcnt, 1);
|
||||
atomic_set(&t->pending, 0);
|
||||
init_waitqueue_head(&t->wait);
|
||||
|
||||
@ -141,12 +142,12 @@ struct dm_table *dm_table_create(void)
|
||||
return t;
|
||||
}
|
||||
|
||||
void dm_table_destroy(struct dm_table *t)
|
||||
static void dm_table_destroy(struct dm_table *t)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (!t)
|
||||
return;
|
||||
if (atomic_read(&t->pending))
|
||||
BUG();
|
||||
|
||||
/* free the indexes */
|
||||
for (i = 0; i < t->depth - 1; i++) {
|
||||
@ -165,6 +166,12 @@ void dm_table_destroy(struct dm_table *t)
|
||||
kfree(t);
|
||||
}
|
||||
|
||||
void dm_put_table(struct dm_table *t)
|
||||
{
|
||||
if (atomic_dec_and_test(&t->refcnt))
|
||||
dm_table_destroy(t);
|
||||
}
|
||||
|
||||
/*
|
||||
* checks to see if we need to extend highs or targets
|
||||
*/
|
||||
|
@ -167,6 +167,8 @@ struct target {
|
||||
* the btree
|
||||
*/
|
||||
struct dm_table {
|
||||
atomic_t refcnt;
|
||||
|
||||
/* btree table */
|
||||
int depth;
|
||||
int counts[MAX_DEPTH]; /* in nodes */
|
||||
@ -226,7 +228,7 @@ void dm_suspend(struct mapped_device *md);
|
||||
|
||||
/* dm-table.c */
|
||||
struct dm_table *dm_table_create(void);
|
||||
void dm_table_destroy(struct dm_table *t);
|
||||
void dm_put_table(struct dm_table *t);
|
||||
|
||||
int dm_table_add_target(struct dm_table *t, offset_t high,
|
||||
struct target_type *type, void *private);
|
||||
|
@ -27,6 +27,7 @@
|
||||
static int dmfs_lv_create(struct inode *dir, struct dentry *dentry, int mode)
|
||||
{
|
||||
struct inode *inode;
|
||||
struct dm_table *table;
|
||||
|
||||
if (dentry->d_name.name[0] == '.')
|
||||
return -EPERM;
|
||||
@ -37,16 +38,23 @@ static int dmfs_lv_create(struct inode *dir, struct dentry *dentry, int mode)
|
||||
|
||||
inode = dmfs_create_table(dir, dentry, mode)
|
||||
if (!IS_ERR(inode)) {
|
||||
d_instantiate(dentry, inode);
|
||||
dget(dentry);
|
||||
return 0;
|
||||
table = dm_table_create();
|
||||
if (table) {
|
||||
d_instantiate(dentry, inode);
|
||||
dget(dentry);
|
||||
return 0;
|
||||
}
|
||||
iput(inode);
|
||||
return -ENOMEM;
|
||||
}
|
||||
return PTR_ERR(inode);
|
||||
}
|
||||
|
||||
static int dmfs_lv_unlink(struct inode *dir, struct dentry *dentry)
|
||||
{
|
||||
|
||||
inode->i_nlink--;
|
||||
dput(dentry);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int dmfs_lv_link(struct dentry *old_dentry, struct inode *dir, struct dentry *dentry)
|
||||
@ -59,6 +67,9 @@ static int dmfs_lv_link(struct dentry *old_dentry, struct inode *dir, struct den
|
||||
if (dentry->d_parent != old_dentry->d_parent)
|
||||
return -EPERM;
|
||||
|
||||
if (dentry->d_name[0] == '.')
|
||||
return -EPERM;
|
||||
|
||||
inode->i_ctime = CURRENT_TIME;
|
||||
|
||||
return 0;
|
||||
|
@ -41,13 +41,16 @@ static void dmfs_delete_inode(struct inode *inode)
|
||||
case S_IFDIR:
|
||||
if (inode->u.generic_ip) {
|
||||
dm_remove((struct mapped_device *)inode->u.generic_ip);
|
||||
inode->u.generic_ip = NULL;
|
||||
}
|
||||
break;
|
||||
case S_IFREG:
|
||||
if (inode->u.generic_ip) {
|
||||
dm_put_table((struct dm_table *)inode->u.generic_ip);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
inode->u.generic_ip = NULL;
|
||||
clear_inode(inode);
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user