diff options
author | Artem Bityutskiy <Artem.Bityutskiy@nokia.com> | 2007-12-17 10:37:26 -0500 |
---|---|---|
committer | Artem Bityutskiy <Artem.Bityutskiy@nokia.com> | 2007-12-26 12:15:17 -0500 |
commit | e73f4459d969bb266f03dd4cbe21bdba8cb2732c (patch) | |
tree | 5af7655da65f2c33f6ea4efdfaa8b0e0670d6aea /drivers/mtd/ubi/vmt.c | |
parent | 9f961b57568960a150cc9781c52824c9093a0514 (diff) |
UBI: add UBI devices reference counting
This is one more step on the way to "removable" UBI devices. It
adds reference counting for UBI devices. Every time a volume on
this device is opened - the device's refcount is increased. It
is also increased if someone is reading any sysfs file of this
UBI device or of one of its volumes.
Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>
Diffstat (limited to 'drivers/mtd/ubi/vmt.c')
-rw-r--r-- | drivers/mtd/ubi/vmt.c | 14 |
1 files changed, 9 insertions, 5 deletions
diff --git a/drivers/mtd/ubi/vmt.c b/drivers/mtd/ubi/vmt.c index 3ed63dc37386..42d3dd70f2d0 100644 --- a/drivers/mtd/ubi/vmt.c +++ b/drivers/mtd/ubi/vmt.c | |||
@@ -71,11 +71,16 @@ static ssize_t vol_attribute_show(struct device *dev, | |||
71 | { | 71 | { |
72 | int ret; | 72 | int ret; |
73 | struct ubi_volume *vol = container_of(dev, struct ubi_volume, dev); | 73 | struct ubi_volume *vol = container_of(dev, struct ubi_volume, dev); |
74 | struct ubi_device *ubi = vol->ubi; | 74 | struct ubi_device *ubi; |
75 | |||
76 | ubi = ubi_get_device(vol->ubi->ubi_num); | ||
77 | if (!ubi) | ||
78 | return -ENODEV; | ||
75 | 79 | ||
76 | spin_lock(&ubi->volumes_lock); | 80 | spin_lock(&ubi->volumes_lock); |
77 | if (!ubi->volumes[vol->vol_id]) { | 81 | if (!ubi->volumes[vol->vol_id]) { |
78 | spin_unlock(&ubi->volumes_lock); | 82 | spin_unlock(&ubi->volumes_lock); |
83 | ubi_put_device(ubi); | ||
79 | return -ENODEV; | 84 | return -ENODEV; |
80 | } | 85 | } |
81 | /* Take a reference to prevent volume removal */ | 86 | /* Take a reference to prevent volume removal */ |
@@ -108,10 +113,12 @@ static ssize_t vol_attribute_show(struct device *dev, | |||
108 | /* This must be a bug */ | 113 | /* This must be a bug */ |
109 | ret = -EINVAL; | 114 | ret = -EINVAL; |
110 | 115 | ||
116 | /* We've done the operation, drop volume and UBI device references */ | ||
111 | spin_lock(&ubi->volumes_lock); | 117 | spin_lock(&ubi->volumes_lock); |
112 | vol->ref_count -= 1; | 118 | vol->ref_count -= 1; |
113 | ubi_assert(vol->ref_count >= 0); | 119 | ubi_assert(vol->ref_count >= 0); |
114 | spin_unlock(&ubi->volumes_lock); | 120 | spin_unlock(&ubi->volumes_lock); |
121 | ubi_put_device(ubi); | ||
115 | return ret; | 122 | return ret; |
116 | } | 123 | } |
117 | 124 | ||
@@ -260,6 +267,7 @@ int ubi_create_volume(struct ubi_device *ubi, struct ubi_mkvol_req *req) | |||
260 | } | 267 | } |
261 | ubi->avail_pebs -= vol->reserved_pebs; | 268 | ubi->avail_pebs -= vol->reserved_pebs; |
262 | ubi->rsvd_pebs += vol->reserved_pebs; | 269 | ubi->rsvd_pebs += vol->reserved_pebs; |
270 | spin_unlock(&ubi->volumes_lock); | ||
263 | 271 | ||
264 | vol->vol_id = vol_id; | 272 | vol->vol_id = vol_id; |
265 | vol->alignment = req->alignment; | 273 | vol->alignment = req->alignment; |
@@ -267,9 +275,7 @@ int ubi_create_volume(struct ubi_device *ubi, struct ubi_mkvol_req *req) | |||
267 | vol->vol_type = req->vol_type; | 275 | vol->vol_type = req->vol_type; |
268 | vol->name_len = req->name_len; | 276 | vol->name_len = req->name_len; |
269 | memcpy(vol->name, req->name, vol->name_len + 1); | 277 | memcpy(vol->name, req->name, vol->name_len + 1); |
270 | vol->exclusive = 1; | ||
271 | vol->ubi = ubi; | 278 | vol->ubi = ubi; |
272 | spin_unlock(&ubi->volumes_lock); | ||
273 | 279 | ||
274 | /* | 280 | /* |
275 | * Finish all pending erases because there may be some LEBs belonging | 281 | * Finish all pending erases because there may be some LEBs belonging |
@@ -350,8 +356,6 @@ int ubi_create_volume(struct ubi_device *ubi, struct ubi_mkvol_req *req) | |||
350 | goto out_sysfs; | 356 | goto out_sysfs; |
351 | 357 | ||
352 | spin_lock(&ubi->volumes_lock); | 358 | spin_lock(&ubi->volumes_lock); |
353 | ubi->vol_count += 1; | ||
354 | vol->exclusive = 0; | ||
355 | ubi->volumes[vol_id] = vol; | 359 | ubi->volumes[vol_id] = vol; |
356 | spin_unlock(&ubi->volumes_lock); | 360 | spin_unlock(&ubi->volumes_lock); |
357 | 361 | ||