Implement a shared store target in libdevmapper. Signed-off-by: Mikulas Patocka --- libdm/libdevmapper.h | 6 ++++++ libdm/libdm-deptree.c | 32 +++++++++++++++++++++++++++----- 2 files changed, 33 insertions(+), 5 deletions(-) Index: LVM2.2.02.85/libdm/libdevmapper.h =================================================================== --- LVM2.2.02.85.orig/libdm/libdevmapper.h 2011-05-23 15:58:55.000000000 +0200 +++ LVM2.2.02.85/libdm/libdevmapper.h 2011-05-23 15:59:23.000000000 +0200 @@ -416,6 +416,12 @@ int dm_tree_node_add_snapshot_merge_targ const char *cow_uuid, const char *merge_uuid, uint32_t chunk_size); +int dm_tree_node_add_snapshot_shared_target(struct dm_tree_node *node, + uint64_t size, + const char *origin_uuid, + const char *cow_uuid, + const char *exception_store, + uint32_t chunk_size); int dm_tree_node_add_error_target(struct dm_tree_node *node, uint64_t size); int dm_tree_node_add_zero_target(struct dm_tree_node *node, Index: LVM2.2.02.85/libdm/libdm-deptree.c =================================================================== --- LVM2.2.02.85.orig/libdm/libdm-deptree.c 2011-05-23 15:58:55.000000000 +0200 +++ LVM2.2.02.85/libdm/libdm-deptree.c 2011-05-23 15:59:23.000000000 +0200 @@ -40,6 +40,7 @@ enum { SEG_SNAPSHOT, SEG_SNAPSHOT_ORIGIN, SEG_SNAPSHOT_MERGE, + SEG_SNAPSHOT_SHARED, SEG_STRIPED, SEG_ZERO, }; @@ -59,6 +60,7 @@ struct { { SEG_SNAPSHOT, "snapshot" }, { SEG_SNAPSHOT_ORIGIN, "snapshot-origin" }, { SEG_SNAPSHOT_MERGE, "snapshot-merge" }, + { SEG_SNAPSHOT_SHARED, "multisnapshot" }, { SEG_STRIPED, "striped" }, { SEG_ZERO, "zero"}, }; @@ -1704,6 +1706,14 @@ static int _emit_segment_line(struct dm_ return_0; EMIT_PARAMS(pos, "%s", originbuf); break; + case SEG_SNAPSHOT_SHARED: + if (!_build_dev_string(originbuf, sizeof(originbuf), seg->origin)) + return_0; + if (!_build_dev_string(cowbuf, sizeof(cowbuf), seg->cow)) + return_0; + EMIT_PARAMS(pos, "%s %s %d 0 %s 0", originbuf, cowbuf, + seg->chunk_size, seg->exception_store); + break; case SEG_STRIPED: EMIT_PARAMS(pos, "%u %u ", seg->area_count, seg->stripe_size); break; @@ -1722,6 +1732,7 @@ static int _emit_segment_line(struct dm_ case SEG_SNAPSHOT: case SEG_SNAPSHOT_ORIGIN: case SEG_SNAPSHOT_MERGE: + case SEG_SNAPSHOT_SHARED: case SEG_ZERO: break; case SEG_CRYPT: @@ -2013,14 +2024,12 @@ static int _add_snapshot_target(struct d const char *origin_uuid, const char *cow_uuid, const char *merge_uuid, + unsigned seg_type, const char *exception_store, uint32_t chunk_size) { struct load_segment *seg; struct dm_tree_node *origin_node, *cow_node, *merge_node; - unsigned seg_type; - - seg_type = !merge_uuid ? SEG_SNAPSHOT : SEG_SNAPSHOT_MERGE; if (!(seg = _add_segment(node, seg_type, size))) return_0; @@ -2079,7 +2088,8 @@ int dm_tree_node_add_snapshot_target(str uint32_t chunk_size) { return _add_snapshot_target(node, size, origin_uuid, cow_uuid, - NULL, exception_store, chunk_size); + NULL, SEG_SNAPSHOT, exception_store, + chunk_size); } int dm_tree_node_add_snapshot_merge_target(struct dm_tree_node *node, @@ -2090,7 +2100,19 @@ int dm_tree_node_add_snapshot_merge_targ uint32_t chunk_size) { return _add_snapshot_target(node, size, origin_uuid, cow_uuid, - merge_uuid, "P", chunk_size); + merge_uuid, SEG_SNAPSHOT_MERGE, "P", + chunk_size); +} + +int dm_tree_node_add_snapshot_shared_target(struct dm_tree_node *node, + uint64_t size, + const char *origin_uuid, + const char *cow_uuid, + const char *exception_store, + uint32_t chunk_size) +{ + return _add_snapshot_target(node, size, origin_uuid, cow_uuid, NULL, + SEG_SNAPSHOT_SHARED, exception_store, chunk_size); } int dm_tree_node_add_error_target(struct dm_tree_node *node,