summaryrefslogtreecommitdiff
path: root/drivers/staging/zram/zram_sysfs.c
diff options
context:
space:
mode:
authorJerome Marchand <jmarchan@redhat.com>2011-09-06 13:02:11 (GMT)
committerGreg Kroah-Hartman <gregkh@suse.de>2011-09-06 23:56:15 (GMT)
commit0900beae178a84e653d9088979cf3014babc097e (patch)
treec2ddc5d26f4f97e5406fede5cb391ec1296a1e62 /drivers/staging/zram/zram_sysfs.c
parenta1c821ae6c63d9ac648374f4953295e350572d3c (diff)
downloadlinux-fsl-qoriq-0900beae178a84e653d9088979cf3014babc097e.tar.xz
staging: zram: fix zram locking
Currently init_lock only prevents concurrent execution of zram_init_device() and zram_reset_device() but not zram_make_request() nor sysfs store functions. This patch changes init_lock into a rw_semaphore. A write lock is taken by init, reset and store functions, a read lock is taken by zram_make_request(). Also, avoids to release the lock before calling __zram_reset_device() for cleaning after a failed init, thus preventing any concurrent task to see an inconsistent state of zram. Signed-off-by: Jerome Marchand <jmarchan@redhat.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/staging/zram/zram_sysfs.c')
-rw-r--r--drivers/staging/zram/zram_sysfs.c18
1 files changed, 12 insertions, 6 deletions
diff --git a/drivers/staging/zram/zram_sysfs.c b/drivers/staging/zram/zram_sysfs.c
index df1f9dc..0ea8ed2 100644
--- a/drivers/staging/zram/zram_sysfs.c
+++ b/drivers/staging/zram/zram_sysfs.c
@@ -55,19 +55,23 @@ static ssize_t disksize_store(struct device *dev,
struct device_attribute *attr, const char *buf, size_t len)
{
int ret;
+ u64 disksize;
struct zram *zram = dev_to_zram(dev);
+ ret = strict_strtoull(buf, 10, &disksize);
+ if (ret)
+ return ret;
+
+ down_write(&zram->init_lock);
if (zram->init_done) {
+ up_write(&zram->init_lock);
pr_info("Cannot change disksize for initialized device\n");
return -EBUSY;
}
- ret = strict_strtoull(buf, 10, &zram->disksize);
- if (ret)
- return ret;
-
- zram->disksize = PAGE_ALIGN(zram->disksize);
+ zram->disksize = PAGE_ALIGN(disksize);
set_capacity(zram->disk, zram->disksize >> SECTOR_SHIFT);
+ up_write(&zram->init_lock);
return len;
}
@@ -106,8 +110,10 @@ static ssize_t reset_store(struct device *dev,
if (bdev)
fsync_bdev(bdev);
+ down_write(&zram->init_lock);
if (zram->init_done)
- zram_reset_device(zram);
+ __zram_reset_device(zram);
+ up_write(&zram->init_lock);
return len;
}