From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:33826) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VijRc-0002mF-6I for qemu-devel@nongnu.org; Tue, 19 Nov 2013 06:26:16 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1VijRX-0006bu-DZ for qemu-devel@nongnu.org; Tue, 19 Nov 2013 06:26:12 -0500 Received: from mx1.redhat.com ([209.132.183.28]:26562) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VijRX-0006bk-5J for qemu-devel@nongnu.org; Tue, 19 Nov 2013 06:26:07 -0500 Date: Tue, 19 Nov 2013 12:26:01 +0100 From: Kevin Wolf Message-ID: <20131119112601.GD4040@dhcp-200-207.str.redhat.com> References: <1384121021-24815-1-git-send-email-xiawenc@linux.vnet.ibm.com> <1384121021-24815-3-git-send-email-xiawenc@linux.vnet.ibm.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1384121021-24815-3-git-send-email-xiawenc@linux.vnet.ibm.com> Subject: Re: [Qemu-devel] [PATCH V5 2/5] qemu-nbd: support internal snapshot export List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: Wenchao Xia Cc: pbonzini@redhat.com, jcody@redhat.com, qemu-devel@nongnu.org, stefanha@redhat.com Am 10.11.2013 um 23:03 hat Wenchao Xia geschrieben: > Now it is possible to directly export an internal snapshot, which > can be used to probe the snapshot's contents without qemu-img > convert. > > Signed-off-by: Wenchao Xia > --- > block/snapshot.c | 18 +++++++++++++++++ > include/block/snapshot.h | 8 +++++++ > qemu-nbd.c | 47 ++++++++++++++++++++++++++++++++++++++++++++- > qemu-nbd.texi | 8 ++++++- > 4 files changed, 78 insertions(+), 3 deletions(-) > > diff --git a/block/snapshot.c b/block/snapshot.c > index e51a7db..7cc45fa 100644 > --- a/block/snapshot.c > +++ b/block/snapshot.c > @@ -25,6 +25,24 @@ > #include "block/snapshot.h" > #include "block/block_int.h" > > +QemuOptsList internal_snapshot_opts = { > + .name = "snapshot", > + .head = QTAILQ_HEAD_INITIALIZER(internal_snapshot_opts.head), > + .desc = { > + { > + .name = SNAPSHOT_OPT_ID, > + .type = QEMU_OPT_STRING, > + .help = "snapshot id" > + },{ > + .name = SNAPSHOT_OPT_NAME, > + .type = QEMU_OPT_STRING, > + .help = "snapshot name" > + },{ > + /* end of list */ > + } > + }, > +}; > + > int bdrv_snapshot_find(BlockDriverState *bs, QEMUSnapshotInfo *sn_info, > const char *name) > { > diff --git a/include/block/snapshot.h b/include/block/snapshot.h > index d05bea7..770d9bb 100644 > --- a/include/block/snapshot.h > +++ b/include/block/snapshot.h > @@ -27,6 +27,14 @@ > > #include "qemu-common.h" > #include "qapi/error.h" > +#include "qemu/option.h" > + > + > +#define SNAPSHOT_OPT_BASE "snapshot." > +#define SNAPSHOT_OPT_ID "snapshot.id" > +#define SNAPSHOT_OPT_NAME "snapshot.name" > + > +extern QemuOptsList internal_snapshot_opts; > > typedef struct QEMUSnapshotInfo { > char id_str[128]; /* unique snapshot id */ > diff --git a/qemu-nbd.c b/qemu-nbd.c > index c26c98e..f934eaa 100644 > --- a/qemu-nbd.c > +++ b/qemu-nbd.c > @@ -20,6 +20,7 @@ > #include "block/block.h" > #include "block/nbd.h" > #include "qemu/main-loop.h" > +#include "block/snapshot.h" > > #include > #include > @@ -79,7 +80,14 @@ static void usage(const char *name) > "\n" > "Block device options:\n" > " -r, --read-only export read-only\n" > -" -s, --snapshot use snapshot file\n" > +" -s, --snapshot use FILE as an external snapshot, create a temporary\n" > +" file with backing_file=FILE, redirect the write to\n" > +" the temporary one\n" > +" -l, --load-snapshot=SNAPSHOT_PARAM\n" > +" load an internal snapshot inside FILE and export it\n" > +" as an read-only device, SNAPSHOT_PARAM format is\n" > +" 'snapshot.id=[ID],snapshot.name=[NAME]', or\n" > +" '[ID_OR_NAME]'\n" > " -n, --nocache disable host cache\n" > " --cache=MODE set cache mode (none, writeback, ...)\n" > #ifdef CONFIG_LINUX_AIO > @@ -315,7 +323,9 @@ int main(int argc, char **argv) > char *device = NULL; > int port = NBD_DEFAULT_PORT; > off_t fd_size; > - const char *sopt = "hVb:o:p:rsnP:c:dvk:e:f:t"; > + QemuOpts *sn_opts = NULL; > + const char *sn_id_or_name = NULL; > + const char *sopt = "hVb:o:p:rsnP:c:dvk:e:f:tl:"; > struct option lopt[] = { > { "help", 0, NULL, 'h' }, > { "version", 0, NULL, 'V' }, > @@ -328,6 +338,7 @@ int main(int argc, char **argv) > { "connect", 1, NULL, 'c' }, > { "disconnect", 0, NULL, 'd' }, > { "snapshot", 0, NULL, 's' }, > + { "load-snapshot", 1, NULL, 'l' }, > { "nocache", 0, NULL, 'n' }, > { "cache", 1, NULL, QEMU_NBD_OPT_CACHE }, > #ifdef CONFIG_LINUX_AIO > @@ -428,6 +439,18 @@ int main(int argc, char **argv) > errx(EXIT_FAILURE, "Offset must be positive `%s'", optarg); > } > break; > + case 'l': > + if (strncmp(optarg, SNAPSHOT_OPT_BASE, strlen(SNAPSHOT_OPT_BASE)) > + == 0) { You can avoid this ugly line break by using strstart(): if (strstart(optarg, SNAPSHOT_OPT_BASE, NULL)) { ... Kevin