blob: 5b6e64844ee9e3633a72b2b11c9aada0b8c67c85 [file] [log] [blame]
bellardea2384d2004-08-01 21:59:26 +00001/*
bellardfb43f4d2006-08-07 21:34:46 +00002 * QEMU disk image utility
ths5fafdf22007-09-16 21:08:06 +00003 *
bellard68d0f702008-01-06 17:21:48 +00004 * Copyright (c) 2003-2008 Fabrice Bellard
ths5fafdf22007-09-16 21:08:06 +00005 *
bellardea2384d2004-08-01 21:59:26 +00006 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 * THE SOFTWARE.
23 */
pbrookfaf07962007-11-11 02:51:17 +000024#include "qemu-common.h"
Kevin Wolf9ea2ea72009-05-18 16:42:11 +020025#include "qemu-option.h"
aliguorif7b4a942009-01-07 17:40:15 +000026#include "osdep.h"
Jes Sorensendc786bc2010-10-26 10:39:23 +020027#include "sysemu.h"
thsec36ba12007-09-16 21:59:02 +000028#include "block_int.h"
aliguori9230eaf2009-03-28 17:55:19 +000029#include <stdio.h>
bellardea2384d2004-08-01 21:59:26 +000030
bellarde8445332006-06-14 15:32:10 +000031#ifdef _WIN32
32#include <windows.h>
33#endif
34
Anthony Liguoric227f092009-10-01 16:12:16 -050035typedef struct img_cmd_t {
Stuart Brady153859b2009-06-07 00:42:17 +010036 const char *name;
37 int (*handler)(int argc, char **argv);
Anthony Liguoric227f092009-10-01 16:12:16 -050038} img_cmd_t;
Stuart Brady153859b2009-06-07 00:42:17 +010039
aurel32137519c2008-11-30 19:12:49 +000040/* Default to cache=writeback as data integrity is not important for qemu-tcg. */
Stefan Hajnocziadfe0782010-04-13 10:29:35 +010041#define BDRV_O_FLAGS BDRV_O_CACHE_WB
aurel32137519c2008-11-30 19:12:49 +000042
Stefan Weil8b7968f2010-09-23 21:28:05 +020043static void GCC_FMT_ATTR(1, 2) error(const char *fmt, ...)
bellardea2384d2004-08-01 21:59:26 +000044{
45 va_list ap;
46 va_start(ap, fmt);
bellard57d1a2b2004-08-03 21:15:11 +000047 fprintf(stderr, "qemu-img: ");
bellardea2384d2004-08-01 21:59:26 +000048 vfprintf(stderr, fmt, ap);
49 fprintf(stderr, "\n");
bellardea2384d2004-08-01 21:59:26 +000050 va_end(ap);
51}
52
53static void format_print(void *opaque, const char *name)
54{
55 printf(" %s", name);
56}
57
blueswir1d2c639d2009-01-24 18:19:25 +000058/* Please keep in synch with qemu-img.texi */
pbrook3f379ab2007-11-11 03:33:13 +000059static void help(void)
bellardea2384d2004-08-01 21:59:26 +000060{
Paolo Bonzinie00291c2010-02-04 16:49:56 +010061 const char *help_msg =
62 "qemu-img version " QEMU_VERSION ", Copyright (c) 2004-2008 Fabrice Bellard\n"
malc3f020d72010-02-08 12:04:56 +030063 "usage: qemu-img command [command options]\n"
64 "QEMU disk image utility\n"
65 "\n"
66 "Command syntax:\n"
Stuart Brady153859b2009-06-07 00:42:17 +010067#define DEF(option, callback, arg_string) \
68 " " arg_string "\n"
69#include "qemu-img-cmds.h"
70#undef DEF
71#undef GEN_DOCS
malc3f020d72010-02-08 12:04:56 +030072 "\n"
73 "Command parameters:\n"
74 " 'filename' is a disk image filename\n"
75 " 'fmt' is the disk image format. It is guessed automatically in most cases\n"
76 " 'size' is the disk image size in bytes. Optional suffixes\n"
77 " 'k' or 'K' (kilobyte, 1024), 'M' (megabyte, 1024k), 'G' (gigabyte, 1024M)\n"
78 " and T (terabyte, 1024G) are supported. 'b' is ignored.\n"
79 " 'output_filename' is the destination disk image filename\n"
80 " 'output_fmt' is the destination format\n"
81 " 'options' is a comma separated list of format specific options in a\n"
82 " name=value format. Use -o ? for an overview of the options supported by the\n"
83 " used format\n"
84 " '-c' indicates that target image must be compressed (qcow format only)\n"
85 " '-u' enables unsafe rebasing. It is assumed that old and new backing file\n"
86 " match exactly. The image doesn't need a working backing file before\n"
87 " rebasing in this case (useful for renaming the backing file)\n"
88 " '-h' with or without a command shows this help and lists the supported formats\n"
89 "\n"
90 "Parameters to snapshot subcommand:\n"
91 " 'snapshot' is the name of the snapshot to create, apply or delete\n"
92 " '-a' applies a snapshot (revert disk to saved state)\n"
93 " '-c' creates a snapshot\n"
94 " '-d' deletes a snapshot\n"
Paolo Bonzinie00291c2010-02-04 16:49:56 +010095 " '-l' lists all snapshots in the given image\n";
96
97 printf("%s\nSupported formats:", help_msg);
bellardea2384d2004-08-01 21:59:26 +000098 bdrv_iterate_format(format_print, NULL);
99 printf("\n");
100 exit(1);
101}
102
bellardea2384d2004-08-01 21:59:26 +0000103#if defined(WIN32)
104/* XXX: put correct support for win32 */
105static int read_password(char *buf, int buf_size)
106{
107 int c, i;
108 printf("Password: ");
109 fflush(stdout);
110 i = 0;
111 for(;;) {
112 c = getchar();
113 if (c == '\n')
114 break;
115 if (i < (buf_size - 1))
116 buf[i++] = c;
117 }
118 buf[i] = '\0';
119 return 0;
120}
121
122#else
123
124#include <termios.h>
125
126static struct termios oldtty;
127
128static void term_exit(void)
129{
130 tcsetattr (0, TCSANOW, &oldtty);
131}
132
133static void term_init(void)
134{
135 struct termios tty;
136
137 tcgetattr (0, &tty);
138 oldtty = tty;
139
140 tty.c_iflag &= ~(IGNBRK|BRKINT|PARMRK|ISTRIP
141 |INLCR|IGNCR|ICRNL|IXON);
142 tty.c_oflag |= OPOST;
143 tty.c_lflag &= ~(ECHO|ECHONL|ICANON|IEXTEN);
144 tty.c_cflag &= ~(CSIZE|PARENB);
145 tty.c_cflag |= CS8;
146 tty.c_cc[VMIN] = 1;
147 tty.c_cc[VTIME] = 0;
ths3b46e622007-09-17 08:09:54 +0000148
bellardea2384d2004-08-01 21:59:26 +0000149 tcsetattr (0, TCSANOW, &tty);
150
151 atexit(term_exit);
152}
153
pbrook3f379ab2007-11-11 03:33:13 +0000154static int read_password(char *buf, int buf_size)
bellardea2384d2004-08-01 21:59:26 +0000155{
156 uint8_t ch;
157 int i, ret;
158
159 printf("password: ");
160 fflush(stdout);
161 term_init();
162 i = 0;
163 for(;;) {
164 ret = read(0, &ch, 1);
165 if (ret == -1) {
166 if (errno == EAGAIN || errno == EINTR) {
167 continue;
168 } else {
169 ret = -1;
170 break;
171 }
172 } else if (ret == 0) {
173 ret = -1;
174 break;
175 } else {
176 if (ch == '\r') {
177 ret = 0;
178 break;
179 }
180 if (i < (buf_size - 1))
181 buf[i++] = ch;
182 }
183 }
184 term_exit();
185 buf[i] = '\0';
186 printf("\n");
187 return ret;
188}
189#endif
190
Jes Sorensen4ac8aac2010-12-06 15:25:38 +0100191static int print_block_option_help(const char *filename, const char *fmt)
192{
193 BlockDriver *drv, *proto_drv;
194 QEMUOptionParameter *create_options = NULL;
195
196 /* Find driver and parse its options */
197 drv = bdrv_find_format(fmt);
198 if (!drv) {
199 error("Unknown file format '%s'", fmt);
200 return 1;
201 }
202
203 proto_drv = bdrv_find_protocol(filename);
204 if (!proto_drv) {
205 error("Unknown protocol '%s'", filename);
206 return 1;
207 }
208
209 create_options = append_option_parameters(create_options,
210 drv->create_options);
211 create_options = append_option_parameters(create_options,
212 proto_drv->create_options);
213 print_option_help(create_options);
214 free_option_parameters(create_options);
215 return 0;
216}
217
bellard75c23802004-08-27 21:28:58 +0000218static BlockDriverState *bdrv_new_open(const char *filename,
Sheng Yang9bc378c2010-01-29 10:15:06 +0800219 const char *fmt,
Stefan Hajnoczif163d072010-04-13 10:29:34 +0100220 int flags)
bellard75c23802004-08-27 21:28:58 +0000221{
222 BlockDriverState *bs;
223 BlockDriver *drv;
224 char password[256];
225
226 bs = bdrv_new("");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900227 if (!bs) {
bellard75c23802004-08-27 21:28:58 +0000228 error("Not enough memory");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900229 goto fail;
230 }
bellard75c23802004-08-27 21:28:58 +0000231 if (fmt) {
232 drv = bdrv_find_format(fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900233 if (!drv) {
bellard75c23802004-08-27 21:28:58 +0000234 error("Unknown file format '%s'", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900235 goto fail;
236 }
bellard75c23802004-08-27 21:28:58 +0000237 } else {
238 drv = NULL;
239 }
Kevin Wolfd6e90982010-03-31 14:40:27 +0200240 if (bdrv_open(bs, filename, flags, drv) < 0) {
bellard75c23802004-08-27 21:28:58 +0000241 error("Could not open '%s'", filename);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900242 goto fail;
bellard75c23802004-08-27 21:28:58 +0000243 }
244 if (bdrv_is_encrypted(bs)) {
245 printf("Disk image '%s' is encrypted.\n", filename);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900246 if (read_password(password, sizeof(password)) < 0) {
bellard75c23802004-08-27 21:28:58 +0000247 error("No password given");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900248 goto fail;
249 }
250 if (bdrv_set_key(bs, password) < 0) {
bellard75c23802004-08-27 21:28:58 +0000251 error("invalid password");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900252 goto fail;
253 }
bellard75c23802004-08-27 21:28:58 +0000254 }
255 return bs;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900256fail:
257 if (bs) {
258 bdrv_delete(bs);
259 }
260 return NULL;
bellard75c23802004-08-27 21:28:58 +0000261}
262
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900263static int add_old_style_options(const char *fmt, QEMUOptionParameter *list,
Kevin Wolfefa84d42009-05-18 16:42:12 +0200264 int flags, const char *base_filename, const char *base_fmt)
265{
266 if (flags & BLOCK_FLAG_ENCRYPT) {
267 if (set_option_parameter(list, BLOCK_OPT_ENCRYPT, "on")) {
268 error("Encryption not supported for file format '%s'", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900269 return -1;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200270 }
271 }
272 if (flags & BLOCK_FLAG_COMPAT6) {
273 if (set_option_parameter(list, BLOCK_OPT_COMPAT6, "on")) {
274 error("VMDK version 6 not supported for file format '%s'", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900275 return -1;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200276 }
277 }
278
279 if (base_filename) {
280 if (set_option_parameter(list, BLOCK_OPT_BACKING_FILE, base_filename)) {
281 error("Backing file not supported for file format '%s'", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900282 return -1;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200283 }
284 }
285 if (base_fmt) {
286 if (set_option_parameter(list, BLOCK_OPT_BACKING_FMT, base_fmt)) {
287 error("Backing file format not supported for file format '%s'", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900288 return -1;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200289 }
290 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900291 return 0;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200292}
293
bellardea2384d2004-08-01 21:59:26 +0000294static int img_create(int argc, char **argv)
295{
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900296 int c, ret = 0, flags;
bellardea2384d2004-08-01 21:59:26 +0000297 const char *fmt = "raw";
aliguori9230eaf2009-03-28 17:55:19 +0000298 const char *base_fmt = NULL;
bellardea2384d2004-08-01 21:59:26 +0000299 const char *filename;
300 const char *base_filename = NULL;
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900301 BlockDriver *drv, *proto_drv;
302 QEMUOptionParameter *param = NULL, *create_options = NULL;
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200303 char *options = NULL;
ths3b46e622007-09-17 08:09:54 +0000304
thsec36ba12007-09-16 21:59:02 +0000305 flags = 0;
bellardea2384d2004-08-01 21:59:26 +0000306 for(;;) {
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200307 c = getopt(argc, argv, "F:b:f:he6o:");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100308 if (c == -1) {
bellardea2384d2004-08-01 21:59:26 +0000309 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100310 }
bellardea2384d2004-08-01 21:59:26 +0000311 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +0100312 case '?':
bellardea2384d2004-08-01 21:59:26 +0000313 case 'h':
314 help();
315 break;
aliguori9230eaf2009-03-28 17:55:19 +0000316 case 'F':
317 base_fmt = optarg;
318 break;
bellardea2384d2004-08-01 21:59:26 +0000319 case 'b':
320 base_filename = optarg;
321 break;
322 case 'f':
323 fmt = optarg;
324 break;
325 case 'e':
thsec36ba12007-09-16 21:59:02 +0000326 flags |= BLOCK_FLAG_ENCRYPT;
bellardea2384d2004-08-01 21:59:26 +0000327 break;
thsd8871c52007-10-24 16:11:42 +0000328 case '6':
thsec36ba12007-09-16 21:59:02 +0000329 flags |= BLOCK_FLAG_COMPAT6;
thsd8871c52007-10-24 16:11:42 +0000330 break;
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200331 case 'o':
332 options = optarg;
333 break;
bellardea2384d2004-08-01 21:59:26 +0000334 }
335 }
aliguori9230eaf2009-03-28 17:55:19 +0000336
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900337 /* Get the filename */
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100338 if (optind >= argc) {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900339 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100340 }
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900341 filename = argv[optind++];
342
Jes Sorensen4ac8aac2010-12-06 15:25:38 +0100343 if (options && !strcmp(options, "?")) {
344 ret = print_block_option_help(filename, fmt);
345 goto out;
346 }
347
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200348 /* Find driver and parse its options */
bellardea2384d2004-08-01 21:59:26 +0000349 drv = bdrv_find_format(fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900350 if (!drv) {
bellardea2384d2004-08-01 21:59:26 +0000351 error("Unknown file format '%s'", fmt);
Jes Sorensen2a819982010-12-06 17:08:31 +0100352 ret = -1;
353 goto out;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900354 }
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200355
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900356 proto_drv = bdrv_find_protocol(filename);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900357 if (!proto_drv) {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900358 error("Unknown protocol '%s'", filename);
Jes Sorensen2a819982010-12-06 17:08:31 +0100359 ret = -1;
360 goto out;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900361 }
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900362
363 create_options = append_option_parameters(create_options,
364 drv->create_options);
365 create_options = append_option_parameters(create_options,
366 proto_drv->create_options);
367
Kevin Wolf9f566402009-10-28 11:36:07 +0100368 /* Create parameter list with default values */
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900369 param = parse_option_parameters("", create_options, param);
Kevin Wolf9f566402009-10-28 11:36:07 +0100370 set_option_parameter_int(param, BLOCK_OPT_SIZE, -1);
371
372 /* Parse -o options */
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200373 if (options) {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900374 param = parse_option_parameters(options, create_options, param);
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200375 if (param == NULL) {
376 error("Invalid options for file format '%s'.", fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900377 ret = -1;
378 goto out;
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200379 }
bellard75c23802004-08-27 21:28:58 +0000380 }
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200381
382 /* Add size to parameters */
383 if (optind < argc) {
384 set_option_parameter(param, BLOCK_OPT_SIZE, argv[optind++]);
385 }
386
387 /* Add old-style options to parameters */
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900388 ret = add_old_style_options(fmt, param, flags, base_filename, base_fmt);
389 if (ret < 0) {
390 goto out;
391 }
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200392
393 // The size for the image must always be specified, with one exception:
394 // If we are using a backing file, we can obtain the size from there
Kevin Wolf9f566402009-10-28 11:36:07 +0100395 if (get_option_parameter(param, BLOCK_OPT_SIZE)->value.n == -1) {
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200396
397 QEMUOptionParameter *backing_file =
398 get_option_parameter(param, BLOCK_OPT_BACKING_FILE);
399 QEMUOptionParameter *backing_fmt =
400 get_option_parameter(param, BLOCK_OPT_BACKING_FMT);
401
402 if (backing_file && backing_file->value.s) {
403 BlockDriverState *bs;
404 uint64_t size;
405 const char *fmt = NULL;
406 char buf[32];
407
408 if (backing_fmt && backing_fmt->value.s) {
409 if (bdrv_find_format(backing_fmt->value.s)) {
410 fmt = backing_fmt->value.s;
411 } else {
412 error("Unknown backing file format '%s'",
413 backing_fmt->value.s);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900414 ret = -1;
415 goto out;
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200416 }
417 }
418
Stefan Hajnocziadfe0782010-04-13 10:29:35 +0100419 bs = bdrv_new_open(backing_file->value.s, fmt, BDRV_O_FLAGS);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900420 if (!bs) {
421 ret = -1;
422 goto out;
423 }
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200424 bdrv_get_geometry(bs, &size);
425 size *= 512;
426 bdrv_delete(bs);
427
428 snprintf(buf, sizeof(buf), "%" PRId64, size);
429 set_option_parameter(param, BLOCK_OPT_SIZE, buf);
430 } else {
431 error("Image creation needs a size parameter");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900432 ret = -1;
433 goto out;
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200434 }
435 }
436
437 printf("Formatting '%s', fmt=%s ", filename, fmt);
438 print_option_parameters(param);
439 puts("");
440
441 ret = bdrv_create(drv, filename, param);
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900442 free_option_parameters(create_options);
Kevin Wolf9ea2ea72009-05-18 16:42:11 +0200443 free_option_parameters(param);
444
bellardea2384d2004-08-01 21:59:26 +0000445 if (ret < 0) {
446 if (ret == -ENOTSUP) {
bellard3c565212004-09-29 21:29:14 +0000447 error("Formatting or formatting option not supported for file format '%s'", fmt);
aurel326e9ea0c2009-04-15 14:42:46 +0000448 } else if (ret == -EFBIG) {
449 error("The image size is too large for file format '%s'", fmt);
bellardea2384d2004-08-01 21:59:26 +0000450 } else {
Juan Quintela3e7896d2010-03-04 10:00:38 +0100451 error("%s: error while creating %s: %s", filename, fmt, strerror(-ret));
bellardea2384d2004-08-01 21:59:26 +0000452 }
453 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900454out:
455 if (ret) {
456 return 1;
457 }
bellardea2384d2004-08-01 21:59:26 +0000458 return 0;
459}
460
Kevin Wolfe076f332010-06-29 11:43:13 +0200461/*
462 * Checks an image for consistency. Exit codes:
463 *
464 * 0 - Check completed, image is good
465 * 1 - Check not completed because of internal errors
466 * 2 - Check completed, image is corrupted
467 * 3 - Check completed, image has leaked clusters, but is good otherwise
468 */
aliguori15859692009-04-21 23:11:53 +0000469static int img_check(int argc, char **argv)
470{
471 int c, ret;
472 const char *filename, *fmt;
aliguori15859692009-04-21 23:11:53 +0000473 BlockDriverState *bs;
Kevin Wolfe076f332010-06-29 11:43:13 +0200474 BdrvCheckResult result;
aliguori15859692009-04-21 23:11:53 +0000475
476 fmt = NULL;
477 for(;;) {
478 c = getopt(argc, argv, "f:h");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100479 if (c == -1) {
aliguori15859692009-04-21 23:11:53 +0000480 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100481 }
aliguori15859692009-04-21 23:11:53 +0000482 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +0100483 case '?':
aliguori15859692009-04-21 23:11:53 +0000484 case 'h':
485 help();
486 break;
487 case 'f':
488 fmt = optarg;
489 break;
490 }
491 }
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100492 if (optind >= argc) {
aliguori15859692009-04-21 23:11:53 +0000493 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100494 }
aliguori15859692009-04-21 23:11:53 +0000495 filename = argv[optind++];
496
Stefan Hajnocziadfe0782010-04-13 10:29:35 +0100497 bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900498 if (!bs) {
499 return 1;
500 }
Kevin Wolfe076f332010-06-29 11:43:13 +0200501 ret = bdrv_check(bs, &result);
502
503 if (ret == -ENOTSUP) {
aliguori15859692009-04-21 23:11:53 +0000504 error("This image format does not support checks");
Kevin Wolfe076f332010-06-29 11:43:13 +0200505 bdrv_delete(bs);
506 return 1;
507 }
508
509 if (!(result.corruptions || result.leaks || result.check_errors)) {
510 printf("No errors were found on the image.\n");
511 } else {
512 if (result.corruptions) {
513 printf("\n%d errors were found on the image.\n"
514 "Data may be corrupted, or further writes to the image "
515 "may corrupt it.\n",
516 result.corruptions);
aliguori15859692009-04-21 23:11:53 +0000517 }
Kevin Wolfe076f332010-06-29 11:43:13 +0200518
519 if (result.leaks) {
520 printf("\n%d leaked clusters were found on the image.\n"
521 "This means waste of disk space, but no harm to data.\n",
522 result.leaks);
523 }
524
525 if (result.check_errors) {
526 printf("\n%d internal errors have occurred during the check.\n",
527 result.check_errors);
528 }
aliguori15859692009-04-21 23:11:53 +0000529 }
530
531 bdrv_delete(bs);
Kevin Wolfe076f332010-06-29 11:43:13 +0200532
533 if (ret < 0 || result.check_errors) {
534 printf("\nAn error has occurred during the check: %s\n"
535 "The check is not complete and may have missed error.\n",
536 strerror(-ret));
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900537 return 1;
538 }
Kevin Wolfe076f332010-06-29 11:43:13 +0200539
540 if (result.corruptions) {
541 return 2;
542 } else if (result.leaks) {
543 return 3;
544 } else {
545 return 0;
546 }
aliguori15859692009-04-21 23:11:53 +0000547}
548
bellardea2384d2004-08-01 21:59:26 +0000549static int img_commit(int argc, char **argv)
550{
551 int c, ret;
552 const char *filename, *fmt;
bellardea2384d2004-08-01 21:59:26 +0000553 BlockDriverState *bs;
554
555 fmt = NULL;
556 for(;;) {
557 c = getopt(argc, argv, "f:h");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100558 if (c == -1) {
bellardea2384d2004-08-01 21:59:26 +0000559 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100560 }
bellardea2384d2004-08-01 21:59:26 +0000561 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +0100562 case '?':
bellardea2384d2004-08-01 21:59:26 +0000563 case 'h':
564 help();
565 break;
566 case 'f':
567 fmt = optarg;
568 break;
569 }
570 }
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100571 if (optind >= argc) {
bellardea2384d2004-08-01 21:59:26 +0000572 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100573 }
bellardea2384d2004-08-01 21:59:26 +0000574 filename = argv[optind++];
575
Stefan Hajnocziadfe0782010-04-13 10:29:35 +0100576 bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_RDWR);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900577 if (!bs) {
578 return 1;
579 }
bellardea2384d2004-08-01 21:59:26 +0000580 ret = bdrv_commit(bs);
581 switch(ret) {
582 case 0:
583 printf("Image committed.\n");
584 break;
585 case -ENOENT:
586 error("No disk inserted");
587 break;
588 case -EACCES:
589 error("Image is read-only");
590 break;
591 case -ENOTSUP:
592 error("Image is already committed");
593 break;
594 default:
595 error("Error while committing image");
596 break;
597 }
598
599 bdrv_delete(bs);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900600 if (ret) {
601 return 1;
602 }
bellardea2384d2004-08-01 21:59:26 +0000603 return 0;
604}
605
606static int is_not_zero(const uint8_t *sector, int len)
607{
608 int i;
609 len >>= 2;
610 for(i = 0;i < len; i++) {
611 if (((uint32_t *)sector)[i] != 0)
612 return 1;
613 }
614 return 0;
615}
616
thsf58c7b32008-06-05 21:53:49 +0000617/*
618 * Returns true iff the first sector pointed to by 'buf' contains at least
619 * a non-NUL byte.
620 *
621 * 'pnum' is set to the number of sectors (including and immediately following
622 * the first one) that are known to be in the same allocated/unallocated state.
623 */
bellardea2384d2004-08-01 21:59:26 +0000624static int is_allocated_sectors(const uint8_t *buf, int n, int *pnum)
625{
626 int v, i;
627
628 if (n <= 0) {
629 *pnum = 0;
630 return 0;
631 }
632 v = is_not_zero(buf, 512);
633 for(i = 1; i < n; i++) {
634 buf += 512;
635 if (v != is_not_zero(buf, 512))
636 break;
637 }
638 *pnum = i;
639 return v;
640}
641
Kevin Wolf3e85c6f2010-01-12 12:55:18 +0100642/*
643 * Compares two buffers sector by sector. Returns 0 if the first sector of both
644 * buffers matches, non-zero otherwise.
645 *
646 * pnum is set to the number of sectors (including and immediately following
647 * the first one) that are known to have the same comparison result
648 */
649static int compare_sectors(const uint8_t *buf1, const uint8_t *buf2, int n,
650 int *pnum)
651{
652 int res, i;
653
654 if (n <= 0) {
655 *pnum = 0;
656 return 0;
657 }
658
659 res = !!memcmp(buf1, buf2, 512);
660 for(i = 1; i < n; i++) {
661 buf1 += 512;
662 buf2 += 512;
663
664 if (!!memcmp(buf1, buf2, 512) != res) {
665 break;
666 }
667 }
668
669 *pnum = i;
670 return res;
671}
672
Kevin Wolf80ee15a2009-09-15 12:30:43 +0200673#define IO_BUF_SIZE (2 * 1024 * 1024)
bellardea2384d2004-08-01 21:59:26 +0000674
675static int img_convert(int argc, char **argv)
676{
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900677 int c, ret = 0, n, n1, bs_n, bs_i, flags, cluster_size, cluster_sectors;
thsf58c7b32008-06-05 21:53:49 +0000678 const char *fmt, *out_fmt, *out_baseimg, *out_filename;
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900679 BlockDriver *drv, *proto_drv;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900680 BlockDriverState **bs = NULL, *out_bs = NULL;
ths96b8f132007-12-17 01:35:20 +0000681 int64_t total_sectors, nb_sectors, sector_num, bs_offset;
682 uint64_t bs_sectors;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900683 uint8_t * buf = NULL;
bellardea2384d2004-08-01 21:59:26 +0000684 const uint8_t *buf1;
bellardfaea38e2006-08-05 21:31:00 +0000685 BlockDriverInfo bdi;
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900686 QEMUOptionParameter *param = NULL, *create_options = NULL;
Kevin Wolfa18953f2010-10-14 15:46:04 +0200687 QEMUOptionParameter *out_baseimg_param;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200688 char *options = NULL;
edison51ef6722010-09-21 19:58:41 -0700689 const char *snapshot_name = NULL;
bellardea2384d2004-08-01 21:59:26 +0000690
691 fmt = NULL;
692 out_fmt = "raw";
thsf58c7b32008-06-05 21:53:49 +0000693 out_baseimg = NULL;
thsec36ba12007-09-16 21:59:02 +0000694 flags = 0;
bellardea2384d2004-08-01 21:59:26 +0000695 for(;;) {
edison51ef6722010-09-21 19:58:41 -0700696 c = getopt(argc, argv, "f:O:B:s:hce6o:");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100697 if (c == -1) {
bellardea2384d2004-08-01 21:59:26 +0000698 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100699 }
bellardea2384d2004-08-01 21:59:26 +0000700 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +0100701 case '?':
bellardea2384d2004-08-01 21:59:26 +0000702 case 'h':
703 help();
704 break;
705 case 'f':
706 fmt = optarg;
707 break;
708 case 'O':
709 out_fmt = optarg;
710 break;
thsf58c7b32008-06-05 21:53:49 +0000711 case 'B':
712 out_baseimg = optarg;
713 break;
bellardea2384d2004-08-01 21:59:26 +0000714 case 'c':
thsec36ba12007-09-16 21:59:02 +0000715 flags |= BLOCK_FLAG_COMPRESS;
bellardea2384d2004-08-01 21:59:26 +0000716 break;
717 case 'e':
thsec36ba12007-09-16 21:59:02 +0000718 flags |= BLOCK_FLAG_ENCRYPT;
719 break;
720 case '6':
721 flags |= BLOCK_FLAG_COMPAT6;
bellardea2384d2004-08-01 21:59:26 +0000722 break;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200723 case 'o':
724 options = optarg;
725 break;
edison51ef6722010-09-21 19:58:41 -0700726 case 's':
727 snapshot_name = optarg;
728 break;
bellardea2384d2004-08-01 21:59:26 +0000729 }
730 }
ths3b46e622007-09-17 08:09:54 +0000731
balrog926c2d22007-10-31 01:11:44 +0000732 bs_n = argc - optind - 1;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100733 if (bs_n < 1) {
734 help();
735 }
balrog926c2d22007-10-31 01:11:44 +0000736
737 out_filename = argv[argc - 1];
thsf58c7b32008-06-05 21:53:49 +0000738
Jes Sorensen4ac8aac2010-12-06 15:25:38 +0100739 if (options && !strcmp(options, "?")) {
740 ret = print_block_option_help(out_filename, out_fmt);
741 goto out;
742 }
743
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900744 if (bs_n > 1 && out_baseimg) {
thsf58c7b32008-06-05 21:53:49 +0000745 error("-B makes no sense when concatenating multiple input images");
Jes Sorensen31ca34b2010-12-06 15:25:36 +0100746 ret = -1;
747 goto out;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900748 }
balrog926c2d22007-10-31 01:11:44 +0000749
Jes Sorensen5bdf61f2010-12-06 15:25:35 +0100750 bs = qemu_mallocz(bs_n * sizeof(BlockDriverState *));
balrog926c2d22007-10-31 01:11:44 +0000751
752 total_sectors = 0;
753 for (bs_i = 0; bs_i < bs_n; bs_i++) {
Stefan Hajnocziadfe0782010-04-13 10:29:35 +0100754 bs[bs_i] = bdrv_new_open(argv[optind + bs_i], fmt, BDRV_O_FLAGS);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900755 if (!bs[bs_i]) {
balrog926c2d22007-10-31 01:11:44 +0000756 error("Could not open '%s'", argv[optind + bs_i]);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900757 ret = -1;
758 goto out;
759 }
balrog926c2d22007-10-31 01:11:44 +0000760 bdrv_get_geometry(bs[bs_i], &bs_sectors);
761 total_sectors += bs_sectors;
762 }
bellardea2384d2004-08-01 21:59:26 +0000763
edison51ef6722010-09-21 19:58:41 -0700764 if (snapshot_name != NULL) {
765 if (bs_n > 1) {
766 error("No support for concatenating multiple snapshot\n");
767 ret = -1;
768 goto out;
769 }
770 if (bdrv_snapshot_load_tmp(bs[0], snapshot_name) < 0) {
771 error("Failed to load snapshot\n");
772 ret = -1;
773 goto out;
774 }
775 }
776
Kevin Wolfefa84d42009-05-18 16:42:12 +0200777 /* Find driver and parse its options */
bellardea2384d2004-08-01 21:59:26 +0000778 drv = bdrv_find_format(out_fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900779 if (!drv) {
thsd34dda52007-02-10 22:59:40 +0000780 error("Unknown file format '%s'", out_fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900781 ret = -1;
782 goto out;
783 }
balrog926c2d22007-10-31 01:11:44 +0000784
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900785 proto_drv = bdrv_find_protocol(out_filename);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900786 if (!proto_drv) {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900787 error("Unknown protocol '%s'", out_filename);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900788 ret = -1;
789 goto out;
790 }
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900791
792 create_options = append_option_parameters(create_options,
793 drv->create_options);
794 create_options = append_option_parameters(create_options,
795 proto_drv->create_options);
Kevin Wolfdb08adf2009-06-04 15:39:38 +0200796
Kevin Wolfefa84d42009-05-18 16:42:12 +0200797 if (options) {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900798 param = parse_option_parameters(options, create_options, param);
Kevin Wolfefa84d42009-05-18 16:42:12 +0200799 if (param == NULL) {
800 error("Invalid options for file format '%s'.", out_fmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900801 ret = -1;
802 goto out;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200803 }
804 } else {
MORITA Kazutakab50cbab2010-05-26 11:35:36 +0900805 param = parse_option_parameters("", create_options, param);
Kevin Wolfefa84d42009-05-18 16:42:12 +0200806 }
807
808 set_option_parameter_int(param, BLOCK_OPT_SIZE, total_sectors * 512);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900809 ret = add_old_style_options(out_fmt, param, flags, out_baseimg, NULL);
810 if (ret < 0) {
811 goto out;
812 }
Kevin Wolfefa84d42009-05-18 16:42:12 +0200813
Kevin Wolfa18953f2010-10-14 15:46:04 +0200814 /* Get backing file name if -o backing_file was used */
815 out_baseimg_param = get_option_parameter(param, BLOCK_OPT_BACKING_FILE);
816 if (out_baseimg_param) {
817 out_baseimg = out_baseimg_param->value.s;
818 }
819
Kevin Wolfefa84d42009-05-18 16:42:12 +0200820 /* Check if compression is supported */
821 if (flags & BLOCK_FLAG_COMPRESS) {
822 QEMUOptionParameter *encryption =
823 get_option_parameter(param, BLOCK_OPT_ENCRYPT);
824
825 if (!drv->bdrv_write_compressed) {
826 error("Compression not supported for this file format");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900827 ret = -1;
828 goto out;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200829 }
830
831 if (encryption && encryption->value.n) {
832 error("Compression and encryption not supported at the same time");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900833 ret = -1;
834 goto out;
Kevin Wolfefa84d42009-05-18 16:42:12 +0200835 }
836 }
837
838 /* Create the new image */
839 ret = bdrv_create(drv, out_filename, param);
bellardea2384d2004-08-01 21:59:26 +0000840 if (ret < 0) {
841 if (ret == -ENOTSUP) {
aliguori93c65b42009-04-05 17:40:43 +0000842 error("Formatting not supported for file format '%s'", out_fmt);
aurel326e9ea0c2009-04-15 14:42:46 +0000843 } else if (ret == -EFBIG) {
844 error("The image size is too large for file format '%s'", out_fmt);
bellardea2384d2004-08-01 21:59:26 +0000845 } else {
Juan Quintela3e7896d2010-03-04 10:00:38 +0100846 error("%s: error while converting %s: %s", out_filename, out_fmt, strerror(-ret));
bellardea2384d2004-08-01 21:59:26 +0000847 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900848 goto out;
bellardea2384d2004-08-01 21:59:26 +0000849 }
ths3b46e622007-09-17 08:09:54 +0000850
Kevin Wolf1bd8e172010-08-31 13:44:25 +0200851 out_bs = bdrv_new_open(out_filename, out_fmt,
852 BDRV_O_FLAGS | BDRV_O_RDWR | BDRV_O_NO_FLUSH);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900853 if (!out_bs) {
854 ret = -1;
855 goto out;
856 }
bellardea2384d2004-08-01 21:59:26 +0000857
balrog926c2d22007-10-31 01:11:44 +0000858 bs_i = 0;
859 bs_offset = 0;
860 bdrv_get_geometry(bs[0], &bs_sectors);
TeLeMand6771bf2010-02-08 16:20:00 +0800861 buf = qemu_malloc(IO_BUF_SIZE);
balrog926c2d22007-10-31 01:11:44 +0000862
863 if (flags & BLOCK_FLAG_COMPRESS) {
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900864 ret = bdrv_get_info(out_bs, &bdi);
865 if (ret < 0) {
bellardfaea38e2006-08-05 21:31:00 +0000866 error("could not get block driver info");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900867 goto out;
868 }
bellardfaea38e2006-08-05 21:31:00 +0000869 cluster_size = bdi.cluster_size;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900870 if (cluster_size <= 0 || cluster_size > IO_BUF_SIZE) {
bellardea2384d2004-08-01 21:59:26 +0000871 error("invalid cluster size");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900872 ret = -1;
873 goto out;
874 }
bellardea2384d2004-08-01 21:59:26 +0000875 cluster_sectors = cluster_size >> 9;
876 sector_num = 0;
877 for(;;) {
balrog926c2d22007-10-31 01:11:44 +0000878 int64_t bs_num;
879 int remainder;
880 uint8_t *buf2;
881
bellardea2384d2004-08-01 21:59:26 +0000882 nb_sectors = total_sectors - sector_num;
883 if (nb_sectors <= 0)
884 break;
885 if (nb_sectors >= cluster_sectors)
886 n = cluster_sectors;
887 else
888 n = nb_sectors;
balrog926c2d22007-10-31 01:11:44 +0000889
890 bs_num = sector_num - bs_offset;
891 assert (bs_num >= 0);
892 remainder = n;
893 buf2 = buf;
894 while (remainder > 0) {
895 int nlow;
896 while (bs_num == bs_sectors) {
897 bs_i++;
898 assert (bs_i < bs_n);
899 bs_offset += bs_sectors;
900 bdrv_get_geometry(bs[bs_i], &bs_sectors);
901 bs_num = 0;
Blue Swirl0bfcd592010-05-22 08:02:12 +0000902 /* printf("changing part: sector_num=%" PRId64 ", "
903 "bs_i=%d, bs_offset=%" PRId64 ", bs_sectors=%" PRId64
904 "\n", sector_num, bs_i, bs_offset, bs_sectors); */
balrog926c2d22007-10-31 01:11:44 +0000905 }
906 assert (bs_num < bs_sectors);
907
908 nlow = (remainder > bs_sectors - bs_num) ? bs_sectors - bs_num : remainder;
909
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900910 ret = bdrv_read(bs[bs_i], bs_num, buf2, nlow);
911 if (ret < 0) {
balrog926c2d22007-10-31 01:11:44 +0000912 error("error while reading");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900913 goto out;
914 }
balrog926c2d22007-10-31 01:11:44 +0000915
916 buf2 += nlow * 512;
917 bs_num += nlow;
918
919 remainder -= nlow;
920 }
921 assert (remainder == 0);
922
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100923 if (n < cluster_sectors) {
bellardea2384d2004-08-01 21:59:26 +0000924 memset(buf + n * 512, 0, cluster_size - n * 512);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100925 }
bellardea2384d2004-08-01 21:59:26 +0000926 if (is_not_zero(buf, cluster_size)) {
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900927 ret = bdrv_write_compressed(out_bs, sector_num, buf,
928 cluster_sectors);
929 if (ret != 0) {
bellardec3757d2006-06-14 15:50:07 +0000930 error("error while compressing sector %" PRId64,
931 sector_num);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900932 goto out;
933 }
bellardea2384d2004-08-01 21:59:26 +0000934 }
935 sector_num += n;
936 }
bellardfaea38e2006-08-05 21:31:00 +0000937 /* signal EOF to align */
938 bdrv_write_compressed(out_bs, 0, NULL, 0);
bellardea2384d2004-08-01 21:59:26 +0000939 } else {
Kevin Wolff2feebb2010-04-14 17:30:35 +0200940 int has_zero_init = bdrv_has_zero_init(out_bs);
941
thsf58c7b32008-06-05 21:53:49 +0000942 sector_num = 0; // total number of sectors converted so far
bellardea2384d2004-08-01 21:59:26 +0000943 for(;;) {
944 nb_sectors = total_sectors - sector_num;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100945 if (nb_sectors <= 0) {
bellardea2384d2004-08-01 21:59:26 +0000946 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100947 }
948 if (nb_sectors >= (IO_BUF_SIZE / 512)) {
bellardea2384d2004-08-01 21:59:26 +0000949 n = (IO_BUF_SIZE / 512);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100950 } else {
bellardea2384d2004-08-01 21:59:26 +0000951 n = nb_sectors;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100952 }
balrog926c2d22007-10-31 01:11:44 +0000953
954 while (sector_num - bs_offset >= bs_sectors) {
955 bs_i ++;
956 assert (bs_i < bs_n);
957 bs_offset += bs_sectors;
958 bdrv_get_geometry(bs[bs_i], &bs_sectors);
Blue Swirl0bfcd592010-05-22 08:02:12 +0000959 /* printf("changing part: sector_num=%" PRId64 ", bs_i=%d, "
960 "bs_offset=%" PRId64 ", bs_sectors=%" PRId64 "\n",
balrog926c2d22007-10-31 01:11:44 +0000961 sector_num, bs_i, bs_offset, bs_sectors); */
962 }
963
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100964 if (n > bs_offset + bs_sectors - sector_num) {
balrog926c2d22007-10-31 01:11:44 +0000965 n = bs_offset + bs_sectors - sector_num;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +0100966 }
balrog926c2d22007-10-31 01:11:44 +0000967
Kevin Wolff2feebb2010-04-14 17:30:35 +0200968 if (has_zero_init) {
Akkarit Sangpetchd0320442009-07-17 10:02:15 +0200969 /* If the output image is being created as a copy on write image,
970 assume that sectors which are unallocated in the input image
971 are present in both the output's and input's base images (no
972 need to copy them). */
973 if (out_baseimg) {
974 if (!bdrv_is_allocated(bs[bs_i], sector_num - bs_offset,
975 n, &n1)) {
976 sector_num += n1;
977 continue;
978 }
979 /* The next 'n1' sectors are allocated in the input image. Copy
980 only those as they may be followed by unallocated sectors. */
981 n = n1;
aliguori93c65b42009-04-05 17:40:43 +0000982 }
aliguori93c65b42009-04-05 17:40:43 +0000983 } else {
984 n1 = n;
thsf58c7b32008-06-05 21:53:49 +0000985 }
986
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900987 ret = bdrv_read(bs[bs_i], sector_num - bs_offset, buf, n);
988 if (ret < 0) {
bellardea2384d2004-08-01 21:59:26 +0000989 error("error while reading");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +0900990 goto out;
991 }
bellardea2384d2004-08-01 21:59:26 +0000992 /* NOTE: at the same time we convert, we do not write zero
993 sectors to have a chance to compress the image. Ideally, we
994 should add a specific call to have the info to go faster */
995 buf1 = buf;
996 while (n > 0) {
thsf58c7b32008-06-05 21:53:49 +0000997 /* If the output image is being created as a copy on write image,
998 copy all sectors even the ones containing only NUL bytes,
aliguori93c65b42009-04-05 17:40:43 +0000999 because they may differ from the sectors in the base image.
1000
1001 If the output is to a host device, we also write out
1002 sectors that are entirely 0, since whatever data was
1003 already there is garbage, not 0s. */
Kevin Wolff2feebb2010-04-14 17:30:35 +02001004 if (!has_zero_init || out_baseimg ||
aliguori93c65b42009-04-05 17:40:43 +00001005 is_allocated_sectors(buf1, n, &n1)) {
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001006 ret = bdrv_write(out_bs, sector_num, buf1, n1);
1007 if (ret < 0) {
bellardea2384d2004-08-01 21:59:26 +00001008 error("error while writing");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001009 goto out;
1010 }
bellardea2384d2004-08-01 21:59:26 +00001011 }
1012 sector_num += n1;
1013 n -= n1;
1014 buf1 += n1 * 512;
1015 }
1016 }
1017 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001018out:
1019 free_option_parameters(create_options);
1020 free_option_parameters(param);
TeLeMand6771bf2010-02-08 16:20:00 +08001021 qemu_free(buf);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001022 if (out_bs) {
1023 bdrv_delete(out_bs);
1024 }
Jes Sorensen31ca34b2010-12-06 15:25:36 +01001025 if (bs) {
1026 for (bs_i = 0; bs_i < bs_n; bs_i++) {
1027 if (bs[bs_i]) {
1028 bdrv_delete(bs[bs_i]);
1029 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001030 }
Jes Sorensen31ca34b2010-12-06 15:25:36 +01001031 qemu_free(bs);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001032 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001033 if (ret) {
1034 return 1;
1035 }
bellardea2384d2004-08-01 21:59:26 +00001036 return 0;
1037}
1038
bellard57d1a2b2004-08-03 21:15:11 +00001039#ifdef _WIN32
1040static int64_t get_allocated_file_size(const char *filename)
1041{
bellarde8445332006-06-14 15:32:10 +00001042 typedef DWORD (WINAPI * get_compressed_t)(const char *filename, DWORD *high);
1043 get_compressed_t get_compressed;
bellard57d1a2b2004-08-03 21:15:11 +00001044 struct _stati64 st;
bellarde8445332006-06-14 15:32:10 +00001045
1046 /* WinNT support GetCompressedFileSize to determine allocate size */
1047 get_compressed = (get_compressed_t) GetProcAddress(GetModuleHandle("kernel32"), "GetCompressedFileSizeA");
1048 if (get_compressed) {
1049 DWORD high, low;
1050 low = get_compressed(filename, &high);
1051 if (low != 0xFFFFFFFFlu || GetLastError() == NO_ERROR)
1052 return (((int64_t) high) << 32) + low;
1053 }
1054
ths5fafdf22007-09-16 21:08:06 +00001055 if (_stati64(filename, &st) < 0)
bellard57d1a2b2004-08-03 21:15:11 +00001056 return -1;
1057 return st.st_size;
1058}
1059#else
1060static int64_t get_allocated_file_size(const char *filename)
1061{
1062 struct stat st;
ths5fafdf22007-09-16 21:08:06 +00001063 if (stat(filename, &st) < 0)
bellard57d1a2b2004-08-03 21:15:11 +00001064 return -1;
1065 return (int64_t)st.st_blocks * 512;
1066}
1067#endif
1068
bellardfaea38e2006-08-05 21:31:00 +00001069static void dump_snapshots(BlockDriverState *bs)
1070{
1071 QEMUSnapshotInfo *sn_tab, *sn;
1072 int nb_sns, i;
1073 char buf[256];
1074
1075 nb_sns = bdrv_snapshot_list(bs, &sn_tab);
1076 if (nb_sns <= 0)
1077 return;
1078 printf("Snapshot list:\n");
1079 printf("%s\n", bdrv_snapshot_dump(buf, sizeof(buf), NULL));
1080 for(i = 0; i < nb_sns; i++) {
1081 sn = &sn_tab[i];
1082 printf("%s\n", bdrv_snapshot_dump(buf, sizeof(buf), sn));
1083 }
1084 qemu_free(sn_tab);
1085}
1086
bellardea2384d2004-08-01 21:59:26 +00001087static int img_info(int argc, char **argv)
1088{
1089 int c;
1090 const char *filename, *fmt;
bellardea2384d2004-08-01 21:59:26 +00001091 BlockDriverState *bs;
1092 char fmt_name[128], size_buf[128], dsize_buf[128];
ths96b8f132007-12-17 01:35:20 +00001093 uint64_t total_sectors;
1094 int64_t allocated_size;
bellard93b6b2a2006-08-01 15:51:11 +00001095 char backing_filename[1024];
1096 char backing_filename2[1024];
bellardfaea38e2006-08-05 21:31:00 +00001097 BlockDriverInfo bdi;
bellardea2384d2004-08-01 21:59:26 +00001098
1099 fmt = NULL;
1100 for(;;) {
1101 c = getopt(argc, argv, "f:h");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001102 if (c == -1) {
bellardea2384d2004-08-01 21:59:26 +00001103 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001104 }
bellardea2384d2004-08-01 21:59:26 +00001105 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +01001106 case '?':
bellardea2384d2004-08-01 21:59:26 +00001107 case 'h':
1108 help();
1109 break;
1110 case 'f':
1111 fmt = optarg;
1112 break;
1113 }
1114 }
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001115 if (optind >= argc) {
bellardea2384d2004-08-01 21:59:26 +00001116 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001117 }
bellardea2384d2004-08-01 21:59:26 +00001118 filename = argv[optind++];
1119
Stefan Hajnocziadfe0782010-04-13 10:29:35 +01001120 bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_NO_BACKING);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001121 if (!bs) {
1122 return 1;
1123 }
bellardea2384d2004-08-01 21:59:26 +00001124 bdrv_get_format(bs, fmt_name, sizeof(fmt_name));
1125 bdrv_get_geometry(bs, &total_sectors);
1126 get_human_readable_size(size_buf, sizeof(size_buf), total_sectors * 512);
bellard57d1a2b2004-08-03 21:15:11 +00001127 allocated_size = get_allocated_file_size(filename);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001128 if (allocated_size < 0) {
blueswir1a10ea302008-08-24 10:30:33 +00001129 snprintf(dsize_buf, sizeof(dsize_buf), "unavailable");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001130 } else {
ths5fafdf22007-09-16 21:08:06 +00001131 get_human_readable_size(dsize_buf, sizeof(dsize_buf),
bellardde167e42005-04-28 21:15:08 +00001132 allocated_size);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001133 }
bellardea2384d2004-08-01 21:59:26 +00001134 printf("image: %s\n"
1135 "file format: %s\n"
bellardec3757d2006-06-14 15:50:07 +00001136 "virtual size: %s (%" PRId64 " bytes)\n"
bellardea2384d2004-08-01 21:59:26 +00001137 "disk size: %s\n",
ths5fafdf22007-09-16 21:08:06 +00001138 filename, fmt_name, size_buf,
bellardec3757d2006-06-14 15:50:07 +00001139 (total_sectors * 512),
bellardea2384d2004-08-01 21:59:26 +00001140 dsize_buf);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001141 if (bdrv_is_encrypted(bs)) {
bellardea2384d2004-08-01 21:59:26 +00001142 printf("encrypted: yes\n");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001143 }
bellardfaea38e2006-08-05 21:31:00 +00001144 if (bdrv_get_info(bs, &bdi) >= 0) {
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001145 if (bdi.cluster_size != 0) {
bellardfaea38e2006-08-05 21:31:00 +00001146 printf("cluster_size: %d\n", bdi.cluster_size);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001147 }
bellardfaea38e2006-08-05 21:31:00 +00001148 }
bellard93b6b2a2006-08-01 15:51:11 +00001149 bdrv_get_backing_filename(bs, backing_filename, sizeof(backing_filename));
bellardfaea38e2006-08-05 21:31:00 +00001150 if (backing_filename[0] != '\0') {
bellard93b6b2a2006-08-01 15:51:11 +00001151 path_combine(backing_filename2, sizeof(backing_filename2),
1152 filename, backing_filename);
ths5fafdf22007-09-16 21:08:06 +00001153 printf("backing file: %s (actual path: %s)\n",
bellard93b6b2a2006-08-01 15:51:11 +00001154 backing_filename,
1155 backing_filename2);
bellardfaea38e2006-08-05 21:31:00 +00001156 }
1157 dump_snapshots(bs);
bellardea2384d2004-08-01 21:59:26 +00001158 bdrv_delete(bs);
1159 return 0;
1160}
1161
aliguorif7b4a942009-01-07 17:40:15 +00001162#define SNAPSHOT_LIST 1
1163#define SNAPSHOT_CREATE 2
1164#define SNAPSHOT_APPLY 3
1165#define SNAPSHOT_DELETE 4
1166
Stuart Brady153859b2009-06-07 00:42:17 +01001167static int img_snapshot(int argc, char **argv)
aliguorif7b4a942009-01-07 17:40:15 +00001168{
1169 BlockDriverState *bs;
1170 QEMUSnapshotInfo sn;
1171 char *filename, *snapshot_name = NULL;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001172 int c, ret = 0, bdrv_oflags;
aliguorif7b4a942009-01-07 17:40:15 +00001173 int action = 0;
1174 qemu_timeval tv;
1175
Naphtali Spreif5edb012010-01-17 16:48:13 +02001176 bdrv_oflags = BDRV_O_RDWR;
aliguorif7b4a942009-01-07 17:40:15 +00001177 /* Parse commandline parameters */
1178 for(;;) {
1179 c = getopt(argc, argv, "la:c:d:h");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001180 if (c == -1) {
aliguorif7b4a942009-01-07 17:40:15 +00001181 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001182 }
aliguorif7b4a942009-01-07 17:40:15 +00001183 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +01001184 case '?':
aliguorif7b4a942009-01-07 17:40:15 +00001185 case 'h':
1186 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001187 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001188 case 'l':
1189 if (action) {
1190 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001191 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001192 }
1193 action = SNAPSHOT_LIST;
Naphtali Spreif5edb012010-01-17 16:48:13 +02001194 bdrv_oflags &= ~BDRV_O_RDWR; /* no need for RW */
aliguorif7b4a942009-01-07 17:40:15 +00001195 break;
1196 case 'a':
1197 if (action) {
1198 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001199 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001200 }
1201 action = SNAPSHOT_APPLY;
1202 snapshot_name = optarg;
1203 break;
1204 case 'c':
1205 if (action) {
1206 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001207 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001208 }
1209 action = SNAPSHOT_CREATE;
1210 snapshot_name = optarg;
1211 break;
1212 case 'd':
1213 if (action) {
1214 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001215 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001216 }
1217 action = SNAPSHOT_DELETE;
1218 snapshot_name = optarg;
1219 break;
1220 }
1221 }
1222
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001223 if (optind >= argc) {
aliguorif7b4a942009-01-07 17:40:15 +00001224 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001225 }
aliguorif7b4a942009-01-07 17:40:15 +00001226 filename = argv[optind++];
1227
1228 /* Open the image */
Stefan Hajnoczif163d072010-04-13 10:29:34 +01001229 bs = bdrv_new_open(filename, NULL, bdrv_oflags);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001230 if (!bs) {
1231 return 1;
1232 }
aliguorif7b4a942009-01-07 17:40:15 +00001233
1234 /* Perform the requested action */
1235 switch(action) {
1236 case SNAPSHOT_LIST:
1237 dump_snapshots(bs);
1238 break;
1239
1240 case SNAPSHOT_CREATE:
1241 memset(&sn, 0, sizeof(sn));
1242 pstrcpy(sn.name, sizeof(sn.name), snapshot_name);
1243
1244 qemu_gettimeofday(&tv);
1245 sn.date_sec = tv.tv_sec;
1246 sn.date_nsec = tv.tv_usec * 1000;
1247
1248 ret = bdrv_snapshot_create(bs, &sn);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001249 if (ret) {
aliguorif7b4a942009-01-07 17:40:15 +00001250 error("Could not create snapshot '%s': %d (%s)",
1251 snapshot_name, ret, strerror(-ret));
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001252 }
aliguorif7b4a942009-01-07 17:40:15 +00001253 break;
1254
1255 case SNAPSHOT_APPLY:
1256 ret = bdrv_snapshot_goto(bs, snapshot_name);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001257 if (ret) {
aliguorif7b4a942009-01-07 17:40:15 +00001258 error("Could not apply snapshot '%s': %d (%s)",
1259 snapshot_name, ret, strerror(-ret));
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001260 }
aliguorif7b4a942009-01-07 17:40:15 +00001261 break;
1262
1263 case SNAPSHOT_DELETE:
1264 ret = bdrv_snapshot_delete(bs, snapshot_name);
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001265 if (ret) {
aliguorif7b4a942009-01-07 17:40:15 +00001266 error("Could not delete snapshot '%s': %d (%s)",
1267 snapshot_name, ret, strerror(-ret));
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001268 }
aliguorif7b4a942009-01-07 17:40:15 +00001269 break;
1270 }
1271
1272 /* Cleanup */
1273 bdrv_delete(bs);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001274 if (ret) {
1275 return 1;
1276 }
Stuart Brady153859b2009-06-07 00:42:17 +01001277 return 0;
aliguorif7b4a942009-01-07 17:40:15 +00001278}
1279
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001280static int img_rebase(int argc, char **argv)
1281{
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001282 BlockDriverState *bs, *bs_old_backing = NULL, *bs_new_backing = NULL;
Stefan Hajnoczif163d072010-04-13 10:29:34 +01001283 BlockDriver *old_backing_drv, *new_backing_drv;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001284 char *filename;
Kevin Wolfe53dbee2010-03-02 12:14:31 +01001285 const char *fmt, *out_basefmt, *out_baseimg;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001286 int c, flags, ret;
1287 int unsafe = 0;
1288
1289 /* Parse commandline parameters */
Kevin Wolfe53dbee2010-03-02 12:14:31 +01001290 fmt = NULL;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001291 out_baseimg = NULL;
1292 out_basefmt = NULL;
1293
1294 for(;;) {
Kevin Wolfe53dbee2010-03-02 12:14:31 +01001295 c = getopt(argc, argv, "uhf:F:b:");
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001296 if (c == -1) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001297 break;
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001298 }
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001299 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +01001300 case '?':
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001301 case 'h':
1302 help();
1303 return 0;
Kevin Wolfe53dbee2010-03-02 12:14:31 +01001304 case 'f':
1305 fmt = optarg;
1306 break;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001307 case 'F':
1308 out_basefmt = optarg;
1309 break;
1310 case 'b':
1311 out_baseimg = optarg;
1312 break;
1313 case 'u':
1314 unsafe = 1;
1315 break;
1316 }
1317 }
1318
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001319 if ((optind >= argc) || !out_baseimg) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001320 help();
Jes Sorensenb8fb60d2010-12-06 15:25:39 +01001321 }
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001322 filename = argv[optind++];
1323
1324 /*
1325 * Open the images.
1326 *
1327 * Ignore the old backing file for unsafe rebase in case we want to correct
1328 * the reference to a renamed or moved backing file.
1329 */
Stefan Hajnocziadfe0782010-04-13 10:29:35 +01001330 flags = BDRV_O_FLAGS | BDRV_O_RDWR | (unsafe ? BDRV_O_NO_BACKING : 0);
Stefan Hajnoczif163d072010-04-13 10:29:34 +01001331 bs = bdrv_new_open(filename, fmt, flags);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001332 if (!bs) {
1333 return 1;
1334 }
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001335
1336 /* Find the right drivers for the backing files */
1337 old_backing_drv = NULL;
1338 new_backing_drv = NULL;
1339
1340 if (!unsafe && bs->backing_format[0] != '\0') {
1341 old_backing_drv = bdrv_find_format(bs->backing_format);
1342 if (old_backing_drv == NULL) {
1343 error("Invalid format name: '%s'", bs->backing_format);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001344 ret = -1;
1345 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001346 }
1347 }
1348
1349 if (out_basefmt != NULL) {
1350 new_backing_drv = bdrv_find_format(out_basefmt);
1351 if (new_backing_drv == NULL) {
1352 error("Invalid format name: '%s'", out_basefmt);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001353 ret = -1;
1354 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001355 }
1356 }
1357
1358 /* For safe rebasing we need to compare old and new backing file */
1359 if (unsafe) {
1360 /* Make the compiler happy */
1361 bs_old_backing = NULL;
1362 bs_new_backing = NULL;
1363 } else {
1364 char backing_name[1024];
1365
1366 bs_old_backing = bdrv_new("old_backing");
1367 bdrv_get_backing_filename(bs, backing_name, sizeof(backing_name));
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001368 ret = bdrv_open(bs_old_backing, backing_name, BDRV_O_FLAGS,
1369 old_backing_drv);
1370 if (ret) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001371 error("Could not open old backing file '%s'", backing_name);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001372 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001373 }
1374
1375 bs_new_backing = bdrv_new("new_backing");
Kevin Wolfcdbae852010-08-17 18:58:55 +02001376 ret = bdrv_open(bs_new_backing, out_baseimg, BDRV_O_FLAGS,
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001377 new_backing_drv);
1378 if (ret) {
Kevin Wolf584771e2010-02-17 12:33:17 +01001379 error("Could not open new backing file '%s'", out_baseimg);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001380 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001381 }
1382 }
1383
1384 /*
1385 * Check each unallocated cluster in the COW file. If it is unallocated,
1386 * accesses go to the backing file. We must therefore compare this cluster
1387 * in the old and new backing file, and if they differ we need to copy it
1388 * from the old backing file into the COW file.
1389 *
1390 * If qemu-img crashes during this step, no harm is done. The content of
1391 * the image is the same as the original one at any time.
1392 */
1393 if (!unsafe) {
1394 uint64_t num_sectors;
1395 uint64_t sector;
Kevin Wolfcc60e322010-04-29 14:47:48 +02001396 int n;
TeLeMand6771bf2010-02-08 16:20:00 +08001397 uint8_t * buf_old;
1398 uint8_t * buf_new;
1399
1400 buf_old = qemu_malloc(IO_BUF_SIZE);
1401 buf_new = qemu_malloc(IO_BUF_SIZE);
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001402
1403 bdrv_get_geometry(bs, &num_sectors);
1404
1405 for (sector = 0; sector < num_sectors; sector += n) {
1406
1407 /* How many sectors can we handle with the next read? */
1408 if (sector + (IO_BUF_SIZE / 512) <= num_sectors) {
1409 n = (IO_BUF_SIZE / 512);
1410 } else {
1411 n = num_sectors - sector;
1412 }
1413
1414 /* If the cluster is allocated, we don't need to take action */
Kevin Wolfcc60e322010-04-29 14:47:48 +02001415 ret = bdrv_is_allocated(bs, sector, n, &n);
1416 if (ret) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001417 continue;
1418 }
1419
1420 /* Read old and new backing file */
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001421 ret = bdrv_read(bs_old_backing, sector, buf_old, n);
1422 if (ret < 0) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001423 error("error while reading from old backing file");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001424 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001425 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001426 ret = bdrv_read(bs_new_backing, sector, buf_new, n);
1427 if (ret < 0) {
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001428 error("error while reading from new backing file");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001429 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001430 }
1431
1432 /* If they differ, we need to write to the COW file */
1433 uint64_t written = 0;
1434
1435 while (written < n) {
1436 int pnum;
1437
1438 if (compare_sectors(buf_old + written * 512,
Kevin Wolf60b1bd42010-02-17 12:32:59 +01001439 buf_new + written * 512, n - written, &pnum))
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001440 {
1441 ret = bdrv_write(bs, sector + written,
1442 buf_old + written * 512, pnum);
1443 if (ret < 0) {
1444 error("Error while writing to COW image: %s",
1445 strerror(-ret));
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001446 goto out;
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001447 }
1448 }
1449
1450 written += pnum;
1451 }
1452 }
TeLeMand6771bf2010-02-08 16:20:00 +08001453
1454 qemu_free(buf_old);
1455 qemu_free(buf_new);
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001456 }
1457
1458 /*
1459 * Change the backing file. All clusters that are different from the old
1460 * backing file are overwritten in the COW file now, so the visible content
1461 * doesn't change when we switch the backing file.
1462 */
1463 ret = bdrv_change_backing_file(bs, out_baseimg, out_basefmt);
1464 if (ret == -ENOSPC) {
1465 error("Could not change the backing file to '%s': No space left in "
1466 "the file header", out_baseimg);
1467 } else if (ret < 0) {
1468 error("Could not change the backing file to '%s': %s",
1469 out_baseimg, strerror(-ret));
1470 }
1471
1472 /*
1473 * TODO At this point it is possible to check if any clusters that are
1474 * allocated in the COW file are the same in the backing file. If so, they
1475 * could be dropped from the COW file. Don't do this before switching the
1476 * backing file, in case of a crash this would lead to corruption.
1477 */
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001478out:
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001479 /* Cleanup */
1480 if (!unsafe) {
1481 bdrv_delete(bs_old_backing);
1482 bdrv_delete(bs_new_backing);
1483 }
1484
1485 bdrv_delete(bs);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001486 if (ret) {
1487 return 1;
1488 }
Kevin Wolf3e85c6f2010-01-12 12:55:18 +01001489 return 0;
1490}
1491
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001492static int img_resize(int argc, char **argv)
1493{
1494 int c, ret, relative;
1495 const char *filename, *fmt, *size;
1496 int64_t n, total_size;
Jes Sorensen2a819982010-12-06 17:08:31 +01001497 BlockDriverState *bs = NULL;
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001498 QEMUOptionParameter *param;
1499 QEMUOptionParameter resize_options[] = {
1500 {
1501 .name = BLOCK_OPT_SIZE,
1502 .type = OPT_SIZE,
1503 .help = "Virtual disk size"
1504 },
1505 { NULL }
1506 };
1507
1508 fmt = NULL;
1509 for(;;) {
1510 c = getopt(argc, argv, "f:h");
1511 if (c == -1) {
1512 break;
1513 }
1514 switch(c) {
Jes Sorensenef873942010-12-06 15:25:40 +01001515 case '?':
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001516 case 'h':
1517 help();
1518 break;
1519 case 'f':
1520 fmt = optarg;
1521 break;
1522 }
1523 }
1524 if (optind + 1 >= argc) {
1525 help();
1526 }
1527 filename = argv[optind++];
1528 size = argv[optind++];
1529
1530 /* Choose grow, shrink, or absolute resize mode */
1531 switch (size[0]) {
1532 case '+':
1533 relative = 1;
1534 size++;
1535 break;
1536 case '-':
1537 relative = -1;
1538 size++;
1539 break;
1540 default:
1541 relative = 0;
1542 break;
1543 }
1544
1545 /* Parse size */
1546 param = parse_option_parameters("", resize_options, NULL);
1547 if (set_option_parameter(param, BLOCK_OPT_SIZE, size)) {
1548 /* Error message already printed when size parsing fails */
Jes Sorensen2a819982010-12-06 17:08:31 +01001549 ret = -1;
1550 goto out;
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001551 }
1552 n = get_option_parameter(param, BLOCK_OPT_SIZE)->value.n;
1553 free_option_parameters(param);
1554
1555 bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_RDWR);
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001556 if (!bs) {
Jes Sorensen2a819982010-12-06 17:08:31 +01001557 ret = -1;
1558 goto out;
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001559 }
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001560
1561 if (relative) {
1562 total_size = bdrv_getlength(bs) + n * relative;
1563 } else {
1564 total_size = n;
1565 }
1566 if (total_size <= 0) {
1567 error("New image size must be positive");
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001568 ret = -1;
1569 goto out;
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001570 }
1571
1572 ret = bdrv_truncate(bs, total_size);
1573 switch (ret) {
1574 case 0:
1575 printf("Image resized.\n");
1576 break;
1577 case -ENOTSUP:
1578 error("This image format does not support resize");
1579 break;
1580 case -EACCES:
1581 error("Image is read-only");
1582 break;
1583 default:
1584 error("Error resizing image (%d)", -ret);
1585 break;
1586 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001587out:
Jes Sorensen2a819982010-12-06 17:08:31 +01001588 if (bs) {
1589 bdrv_delete(bs);
1590 }
MORITA Kazutakac2abcce2010-06-21 04:26:35 +09001591 if (ret) {
1592 return 1;
1593 }
Stefan Hajnocziae6b0ed2010-04-24 09:12:12 +01001594 return 0;
1595}
1596
Anthony Liguoric227f092009-10-01 16:12:16 -05001597static const img_cmd_t img_cmds[] = {
Stuart Brady153859b2009-06-07 00:42:17 +01001598#define DEF(option, callback, arg_string) \
1599 { option, callback },
1600#include "qemu-img-cmds.h"
1601#undef DEF
1602#undef GEN_DOCS
1603 { NULL, NULL, },
1604};
1605
bellardea2384d2004-08-01 21:59:26 +00001606int main(int argc, char **argv)
1607{
Anthony Liguoric227f092009-10-01 16:12:16 -05001608 const img_cmd_t *cmd;
Stuart Brady153859b2009-06-07 00:42:17 +01001609 const char *cmdname;
bellardea2384d2004-08-01 21:59:26 +00001610
1611 bdrv_init();
1612 if (argc < 2)
1613 help();
Stuart Brady153859b2009-06-07 00:42:17 +01001614 cmdname = argv[1];
aurel328f9b1572009-02-09 18:14:31 +00001615 argc--; argv++;
Stuart Brady153859b2009-06-07 00:42:17 +01001616
1617 /* find the command */
1618 for(cmd = img_cmds; cmd->name != NULL; cmd++) {
1619 if (!strcmp(cmdname, cmd->name)) {
1620 return cmd->handler(argc, argv);
1621 }
bellardea2384d2004-08-01 21:59:26 +00001622 }
Stuart Brady153859b2009-06-07 00:42:17 +01001623
1624 /* not found */
1625 help();
bellardea2384d2004-08-01 21:59:26 +00001626 return 0;
1627}