summaryrefslogtreecommitdiff
path: root/block/qcow2-snapshot.c
diff options
context:
space:
mode:
authoredison <edison@cloud.com>2010-09-21 19:58:41 -0700
committerKevin Wolf <kwolf@redhat.com>2010-10-22 14:49:35 +0200
commit51ef67270b1d10e1fcf3de7368dccad1ba0bf9d1 (patch)
treea06b3ce03bae7ed77a1e1e9bebc6ead157c7a4e5 /block/qcow2-snapshot.c
parenta58b8d5401b6064d52113f243456115d046bdd12 (diff)
Copy snapshots out of QCOW2 disk
In order to backup snapshots, created from QCOW2 iamge, we want to copy snapshots out of QCOW2 disk to a seperate storage. The following patch adds a new option in "qemu-img": qemu-img convert -f qcow2 -O qcow2 -s snapshot_name src_img bck_img. Right now, it only supports to copy the full snapshot, delta snapshot is on the way. Changes from V1: all the comments from Kevin are addressed: Add read-only checking Fix coding style Change the name from bdrv_snapshot_load to bdrv_snapshot_load_tmp Signed-off-by: Disheng Su <edison@cloud.com> Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Diffstat (limited to 'block/qcow2-snapshot.c')
-rw-r--r--block/qcow2-snapshot.c31
1 files changed, 31 insertions, 0 deletions
diff --git a/block/qcow2-snapshot.c b/block/qcow2-snapshot.c
index 8dd5df0bcd..aacf357821 100644
--- a/block/qcow2-snapshot.c
+++ b/block/qcow2-snapshot.c
@@ -418,3 +418,34 @@ int qcow2_snapshot_list(BlockDriverState *bs, QEMUSnapshotInfo **psn_tab)
return s->nb_snapshots;
}
+int qcow2_snapshot_load_tmp(BlockDriverState *bs, const char *snapshot_name)
+{
+ int i, snapshot_index, l1_size2;
+ BDRVQcowState *s = bs->opaque;
+ QCowSnapshot *sn;
+
+ snapshot_index = find_snapshot_by_id_or_name(bs, snapshot_name);
+ if (snapshot_index < 0) {
+ return -ENOENT;
+ }
+
+ sn = &s->snapshots[snapshot_index];
+ s->l1_size = sn->l1_size;
+ l1_size2 = s->l1_size * sizeof(uint64_t);
+ if (s->l1_table != NULL) {
+ qemu_free(s->l1_table);
+ }
+
+ s->l1_table_offset = sn->l1_table_offset;
+ s->l1_table = qemu_mallocz(align_offset(l1_size2, 512));
+
+ if (bdrv_pread(bs->file, sn->l1_table_offset,
+ s->l1_table, l1_size2) != l1_size2) {
+ return -1;
+ }
+
+ for(i = 0;i < s->l1_size; i++) {
+ be64_to_cpus(&s->l1_table[i]);
+ }
+ return 0;
+}