[PATCH] md: Add sysfs access to raid6 stripe cache size
.. just as we already have for raid5. Signed-off-by: Neil Brown <neilb@suse.de> Cc: Greg KH <greg@kroah.com> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
This commit is contained in:
committed by
Linus Torvalds
parent
978f946bb6
commit
35849c75d7
@@ -115,7 +115,7 @@ static void __release_stripe(raid6_conf_t *conf, struct stripe_head *sh)
|
|||||||
list_add_tail(&sh->lru, &conf->inactive_list);
|
list_add_tail(&sh->lru, &conf->inactive_list);
|
||||||
atomic_dec(&conf->active_stripes);
|
atomic_dec(&conf->active_stripes);
|
||||||
if (!conf->inactive_blocked ||
|
if (!conf->inactive_blocked ||
|
||||||
atomic_read(&conf->active_stripes) < (NR_STRIPES*3/4))
|
atomic_read(&conf->active_stripes) < (conf->max_nr_stripes*3/4))
|
||||||
wake_up(&conf->wait_for_stripe);
|
wake_up(&conf->wait_for_stripe);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -273,7 +273,8 @@ static struct stripe_head *get_active_stripe(raid6_conf_t *conf, sector_t sector
|
|||||||
conf->inactive_blocked = 1;
|
conf->inactive_blocked = 1;
|
||||||
wait_event_lock_irq(conf->wait_for_stripe,
|
wait_event_lock_irq(conf->wait_for_stripe,
|
||||||
!list_empty(&conf->inactive_list) &&
|
!list_empty(&conf->inactive_list) &&
|
||||||
(atomic_read(&conf->active_stripes) < (NR_STRIPES *3/4)
|
(atomic_read(&conf->active_stripes)
|
||||||
|
< (conf->max_nr_stripes *3/4)
|
||||||
|| !conf->inactive_blocked),
|
|| !conf->inactive_blocked),
|
||||||
conf->device_lock,
|
conf->device_lock,
|
||||||
unplug_slaves(conf->mddev);
|
unplug_slaves(conf->mddev);
|
||||||
@@ -302,9 +303,31 @@ static struct stripe_head *get_active_stripe(raid6_conf_t *conf, sector_t sector
|
|||||||
return sh;
|
return sh;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int grow_stripes(raid6_conf_t *conf, int num)
|
static int grow_one_stripe(raid6_conf_t *conf)
|
||||||
{
|
{
|
||||||
struct stripe_head *sh;
|
struct stripe_head *sh;
|
||||||
|
sh = kmem_cache_alloc(conf->slab_cache, GFP_KERNEL);
|
||||||
|
if (!sh)
|
||||||
|
return 0;
|
||||||
|
memset(sh, 0, sizeof(*sh) + (conf->raid_disks-1)*sizeof(struct r5dev));
|
||||||
|
sh->raid_conf = conf;
|
||||||
|
spin_lock_init(&sh->lock);
|
||||||
|
|
||||||
|
if (grow_buffers(sh, conf->raid_disks)) {
|
||||||
|
shrink_buffers(sh, conf->raid_disks);
|
||||||
|
kmem_cache_free(conf->slab_cache, sh);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
/* we just created an active stripe so... */
|
||||||
|
atomic_set(&sh->count, 1);
|
||||||
|
atomic_inc(&conf->active_stripes);
|
||||||
|
INIT_LIST_HEAD(&sh->lru);
|
||||||
|
release_stripe(sh);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int grow_stripes(raid6_conf_t *conf, int num)
|
||||||
|
{
|
||||||
kmem_cache_t *sc;
|
kmem_cache_t *sc;
|
||||||
int devs = conf->raid_disks;
|
int devs = conf->raid_disks;
|
||||||
|
|
||||||
@@ -316,44 +339,33 @@ static int grow_stripes(raid6_conf_t *conf, int num)
|
|||||||
if (!sc)
|
if (!sc)
|
||||||
return 1;
|
return 1;
|
||||||
conf->slab_cache = sc;
|
conf->slab_cache = sc;
|
||||||
while (num--) {
|
while (num--)
|
||||||
sh = kmem_cache_alloc(sc, GFP_KERNEL);
|
if (!grow_one_stripe(conf))
|
||||||
if (!sh)
|
|
||||||
return 1;
|
return 1;
|
||||||
memset(sh, 0, sizeof(*sh) + (devs-1)*sizeof(struct r5dev));
|
|
||||||
sh->raid_conf = conf;
|
|
||||||
spin_lock_init(&sh->lock);
|
|
||||||
|
|
||||||
if (grow_buffers(sh, conf->raid_disks)) {
|
|
||||||
shrink_buffers(sh, conf->raid_disks);
|
|
||||||
kmem_cache_free(sc, sh);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
/* we just created an active stripe so... */
|
|
||||||
atomic_set(&sh->count, 1);
|
|
||||||
atomic_inc(&conf->active_stripes);
|
|
||||||
INIT_LIST_HEAD(&sh->lru);
|
|
||||||
release_stripe(sh);
|
|
||||||
}
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int drop_one_stripe(raid6_conf_t *conf)
|
||||||
|
{
|
||||||
|
struct stripe_head *sh;
|
||||||
|
spin_lock_irq(&conf->device_lock);
|
||||||
|
sh = get_free_stripe(conf);
|
||||||
|
spin_unlock_irq(&conf->device_lock);
|
||||||
|
if (!sh)
|
||||||
|
return 0;
|
||||||
|
if (atomic_read(&sh->count))
|
||||||
|
BUG();
|
||||||
|
shrink_buffers(sh, conf->raid_disks);
|
||||||
|
kmem_cache_free(conf->slab_cache, sh);
|
||||||
|
atomic_dec(&conf->active_stripes);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
static void shrink_stripes(raid6_conf_t *conf)
|
static void shrink_stripes(raid6_conf_t *conf)
|
||||||
{
|
{
|
||||||
struct stripe_head *sh;
|
while (drop_one_stripe(conf))
|
||||||
|
;
|
||||||
|
|
||||||
while (1) {
|
|
||||||
spin_lock_irq(&conf->device_lock);
|
|
||||||
sh = get_free_stripe(conf);
|
|
||||||
spin_unlock_irq(&conf->device_lock);
|
|
||||||
if (!sh)
|
|
||||||
break;
|
|
||||||
if (atomic_read(&sh->count))
|
|
||||||
BUG();
|
|
||||||
shrink_buffers(sh, conf->raid_disks);
|
|
||||||
kmem_cache_free(conf->slab_cache, sh);
|
|
||||||
atomic_dec(&conf->active_stripes);
|
|
||||||
}
|
|
||||||
kmem_cache_destroy(conf->slab_cache);
|
kmem_cache_destroy(conf->slab_cache);
|
||||||
conf->slab_cache = NULL;
|
conf->slab_cache = NULL;
|
||||||
}
|
}
|
||||||
@@ -1912,6 +1924,74 @@ static void raid6d (mddev_t *mddev)
|
|||||||
PRINTK("--- raid6d inactive\n");
|
PRINTK("--- raid6d inactive\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static ssize_t
|
||||||
|
raid6_show_stripe_cache_size(mddev_t *mddev, char *page)
|
||||||
|
{
|
||||||
|
raid6_conf_t *conf = mddev_to_conf(mddev);
|
||||||
|
if (conf)
|
||||||
|
return sprintf(page, "%d\n", conf->max_nr_stripes);
|
||||||
|
else
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static ssize_t
|
||||||
|
raid6_store_stripe_cache_size(mddev_t *mddev, const char *page, size_t len)
|
||||||
|
{
|
||||||
|
raid6_conf_t *conf = mddev_to_conf(mddev);
|
||||||
|
char *end;
|
||||||
|
int new;
|
||||||
|
if (len >= PAGE_SIZE)
|
||||||
|
return -EINVAL;
|
||||||
|
if (!conf)
|
||||||
|
return -ENODEV;
|
||||||
|
|
||||||
|
new = simple_strtoul(page, &end, 10);
|
||||||
|
if (!*page || (*end && *end != '\n') )
|
||||||
|
return -EINVAL;
|
||||||
|
if (new <= 16 || new > 32768)
|
||||||
|
return -EINVAL;
|
||||||
|
while (new < conf->max_nr_stripes) {
|
||||||
|
if (drop_one_stripe(conf))
|
||||||
|
conf->max_nr_stripes--;
|
||||||
|
else
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
while (new > conf->max_nr_stripes) {
|
||||||
|
if (grow_one_stripe(conf))
|
||||||
|
conf->max_nr_stripes++;
|
||||||
|
else break;
|
||||||
|
}
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct md_sysfs_entry
|
||||||
|
raid6_stripecache_size = __ATTR(stripe_cache_size, S_IRUGO | S_IWUSR,
|
||||||
|
raid6_show_stripe_cache_size,
|
||||||
|
raid6_store_stripe_cache_size);
|
||||||
|
|
||||||
|
static ssize_t
|
||||||
|
stripe_cache_active_show(mddev_t *mddev, char *page)
|
||||||
|
{
|
||||||
|
raid6_conf_t *conf = mddev_to_conf(mddev);
|
||||||
|
if (conf)
|
||||||
|
return sprintf(page, "%d\n", atomic_read(&conf->active_stripes));
|
||||||
|
else
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct md_sysfs_entry
|
||||||
|
raid6_stripecache_active = __ATTR_RO(stripe_cache_active);
|
||||||
|
|
||||||
|
static struct attribute *raid6_attrs[] = {
|
||||||
|
&raid6_stripecache_size.attr,
|
||||||
|
&raid6_stripecache_active.attr,
|
||||||
|
NULL,
|
||||||
|
};
|
||||||
|
static struct attribute_group raid6_attrs_group = {
|
||||||
|
.name = NULL,
|
||||||
|
.attrs = raid6_attrs,
|
||||||
|
};
|
||||||
|
|
||||||
static int run(mddev_t *mddev)
|
static int run(mddev_t *mddev)
|
||||||
{
|
{
|
||||||
raid6_conf_t *conf;
|
raid6_conf_t *conf;
|
||||||
@@ -2095,6 +2175,7 @@ static int stop (mddev_t *mddev)
|
|||||||
shrink_stripes(conf);
|
shrink_stripes(conf);
|
||||||
kfree(conf->stripe_hashtbl);
|
kfree(conf->stripe_hashtbl);
|
||||||
blk_sync_queue(mddev->queue); /* the unplug fn references 'conf'*/
|
blk_sync_queue(mddev->queue); /* the unplug fn references 'conf'*/
|
||||||
|
sysfs_remove_group(&mddev->kobj, &raid6_attrs_group);
|
||||||
kfree(conf);
|
kfree(conf);
|
||||||
mddev->private = NULL;
|
mddev->private = NULL;
|
||||||
return 0;
|
return 0;
|
||||||
|
Reference in New Issue
Block a user