Commit 5f274d88 authored by Joe Thornber's avatar Joe Thornber Committed by Mike Snitzer

dm bio prison: introduce support for locking ranges of blocks

Ranges will be placed in the same cell if they overlap.

Range locking is a prerequisite for more efficient multi-block discard
support in both the cache and thin-provisioning targets.
Signed-off-by: default avatarJoe Thornber <ejt@redhat.com>
Signed-off-by: default avatarMike Snitzer <snitzer@redhat.com>
parent f1afb36a
...@@ -95,10 +95,10 @@ static int cmp_keys(struct dm_cell_key *lhs, ...@@ -95,10 +95,10 @@ static int cmp_keys(struct dm_cell_key *lhs,
if (lhs->dev > rhs->dev) if (lhs->dev > rhs->dev)
return 1; return 1;
if (lhs->block < rhs->block) if (lhs->block_end <= rhs->block_begin)
return -1; return -1;
if (lhs->block > rhs->block) if (lhs->block_begin >= rhs->block_end)
return 1; return 1;
return 0; return 0;
......
...@@ -23,11 +23,14 @@ ...@@ -23,11 +23,14 @@
*/ */
struct dm_bio_prison; struct dm_bio_prison;
/* FIXME: this needs to be more abstract */ /*
* Keys define a range of blocks within either a virtual or physical
* device.
*/
struct dm_cell_key { struct dm_cell_key {
int virtual; int virtual;
dm_thin_id dev; dm_thin_id dev;
dm_block_t block; dm_block_t block_begin, block_end;
}; };
/* /*
...@@ -59,7 +62,7 @@ void dm_bio_prison_free_cell(struct dm_bio_prison *prison, ...@@ -59,7 +62,7 @@ void dm_bio_prison_free_cell(struct dm_bio_prison *prison,
struct dm_bio_prison_cell *cell); struct dm_bio_prison_cell *cell);
/* /*
* Creates, or retrieves a cell for the given key. * Creates, or retrieves a cell that overlaps the given key.
* *
* Returns 1 if pre-existing cell returned, zero if new cell created using * Returns 1 if pre-existing cell returned, zero if new cell created using
* @cell_prealloc. * @cell_prealloc.
...@@ -70,7 +73,8 @@ int dm_get_cell(struct dm_bio_prison *prison, ...@@ -70,7 +73,8 @@ int dm_get_cell(struct dm_bio_prison *prison,
struct dm_bio_prison_cell **cell_result); struct dm_bio_prison_cell **cell_result);
/* /*
* An atomic op that combines retrieving a cell, and adding a bio to it. * An atomic op that combines retrieving or creating a cell, and adding a
* bio to it.
* *
* Returns 1 if the cell was already held, 0 if @inmate is the new holder. * Returns 1 if the cell was already held, 0 if @inmate is the new holder.
*/ */
......
...@@ -436,7 +436,8 @@ static void build_key(dm_oblock_t oblock, struct dm_cell_key *key) ...@@ -436,7 +436,8 @@ static void build_key(dm_oblock_t oblock, struct dm_cell_key *key)
{ {
key->virtual = 0; key->virtual = 0;
key->dev = 0; key->dev = 0;
key->block = from_oblock(oblock); key->block_begin = from_oblock(oblock);
key->block_end = key->block_begin + 1ULL;
} }
/* /*
......
...@@ -115,7 +115,8 @@ static void build_data_key(struct dm_thin_device *td, ...@@ -115,7 +115,8 @@ static void build_data_key(struct dm_thin_device *td,
{ {
key->virtual = 0; key->virtual = 0;
key->dev = dm_thin_dev_id(td); key->dev = dm_thin_dev_id(td);
key->block = b; key->block_begin = b;
key->block_end = b + 1ULL;
} }
static void build_virtual_key(struct dm_thin_device *td, dm_block_t b, static void build_virtual_key(struct dm_thin_device *td, dm_block_t b,
...@@ -123,7 +124,8 @@ static void build_virtual_key(struct dm_thin_device *td, dm_block_t b, ...@@ -123,7 +124,8 @@ static void build_virtual_key(struct dm_thin_device *td, dm_block_t b,
{ {
key->virtual = 1; key->virtual = 1;
key->dev = dm_thin_dev_id(td); key->dev = dm_thin_dev_id(td);
key->block = b; key->block_begin = b;
key->block_end = b + 1ULL;
} }
/*----------------------------------------------------------------*/ /*----------------------------------------------------------------*/
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment