aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/md/dm-cache-target.c13
1 files changed, 6 insertions, 7 deletions
diff --git a/drivers/md/dm-cache-target.c b/drivers/md/dm-cache-target.c
index 5f054c44b485..2c63326638b6 100644
--- a/drivers/md/dm-cache-target.c
+++ b/drivers/md/dm-cache-target.c
@@ -231,7 +231,7 @@ struct cache {
231 /* 231 /*
232 * cache_size entries, dirty if set 232 * cache_size entries, dirty if set
233 */ 233 */
234 dm_cblock_t nr_dirty; 234 atomic_t nr_dirty;
235 unsigned long *dirty_bitset; 235 unsigned long *dirty_bitset;
236 236
237 /* 237 /*
@@ -492,7 +492,7 @@ static bool is_dirty(struct cache *cache, dm_cblock_t b)
492static void set_dirty(struct cache *cache, dm_oblock_t oblock, dm_cblock_t cblock) 492static void set_dirty(struct cache *cache, dm_oblock_t oblock, dm_cblock_t cblock)
493{ 493{
494 if (!test_and_set_bit(from_cblock(cblock), cache->dirty_bitset)) { 494 if (!test_and_set_bit(from_cblock(cblock), cache->dirty_bitset)) {
495 cache->nr_dirty = to_cblock(from_cblock(cache->nr_dirty) + 1); 495 atomic_inc(&cache->nr_dirty);
496 policy_set_dirty(cache->policy, oblock); 496 policy_set_dirty(cache->policy, oblock);
497 } 497 }
498} 498}
@@ -501,8 +501,7 @@ static void clear_dirty(struct cache *cache, dm_oblock_t oblock, dm_cblock_t cbl
501{ 501{
502 if (test_and_clear_bit(from_cblock(cblock), cache->dirty_bitset)) { 502 if (test_and_clear_bit(from_cblock(cblock), cache->dirty_bitset)) {
503 policy_clear_dirty(cache->policy, oblock); 503 policy_clear_dirty(cache->policy, oblock);
504 cache->nr_dirty = to_cblock(from_cblock(cache->nr_dirty) - 1); 504 if (atomic_dec_return(&cache->nr_dirty) == 0)
505 if (!from_cblock(cache->nr_dirty))
506 dm_table_event(cache->ti->table); 505 dm_table_event(cache->ti->table);
507 } 506 }
508} 507}
@@ -2269,7 +2268,7 @@ static int cache_create(struct cache_args *ca, struct cache **result)
2269 atomic_set(&cache->quiescing_ack, 0); 2268 atomic_set(&cache->quiescing_ack, 0);
2270 2269
2271 r = -ENOMEM; 2270 r = -ENOMEM;
2272 cache->nr_dirty = 0; 2271 atomic_set(&cache->nr_dirty, 0);
2273 cache->dirty_bitset = alloc_bitset(from_cblock(cache->cache_size)); 2272 cache->dirty_bitset = alloc_bitset(from_cblock(cache->cache_size));
2274 if (!cache->dirty_bitset) { 2273 if (!cache->dirty_bitset) {
2275 *error = "could not allocate dirty bitset"; 2274 *error = "could not allocate dirty bitset";
@@ -2808,7 +2807,7 @@ static void cache_status(struct dm_target *ti, status_type_t type,
2808 2807
2809 residency = policy_residency(cache->policy); 2808 residency = policy_residency(cache->policy);
2810 2809
2811 DMEMIT("%u %llu/%llu %u %llu/%llu %u %u %u %u %u %u %llu ", 2810 DMEMIT("%u %llu/%llu %u %llu/%llu %u %u %u %u %u %u %lu ",
2812 (unsigned)(DM_CACHE_METADATA_BLOCK_SIZE >> SECTOR_SHIFT), 2811 (unsigned)(DM_CACHE_METADATA_BLOCK_SIZE >> SECTOR_SHIFT),
2813 (unsigned long long)(nr_blocks_metadata - nr_free_blocks_metadata), 2812 (unsigned long long)(nr_blocks_metadata - nr_free_blocks_metadata),
2814 (unsigned long long)nr_blocks_metadata, 2813 (unsigned long long)nr_blocks_metadata,
@@ -2821,7 +2820,7 @@ static void cache_status(struct dm_target *ti, status_type_t type,
2821 (unsigned) atomic_read(&cache->stats.write_miss), 2820 (unsigned) atomic_read(&cache->stats.write_miss),
2822 (unsigned) atomic_read(&cache->stats.demotion), 2821 (unsigned) atomic_read(&cache->stats.demotion),
2823 (unsigned) atomic_read(&cache->stats.promotion), 2822 (unsigned) atomic_read(&cache->stats.promotion),
2824 (unsigned long long) from_cblock(cache->nr_dirty)); 2823 (unsigned long) atomic_read(&cache->nr_dirty));
2825 2824
2826 if (writethrough_mode(&cache->features)) 2825 if (writethrough_mode(&cache->features))
2827 DMEMIT("1 writethrough "); 2826 DMEMIT("1 writethrough ");