]> git.proxmox.com Git - pve-qemu-kvm.git/blob - debian/patches/old/0007-vma-add-verify-command.patch
a6aff8577f377d03aaba2f5d04ca675103d499c0
[pve-qemu-kvm.git] / debian / patches / old / 0007-vma-add-verify-command.patch
1 From acdcd483ac6977e096ef7cde746d22bbf82e04d3 Mon Sep 17 00:00:00 2001
2 From: Dietmar Maurer <dietmar@proxmox.com>
3 Date: Mon, 11 Mar 2013 07:07:46 +0100
4 Subject: [PATCH v5 7/7] vma: add verify command
5
6 Users wants to verify the archive after backup.
7
8 Examples:
9
10 # vma verify -v test.vma
11
12 # lzop -d -c test.vma.lzo |vma verify -
13
14 Signed-off-by: Dietmar Maurer <dietmar@proxmox.com>
15 ---
16 vma-reader.c | 118 +++++++++++++++++++++++++++++++++++++++++++---------------
17 vma.c | 57 +++++++++++++++++++++++++++-
18 vma.h | 1 +
19 3 files changed, 145 insertions(+), 31 deletions(-)
20
21 diff --git a/vma-reader.c b/vma-reader.c
22 index bc36cba..a740f04 100644
23 --- a/vma-reader.c
24 +++ b/vma-reader.c
25 @@ -53,6 +53,8 @@ struct VmaReader {
26 time_t start_time;
27 int64_t cluster_count;
28 int64_t clusters_read;
29 + int64_t zero_cluster_data;
30 + int64_t partial_zero_cluster_data;
31 int clusters_read_per;
32 };
33
34 @@ -433,6 +435,27 @@ VmaDeviceInfo *vma_reader_get_device_info(VmaReader *vmar, guint8 dev_id)
35 return NULL;
36 }
37
38 +static void allocate_rstate(VmaReader *vmar, guint8 dev_id,
39 + BlockDriverState *bs, bool write_zeroes)
40 +{
41 + assert(vmar);
42 + assert(dev_id);
43 +
44 + vmar->rstate[dev_id].bs = bs;
45 + vmar->rstate[dev_id].write_zeroes = write_zeroes;
46 +
47 + int64_t size = vmar->devinfo[dev_id].size;
48 +
49 + int64_t bitmap_size = (size/BDRV_SECTOR_SIZE) +
50 + (VMA_CLUSTER_SIZE/BDRV_SECTOR_SIZE) * BITS_PER_LONG - 1;
51 + bitmap_size /= (VMA_CLUSTER_SIZE/BDRV_SECTOR_SIZE) * BITS_PER_LONG;
52 +
53 + vmar->rstate[dev_id].bitmap_size = bitmap_size;
54 + vmar->rstate[dev_id].bitmap = g_new0(unsigned long, bitmap_size);
55 +
56 + vmar->cluster_count += size/VMA_CLUSTER_SIZE;
57 +}
58 +
59 int vma_reader_register_bs(VmaReader *vmar, guint8 dev_id, BlockDriverState *bs,
60 bool write_zeroes, Error **errp)
61 {
62 @@ -449,17 +472,7 @@ int vma_reader_register_bs(VmaReader *vmar, guint8 dev_id, BlockDriverState *bs,
63 return -1;
64 }
65
66 - vmar->rstate[dev_id].bs = bs;
67 - vmar->rstate[dev_id].write_zeroes = write_zeroes;
68 -
69 - int64_t bitmap_size = (size/BDRV_SECTOR_SIZE) +
70 - (VMA_CLUSTER_SIZE/BDRV_SECTOR_SIZE) * BITS_PER_LONG - 1;
71 - bitmap_size /= (VMA_CLUSTER_SIZE/BDRV_SECTOR_SIZE) * BITS_PER_LONG;
72 -
73 - vmar->rstate[dev_id].bitmap_size = bitmap_size;
74 - vmar->rstate[dev_id].bitmap = g_new0(unsigned long, bitmap_size);
75 -
76 - vmar->cluster_count += size/VMA_CLUSTER_SIZE;
77 + allocate_rstate(vmar, dev_id, bs, write_zeroes);
78
79 return 0;
80 }
81 @@ -526,9 +539,10 @@ static int restore_write_data(VmaReader *vmar, guint8 dev_id,
82 }
83 return 0;
84 }
85 +
86 static int restore_extent(VmaReader *vmar, unsigned char *buf,
87 int extent_size, int vmstate_fd,
88 - bool verbose, Error **errp)
89 + bool verbose, bool verify, Error **errp)
90 {
91 assert(vmar);
92 assert(buf);
93 @@ -553,7 +567,7 @@ static int restore_extent(VmaReader *vmar, unsigned char *buf,
94
95 if (dev_id != vmar->vmstate_stream) {
96 bs = rstate->bs;
97 - if (!bs) {
98 + if (!verify && !bs) {
99 error_setg(errp, "got wrong dev id %d", dev_id);
100 return -1;
101 }
102 @@ -609,10 +623,13 @@ static int restore_extent(VmaReader *vmar, unsigned char *buf,
103 return -1;
104 }
105
106 - int nb_sectors = end_sector - sector_num;
107 - if (restore_write_data(vmar, dev_id, bs, vmstate_fd, buf + start,
108 - sector_num, nb_sectors, errp) < 0) {
109 - return -1;
110 + if (!verify) {
111 + int nb_sectors = end_sector - sector_num;
112 + if (restore_write_data(vmar, dev_id, bs, vmstate_fd,
113 + buf + start, sector_num, nb_sectors,
114 + errp) < 0) {
115 + return -1;
116 + }
117 }
118
119 start += VMA_CLUSTER_SIZE;
120 @@ -642,26 +659,37 @@ static int restore_extent(VmaReader *vmar, unsigned char *buf,
121 return -1;
122 }
123
124 - int nb_sectors = end_sector - sector_num;
125 - if (restore_write_data(vmar, dev_id, bs, vmstate_fd,
126 - buf + start, sector_num,
127 - nb_sectors, errp) < 0) {
128 - return -1;
129 + if (!verify) {
130 + int nb_sectors = end_sector - sector_num;
131 + if (restore_write_data(vmar, dev_id, bs, vmstate_fd,
132 + buf + start, sector_num,
133 + nb_sectors, errp) < 0) {
134 + return -1;
135 + }
136 }
137
138 start += VMA_BLOCK_SIZE;
139
140 } else {
141
142 - if (rstate->write_zeroes && (end_sector > sector_num)) {
143 +
144 + if (end_sector > sector_num) {
145 /* Todo: use bdrv_co_write_zeroes (but that need to
146 * be run inside coroutine?)
147 */
148 int nb_sectors = end_sector - sector_num;
149 - if (restore_write_data(vmar, dev_id, bs, vmstate_fd,
150 - zero_vma_block, sector_num,
151 - nb_sectors, errp) < 0) {
152 - return -1;
153 + int zero_size = BDRV_SECTOR_SIZE*nb_sectors;
154 + vmar->zero_cluster_data += zero_size;
155 + if (mask != 0) {
156 + vmar->partial_zero_cluster_data += zero_size;
157 + }
158 +
159 + if (rstate->write_zeroes && !verify) {
160 + if (restore_write_data(vmar, dev_id, bs, vmstate_fd,
161 + zero_vma_block, sector_num,
162 + nb_sectors, errp) < 0) {
163 + return -1;
164 + }
165 }
166 }
167 }
168 @@ -679,8 +707,9 @@ static int restore_extent(VmaReader *vmar, unsigned char *buf,
169 return 0;
170 }
171
172 -int vma_reader_restore(VmaReader *vmar, int vmstate_fd, bool verbose,
173 - Error **errp)
174 +static int vma_reader_restore_full(VmaReader *vmar, int vmstate_fd,
175 + bool verbose, bool verify,
176 + Error **errp)
177 {
178 assert(vmar);
179 assert(vmar->head_data);
180 @@ -747,7 +776,7 @@ int vma_reader_restore(VmaReader *vmar, int vmstate_fd, bool verbose,
181 }
182
183 if (restore_extent(vmar, buf, extent_size, vmstate_fd, verbose,
184 - errp) < 0) {
185 + verify, errp) < 0) {
186 return -1;
187 }
188
189 @@ -794,6 +823,35 @@ int vma_reader_restore(VmaReader *vmar, int vmstate_fd, bool verbose,
190 }
191 }
192
193 + if (verbose) {
194 + printf("total bytes read %zd, sparse bytes %zd (%.3g%%)\n",
195 + vmar->clusters_read*VMA_CLUSTER_SIZE,
196 + vmar->zero_cluster_data,
197 + (double)(100.0*vmar->zero_cluster_data)/
198 + (vmar->clusters_read*VMA_CLUSTER_SIZE));
199 + printf("space reduction due to 4K zero blocks %.3g%%\n",
200 + (double)(100.0*vmar->partial_zero_cluster_data) /
201 + (vmar->clusters_read*VMA_CLUSTER_SIZE-vmar->zero_cluster_data));
202 + }
203 return ret;
204 }
205
206 +int vma_reader_restore(VmaReader *vmar, int vmstate_fd, bool verbose,
207 + Error **errp)
208 +{
209 + return vma_reader_restore_full(vmar, vmstate_fd, verbose, false, errp);
210 +}
211 +
212 +int vma_reader_verify(VmaReader *vmar, bool verbose, Error **errp)
213 +{
214 + guint8 dev_id;
215 +
216 + for (dev_id = 1; dev_id < 255; dev_id++) {
217 + if (vma_reader_get_device_info(vmar, dev_id)) {
218 + allocate_rstate(vmar, dev_id, NULL, false);
219 + }
220 + }
221 +
222 + return vma_reader_restore_full(vmar, -1, verbose, true, errp);
223 +}
224 +
225 diff --git a/vma.c b/vma.c
226 index 6633aa5..bcde379 100644
227 --- a/vma.c
228 +++ b/vma.c
229 @@ -33,7 +33,8 @@ static void help(void)
230 "\n"
231 "vma list <filename>\n"
232 "vma create <filename> [-c config] <archive> pathname ...\n"
233 - "vma extract <filename> [-r] <targetdir>\n"
234 + "vma extract <filename> [-v] [-r] <targetdir>\n"
235 + "vma verify <filename> [-v]\n"
236 ;
237
238 printf("%s", help_msg);
239 @@ -337,6 +338,58 @@ static int extract_content(int argc, char **argv)
240 return ret;
241 }
242
243 +static int verify_content(int argc, char **argv)
244 +{
245 + int c, ret = 0;
246 + int verbose = 0;
247 + const char *filename;
248 +
249 + for (;;) {
250 + c = getopt(argc, argv, "hv");
251 + if (c == -1) {
252 + break;
253 + }
254 + switch (c) {
255 + case '?':
256 + case 'h':
257 + help();
258 + break;
259 + case 'v':
260 + verbose = 1;
261 + break;
262 + default:
263 + help();
264 + }
265 + }
266 +
267 + /* Get the filename */
268 + if ((optind + 1) != argc) {
269 + help();
270 + }
271 + filename = argv[optind++];
272 +
273 + Error *errp = NULL;
274 + VmaReader *vmar = vma_reader_create(filename, &errp);
275 +
276 + if (!vmar) {
277 + g_error("%s", error_get_pretty(errp));
278 + }
279 +
280 + if (verbose) {
281 + print_content(vmar);
282 + }
283 +
284 + if (vma_reader_verify(vmar, verbose, &errp) < 0) {
285 + g_error("verify failed - %s", error_get_pretty(errp));
286 + }
287 +
288 + vma_reader_destroy(vmar);
289 +
290 + bdrv_close_all();
291 +
292 + return ret;
293 +}
294 +
295 typedef struct BackupCB {
296 VmaWriter *vmaw;
297 uint8_t dev_id;
298 @@ -554,6 +607,8 @@ int main(int argc, char **argv)
299 return create_archive(argc, argv);
300 } else if (!strcmp(cmdname, "extract")) {
301 return extract_content(argc, argv);
302 + } else if (!strcmp(cmdname, "verify")) {
303 + return verify_content(argc, argv);
304 }
305
306 help();
307 diff --git a/vma.h b/vma.h
308 index 76d0dc8..ebd96c1 100644
309 --- a/vma.h
310 +++ b/vma.h
311 @@ -141,5 +141,6 @@ int vma_reader_register_bs(VmaReader *vmar, guint8 dev_id,
312 Error **errp);
313 int vma_reader_restore(VmaReader *vmar, int vmstate_fd, bool verbose,
314 Error **errp);
315 +int vma_reader_verify(VmaReader *vmar, bool verbose, Error **errp);
316
317 #endif /* BACKUP_VMA_H */
318 --
319 1.7.2.5
320