dm snapshot: do not use map_context
Eliminate struct map_info from dm-snap. map_info->ptr was used in dm-snap to indicate if the bio was tracked. If map_info->ptr was non-NULL, the bio was linked in tracked_chunk_hash. This patch removes the use of map_info->ptr. We determine if the bio was tracked based on hlist_unhashed(&c->node). If hlist_unhashed is true, the bio is not tracked, if it is false, the bio is tracked. Signed-off-by: Mikulas Patocka <mpatocka@redhat.com> Signed-off-by: Alasdair G Kergon <agk@redhat.com>
This commit is contained in:
parent
59c3d2c6a1
commit
ee18026ac6
1 changed files with 23 additions and 13 deletions
|
@ -190,9 +190,19 @@ struct dm_snap_tracked_chunk {
|
||||||
chunk_t chunk;
|
chunk_t chunk;
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct dm_snap_tracked_chunk *track_chunk(struct dm_snapshot *s,
|
static void init_tracked_chunk(struct bio *bio)
|
||||||
struct bio *bio,
|
{
|
||||||
chunk_t chunk)
|
struct dm_snap_tracked_chunk *c = dm_per_bio_data(bio, sizeof(struct dm_snap_tracked_chunk));
|
||||||
|
INIT_HLIST_NODE(&c->node);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool is_bio_tracked(struct bio *bio)
|
||||||
|
{
|
||||||
|
struct dm_snap_tracked_chunk *c = dm_per_bio_data(bio, sizeof(struct dm_snap_tracked_chunk));
|
||||||
|
return !hlist_unhashed(&c->node);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void track_chunk(struct dm_snapshot *s, struct bio *bio, chunk_t chunk)
|
||||||
{
|
{
|
||||||
struct dm_snap_tracked_chunk *c = dm_per_bio_data(bio, sizeof(struct dm_snap_tracked_chunk));
|
struct dm_snap_tracked_chunk *c = dm_per_bio_data(bio, sizeof(struct dm_snap_tracked_chunk));
|
||||||
|
|
||||||
|
@ -202,13 +212,11 @@ static struct dm_snap_tracked_chunk *track_chunk(struct dm_snapshot *s,
|
||||||
hlist_add_head(&c->node,
|
hlist_add_head(&c->node,
|
||||||
&s->tracked_chunk_hash[DM_TRACKED_CHUNK_HASH(chunk)]);
|
&s->tracked_chunk_hash[DM_TRACKED_CHUNK_HASH(chunk)]);
|
||||||
spin_unlock_irq(&s->tracked_chunk_lock);
|
spin_unlock_irq(&s->tracked_chunk_lock);
|
||||||
|
|
||||||
return c;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void stop_tracking_chunk(struct dm_snapshot *s,
|
static void stop_tracking_chunk(struct dm_snapshot *s, struct bio *bio)
|
||||||
struct dm_snap_tracked_chunk *c)
|
|
||||||
{
|
{
|
||||||
|
struct dm_snap_tracked_chunk *c = dm_per_bio_data(bio, sizeof(struct dm_snap_tracked_chunk));
|
||||||
unsigned long flags;
|
unsigned long flags;
|
||||||
|
|
||||||
spin_lock_irqsave(&s->tracked_chunk_lock, flags);
|
spin_lock_irqsave(&s->tracked_chunk_lock, flags);
|
||||||
|
@ -1568,6 +1576,8 @@ static int snapshot_map(struct dm_target *ti, struct bio *bio,
|
||||||
chunk_t chunk;
|
chunk_t chunk;
|
||||||
struct dm_snap_pending_exception *pe = NULL;
|
struct dm_snap_pending_exception *pe = NULL;
|
||||||
|
|
||||||
|
init_tracked_chunk(bio);
|
||||||
|
|
||||||
if (bio->bi_rw & REQ_FLUSH) {
|
if (bio->bi_rw & REQ_FLUSH) {
|
||||||
bio->bi_bdev = s->cow->bdev;
|
bio->bi_bdev = s->cow->bdev;
|
||||||
return DM_MAPIO_REMAPPED;
|
return DM_MAPIO_REMAPPED;
|
||||||
|
@ -1652,7 +1662,7 @@ static int snapshot_map(struct dm_target *ti, struct bio *bio,
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
bio->bi_bdev = s->origin->bdev;
|
bio->bi_bdev = s->origin->bdev;
|
||||||
map_context->ptr = track_chunk(s, bio, chunk);
|
track_chunk(s, bio, chunk);
|
||||||
}
|
}
|
||||||
|
|
||||||
out_unlock:
|
out_unlock:
|
||||||
|
@ -1681,12 +1691,13 @@ static int snapshot_merge_map(struct dm_target *ti, struct bio *bio,
|
||||||
int r = DM_MAPIO_REMAPPED;
|
int r = DM_MAPIO_REMAPPED;
|
||||||
chunk_t chunk;
|
chunk_t chunk;
|
||||||
|
|
||||||
|
init_tracked_chunk(bio);
|
||||||
|
|
||||||
if (bio->bi_rw & REQ_FLUSH) {
|
if (bio->bi_rw & REQ_FLUSH) {
|
||||||
if (!dm_bio_get_target_request_nr(bio))
|
if (!dm_bio_get_target_request_nr(bio))
|
||||||
bio->bi_bdev = s->origin->bdev;
|
bio->bi_bdev = s->origin->bdev;
|
||||||
else
|
else
|
||||||
bio->bi_bdev = s->cow->bdev;
|
bio->bi_bdev = s->cow->bdev;
|
||||||
map_context->ptr = NULL;
|
|
||||||
return DM_MAPIO_REMAPPED;
|
return DM_MAPIO_REMAPPED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1715,7 +1726,7 @@ static int snapshot_merge_map(struct dm_target *ti, struct bio *bio,
|
||||||
remap_exception(s, e, bio, chunk);
|
remap_exception(s, e, bio, chunk);
|
||||||
|
|
||||||
if (bio_rw(bio) == WRITE)
|
if (bio_rw(bio) == WRITE)
|
||||||
map_context->ptr = track_chunk(s, bio, chunk);
|
track_chunk(s, bio, chunk);
|
||||||
goto out_unlock;
|
goto out_unlock;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1737,10 +1748,9 @@ static int snapshot_end_io(struct dm_target *ti, struct bio *bio,
|
||||||
int error, union map_info *map_context)
|
int error, union map_info *map_context)
|
||||||
{
|
{
|
||||||
struct dm_snapshot *s = ti->private;
|
struct dm_snapshot *s = ti->private;
|
||||||
struct dm_snap_tracked_chunk *c = map_context->ptr;
|
|
||||||
|
|
||||||
if (c)
|
if (is_bio_tracked(bio))
|
||||||
stop_tracking_chunk(s, c);
|
stop_tracking_chunk(s, bio);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue