Statistics
| Branch: | Revision:

root / block / vmdk.c @ 2923d34f

History | View | Annotate | Download (45.3 kB)

1
/*
2
 * Block driver for the VMDK format
3
 *
4
 * Copyright (c) 2004 Fabrice Bellard
5
 * Copyright (c) 2005 Filip Navara
6
 *
7
 * Permission is hereby granted, free of charge, to any person obtaining a copy
8
 * of this software and associated documentation files (the "Software"), to deal
9
 * in the Software without restriction, including without limitation the rights
10
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11
 * copies of the Software, and to permit persons to whom the Software is
12
 * furnished to do so, subject to the following conditions:
13
 *
14
 * The above copyright notice and this permission notice shall be included in
15
 * all copies or substantial portions of the Software.
16
 *
17
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
20
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23
 * THE SOFTWARE.
24
 */
25

    
26
#include "qemu-common.h"
27
#include "block_int.h"
28
#include "module.h"
29
#include <zlib.h>
30

    
31
#define VMDK3_MAGIC (('C' << 24) | ('O' << 16) | ('W' << 8) | 'D')
32
#define VMDK4_MAGIC (('K' << 24) | ('D' << 16) | ('M' << 8) | 'V')
33
#define VMDK4_COMPRESSION_DEFLATE 1
34
#define VMDK4_FLAG_RGD (1 << 1)
35
#define VMDK4_FLAG_COMPRESS (1 << 16)
36
#define VMDK4_FLAG_MARKER (1 << 17)
37

    
38
typedef struct {
39
    uint32_t version;
40
    uint32_t flags;
41
    uint32_t disk_sectors;
42
    uint32_t granularity;
43
    uint32_t l1dir_offset;
44
    uint32_t l1dir_size;
45
    uint32_t file_sectors;
46
    uint32_t cylinders;
47
    uint32_t heads;
48
    uint32_t sectors_per_track;
49
} VMDK3Header;
50

    
51
typedef struct {
52
    uint32_t version;
53
    uint32_t flags;
54
    int64_t capacity;
55
    int64_t granularity;
56
    int64_t desc_offset;
57
    int64_t desc_size;
58
    int32_t num_gtes_per_gte;
59
    int64_t gd_offset;
60
    int64_t rgd_offset;
61
    int64_t grain_offset;
62
    char filler[1];
63
    char check_bytes[4];
64
    uint16_t compressAlgorithm;
65
} QEMU_PACKED VMDK4Header;
66

    
67
#define L2_CACHE_SIZE 16
68

    
69
typedef struct VmdkExtent {
70
    BlockDriverState *file;
71
    bool flat;
72
    bool compressed;
73
    bool has_marker;
74
    int64_t sectors;
75
    int64_t end_sector;
76
    int64_t flat_start_offset;
77
    int64_t l1_table_offset;
78
    int64_t l1_backup_table_offset;
79
    uint32_t *l1_table;
80
    uint32_t *l1_backup_table;
81
    unsigned int l1_size;
82
    uint32_t l1_entry_sectors;
83

    
84
    unsigned int l2_size;
85
    uint32_t *l2_cache;
86
    uint32_t l2_cache_offsets[L2_CACHE_SIZE];
87
    uint32_t l2_cache_counts[L2_CACHE_SIZE];
88

    
89
    unsigned int cluster_sectors;
90
} VmdkExtent;
91

    
92
typedef struct BDRVVmdkState {
93
    CoMutex lock;
94
    int desc_offset;
95
    bool cid_updated;
96
    uint32_t parent_cid;
97
    int num_extents;
98
    /* Extent array with num_extents entries, ascend ordered by address */
99
    VmdkExtent *extents;
100
} BDRVVmdkState;
101

    
102
typedef struct VmdkMetaData {
103
    uint32_t offset;
104
    unsigned int l1_index;
105
    unsigned int l2_index;
106
    unsigned int l2_offset;
107
    int valid;
108
} VmdkMetaData;
109

    
110
typedef struct VmdkGrainMarker {
111
    uint64_t lba;
112
    uint32_t size;
113
    uint8_t  data[0];
114
} VmdkGrainMarker;
115

    
116
static int vmdk_probe(const uint8_t *buf, int buf_size, const char *filename)
117
{
118
    uint32_t magic;
119

    
120
    if (buf_size < 4) {
121
        return 0;
122
    }
123
    magic = be32_to_cpu(*(uint32_t *)buf);
124
    if (magic == VMDK3_MAGIC ||
125
        magic == VMDK4_MAGIC) {
126
        return 100;
127
    } else {
128
        const char *p = (const char *)buf;
129
        const char *end = p + buf_size;
130
        while (p < end) {
131
            if (*p == '#') {
132
                /* skip comment line */
133
                while (p < end && *p != '\n') {
134
                    p++;
135
                }
136
                p++;
137
                continue;
138
            }
139
            if (*p == ' ') {
140
                while (p < end && *p == ' ') {
141
                    p++;
142
                }
143
                /* skip '\r' if windows line endings used. */
144
                if (p < end && *p == '\r') {
145
                    p++;
146
                }
147
                /* only accept blank lines before 'version=' line */
148
                if (p == end || *p != '\n') {
149
                    return 0;
150
                }
151
                p++;
152
                continue;
153
            }
154
            if (end - p >= strlen("version=X\n")) {
155
                if (strncmp("version=1\n", p, strlen("version=1\n")) == 0 ||
156
                    strncmp("version=2\n", p, strlen("version=2\n")) == 0) {
157
                    return 100;
158
                }
159
            }
160
            if (end - p >= strlen("version=X\r\n")) {
161
                if (strncmp("version=1\r\n", p, strlen("version=1\r\n")) == 0 ||
162
                    strncmp("version=2\r\n", p, strlen("version=2\r\n")) == 0) {
163
                    return 100;
164
                }
165
            }
166
            return 0;
167
        }
168
        return 0;
169
    }
170
}
171

    
172
#define CHECK_CID 1
173

    
174
#define SECTOR_SIZE 512
175
#define DESC_SIZE (20 * SECTOR_SIZE)    /* 20 sectors of 512 bytes each */
176
#define BUF_SIZE 4096
177
#define HEADER_SIZE 512                 /* first sector of 512 bytes */
178

    
179
static void vmdk_free_extents(BlockDriverState *bs)
180
{
181
    int i;
182
    BDRVVmdkState *s = bs->opaque;
183
    VmdkExtent *e;
184

    
185
    for (i = 0; i < s->num_extents; i++) {
186
        e = &s->extents[i];
187
        g_free(e->l1_table);
188
        g_free(e->l2_cache);
189
        g_free(e->l1_backup_table);
190
        if (e->file != bs->file) {
191
            bdrv_delete(e->file);
192
        }
193
    }
194
    g_free(s->extents);
195
}
196

    
197
static void vmdk_free_last_extent(BlockDriverState *bs)
198
{
199
    BDRVVmdkState *s = bs->opaque;
200

    
201
    if (s->num_extents == 0) {
202
        return;
203
    }
204
    s->num_extents--;
205
    s->extents = g_realloc(s->extents, s->num_extents * sizeof(VmdkExtent));
206
}
207

    
208
static uint32_t vmdk_read_cid(BlockDriverState *bs, int parent)
209
{
210
    char desc[DESC_SIZE];
211
    uint32_t cid = 0xffffffff;
212
    const char *p_name, *cid_str;
213
    size_t cid_str_size;
214
    BDRVVmdkState *s = bs->opaque;
215
    int ret;
216

    
217
    ret = bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE);
218
    if (ret < 0) {
219
        return 0;
220
    }
221

    
222
    if (parent) {
223
        cid_str = "parentCID";
224
        cid_str_size = sizeof("parentCID");
225
    } else {
226
        cid_str = "CID";
227
        cid_str_size = sizeof("CID");
228
    }
229

    
230
    desc[DESC_SIZE - 1] = '\0';
231
    p_name = strstr(desc, cid_str);
232
    if (p_name != NULL) {
233
        p_name += cid_str_size;
234
        sscanf(p_name, "%x", &cid);
235
    }
236

    
237
    return cid;
238
}
239

    
240
static int vmdk_write_cid(BlockDriverState *bs, uint32_t cid)
241
{
242
    char desc[DESC_SIZE], tmp_desc[DESC_SIZE];
243
    char *p_name, *tmp_str;
244
    BDRVVmdkState *s = bs->opaque;
245
    int ret;
246

    
247
    ret = bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE);
248
    if (ret < 0) {
249
        return ret;
250
    }
251

    
252
    desc[DESC_SIZE - 1] = '\0';
253
    tmp_str = strstr(desc, "parentCID");
254
    if (tmp_str == NULL) {
255
        return -EINVAL;
256
    }
257

    
258
    pstrcpy(tmp_desc, sizeof(tmp_desc), tmp_str);
259
    p_name = strstr(desc, "CID");
260
    if (p_name != NULL) {
261
        p_name += sizeof("CID");
262
        snprintf(p_name, sizeof(desc) - (p_name - desc), "%x\n", cid);
263
        pstrcat(desc, sizeof(desc), tmp_desc);
264
    }
265

    
266
    ret = bdrv_pwrite_sync(bs->file, s->desc_offset, desc, DESC_SIZE);
267
    if (ret < 0) {
268
        return ret;
269
    }
270

    
271
    return 0;
272
}
273

    
274
static int vmdk_is_cid_valid(BlockDriverState *bs)
275
{
276
#ifdef CHECK_CID
277
    BDRVVmdkState *s = bs->opaque;
278
    BlockDriverState *p_bs = bs->backing_hd;
279
    uint32_t cur_pcid;
280

    
281
    if (p_bs) {
282
        cur_pcid = vmdk_read_cid(p_bs, 0);
283
        if (s->parent_cid != cur_pcid) {
284
            /* CID not valid */
285
            return 0;
286
        }
287
    }
288
#endif
289
    /* CID valid */
290
    return 1;
291
}
292

    
293
static int vmdk_parent_open(BlockDriverState *bs)
294
{
295
    char *p_name;
296
    char desc[DESC_SIZE + 1];
297
    BDRVVmdkState *s = bs->opaque;
298
    int ret;
299

    
300
    desc[DESC_SIZE] = '\0';
301
    ret = bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE);
302
    if (ret < 0) {
303
        return ret;
304
    }
305

    
306
    p_name = strstr(desc, "parentFileNameHint");
307
    if (p_name != NULL) {
308
        char *end_name;
309

    
310
        p_name += sizeof("parentFileNameHint") + 1;
311
        end_name = strchr(p_name, '\"');
312
        if (end_name == NULL) {
313
            return -EINVAL;
314
        }
315
        if ((end_name - p_name) > sizeof(bs->backing_file) - 1) {
316
            return -EINVAL;
317
        }
318

    
319
        pstrcpy(bs->backing_file, end_name - p_name + 1, p_name);
320
    }
321

    
322
    return 0;
323
}
324

    
325
/* Create and append extent to the extent array. Return the added VmdkExtent
326
 * address. return NULL if allocation failed. */
327
static VmdkExtent *vmdk_add_extent(BlockDriverState *bs,
328
                           BlockDriverState *file, bool flat, int64_t sectors,
329
                           int64_t l1_offset, int64_t l1_backup_offset,
330
                           uint32_t l1_size,
331
                           int l2_size, unsigned int cluster_sectors)
332
{
333
    VmdkExtent *extent;
334
    BDRVVmdkState *s = bs->opaque;
335

    
336
    s->extents = g_realloc(s->extents,
337
                              (s->num_extents + 1) * sizeof(VmdkExtent));
338
    extent = &s->extents[s->num_extents];
339
    s->num_extents++;
340

    
341
    memset(extent, 0, sizeof(VmdkExtent));
342
    extent->file = file;
343
    extent->flat = flat;
344
    extent->sectors = sectors;
345
    extent->l1_table_offset = l1_offset;
346
    extent->l1_backup_table_offset = l1_backup_offset;
347
    extent->l1_size = l1_size;
348
    extent->l1_entry_sectors = l2_size * cluster_sectors;
349
    extent->l2_size = l2_size;
350
    extent->cluster_sectors = cluster_sectors;
351

    
352
    if (s->num_extents > 1) {
353
        extent->end_sector = (*(extent - 1)).end_sector + extent->sectors;
354
    } else {
355
        extent->end_sector = extent->sectors;
356
    }
357
    bs->total_sectors = extent->end_sector;
358
    return extent;
359
}
360

    
361
static int vmdk_init_tables(BlockDriverState *bs, VmdkExtent *extent)
362
{
363
    int ret;
364
    int l1_size, i;
365

    
366
    /* read the L1 table */
367
    l1_size = extent->l1_size * sizeof(uint32_t);
368
    extent->l1_table = g_malloc(l1_size);
369
    ret = bdrv_pread(extent->file,
370
                    extent->l1_table_offset,
371
                    extent->l1_table,
372
                    l1_size);
373
    if (ret < 0) {
374
        goto fail_l1;
375
    }
376
    for (i = 0; i < extent->l1_size; i++) {
377
        le32_to_cpus(&extent->l1_table[i]);
378
    }
379

    
380
    if (extent->l1_backup_table_offset) {
381
        extent->l1_backup_table = g_malloc(l1_size);
382
        ret = bdrv_pread(extent->file,
383
                        extent->l1_backup_table_offset,
384
                        extent->l1_backup_table,
385
                        l1_size);
386
        if (ret < 0) {
387
            goto fail_l1b;
388
        }
389
        for (i = 0; i < extent->l1_size; i++) {
390
            le32_to_cpus(&extent->l1_backup_table[i]);
391
        }
392
    }
393

    
394
    extent->l2_cache =
395
        g_malloc(extent->l2_size * L2_CACHE_SIZE * sizeof(uint32_t));
396
    return 0;
397
 fail_l1b:
398
    g_free(extent->l1_backup_table);
399
 fail_l1:
400
    g_free(extent->l1_table);
401
    return ret;
402
}
403

    
404
static int vmdk_open_vmdk3(BlockDriverState *bs,
405
                           BlockDriverState *file,
406
                           int flags)
407
{
408
    int ret;
409
    uint32_t magic;
410
    VMDK3Header header;
411
    VmdkExtent *extent;
412

    
413
    ret = bdrv_pread(file, sizeof(magic), &header, sizeof(header));
414
    if (ret < 0) {
415
        return ret;
416
    }
417
    extent = vmdk_add_extent(bs,
418
                             bs->file, false,
419
                             le32_to_cpu(header.disk_sectors),
420
                             le32_to_cpu(header.l1dir_offset) << 9,
421
                             0, 1 << 6, 1 << 9,
422
                             le32_to_cpu(header.granularity));
423
    ret = vmdk_init_tables(bs, extent);
424
    if (ret) {
425
        /* free extent allocated by vmdk_add_extent */
426
        vmdk_free_last_extent(bs);
427
    }
428
    return ret;
429
}
430

    
431
static int vmdk_open_desc_file(BlockDriverState *bs, int flags,
432
                               int64_t desc_offset);
433

    
434
static int vmdk_open_vmdk4(BlockDriverState *bs,
435
                           BlockDriverState *file,
436
                           int flags)
437
{
438
    int ret;
439
    uint32_t magic;
440
    uint32_t l1_size, l1_entry_sectors;
441
    VMDK4Header header;
442
    VmdkExtent *extent;
443
    int64_t l1_backup_offset = 0;
444

    
445
    ret = bdrv_pread(file, sizeof(magic), &header, sizeof(header));
446
    if (ret < 0) {
447
        return ret;
448
    }
449
    if (header.capacity == 0 && header.desc_offset) {
450
        return vmdk_open_desc_file(bs, flags, header.desc_offset << 9);
451
    }
452
    l1_entry_sectors = le32_to_cpu(header.num_gtes_per_gte)
453
                        * le64_to_cpu(header.granularity);
454
    if (l1_entry_sectors <= 0) {
455
        return -EINVAL;
456
    }
457
    l1_size = (le64_to_cpu(header.capacity) + l1_entry_sectors - 1)
458
                / l1_entry_sectors;
459
    if (le32_to_cpu(header.flags) & VMDK4_FLAG_RGD) {
460
        l1_backup_offset = le64_to_cpu(header.rgd_offset) << 9;
461
    }
462
    extent = vmdk_add_extent(bs, file, false,
463
                          le64_to_cpu(header.capacity),
464
                          le64_to_cpu(header.gd_offset) << 9,
465
                          l1_backup_offset,
466
                          l1_size,
467
                          le32_to_cpu(header.num_gtes_per_gte),
468
                          le64_to_cpu(header.granularity));
469
    extent->compressed =
470
        le16_to_cpu(header.compressAlgorithm) == VMDK4_COMPRESSION_DEFLATE;
471
    extent->has_marker = le32_to_cpu(header.flags) & VMDK4_FLAG_MARKER;
472
    ret = vmdk_init_tables(bs, extent);
473
    if (ret) {
474
        /* free extent allocated by vmdk_add_extent */
475
        vmdk_free_last_extent(bs);
476
    }
477
    return ret;
478
}
479

    
480
/* find an option value out of descriptor file */
481
static int vmdk_parse_description(const char *desc, const char *opt_name,
482
        char *buf, int buf_size)
483
{
484
    char *opt_pos, *opt_end;
485
    const char *end = desc + strlen(desc);
486

    
487
    opt_pos = strstr(desc, opt_name);
488
    if (!opt_pos) {
489
        return -1;
490
    }
491
    /* Skip "=\"" following opt_name */
492
    opt_pos += strlen(opt_name) + 2;
493
    if (opt_pos >= end) {
494
        return -1;
495
    }
496
    opt_end = opt_pos;
497
    while (opt_end < end && *opt_end != '"') {
498
        opt_end++;
499
    }
500
    if (opt_end == end || buf_size < opt_end - opt_pos + 1) {
501
        return -1;
502
    }
503
    pstrcpy(buf, opt_end - opt_pos + 1, opt_pos);
504
    return 0;
505
}
506

    
507
/* Open an extent file and append to bs array */
508
static int vmdk_open_sparse(BlockDriverState *bs,
509
                            BlockDriverState *file,
510
                            int flags)
511
{
512
    uint32_t magic;
513

    
514
    if (bdrv_pread(file, 0, &magic, sizeof(magic)) != sizeof(magic)) {
515
        return -EIO;
516
    }
517

    
518
    magic = be32_to_cpu(magic);
519
    switch (magic) {
520
        case VMDK3_MAGIC:
521
            return vmdk_open_vmdk3(bs, file, flags);
522
            break;
523
        case VMDK4_MAGIC:
524
            return vmdk_open_vmdk4(bs, file, flags);
525
            break;
526
        default:
527
            return -EINVAL;
528
            break;
529
    }
530
}
531

    
532
static int vmdk_parse_extents(const char *desc, BlockDriverState *bs,
533
        const char *desc_file_path)
534
{
535
    int ret;
536
    char access[11];
537
    char type[11];
538
    char fname[512];
539
    const char *p = desc;
540
    int64_t sectors = 0;
541
    int64_t flat_offset;
542
    char extent_path[PATH_MAX];
543
    BlockDriverState *extent_file;
544

    
545
    while (*p) {
546
        /* parse extent line:
547
         * RW [size in sectors] FLAT "file-name.vmdk" OFFSET
548
         * or
549
         * RW [size in sectors] SPARSE "file-name.vmdk"
550
         */
551
        flat_offset = -1;
552
        ret = sscanf(p, "%10s %" SCNd64 " %10s %511s %" SCNd64,
553
                access, &sectors, type, fname, &flat_offset);
554
        if (ret < 4 || strcmp(access, "RW")) {
555
            goto next_line;
556
        } else if (!strcmp(type, "FLAT")) {
557
            if (ret != 5 || flat_offset < 0) {
558
                return -EINVAL;
559
            }
560
        } else if (ret != 4) {
561
            return -EINVAL;
562
        }
563

    
564
        /* trim the quotation marks around */
565
        if (fname[0] == '"') {
566
            memmove(fname, fname + 1, strlen(fname));
567
            if (strlen(fname) <= 1 || fname[strlen(fname) - 1] != '"') {
568
                return -EINVAL;
569
            }
570
            fname[strlen(fname) - 1] = '\0';
571
        }
572
        if (sectors <= 0 ||
573
            (strcmp(type, "FLAT") && strcmp(type, "SPARSE")) ||
574
            (strcmp(access, "RW"))) {
575
            goto next_line;
576
        }
577

    
578
        path_combine(extent_path, sizeof(extent_path),
579
                desc_file_path, fname);
580
        ret = bdrv_file_open(&extent_file, extent_path, bs->open_flags);
581
        if (ret) {
582
            return ret;
583
        }
584

    
585
        /* save to extents array */
586
        if (!strcmp(type, "FLAT")) {
587
            /* FLAT extent */
588
            VmdkExtent *extent;
589

    
590
            extent = vmdk_add_extent(bs, extent_file, true, sectors,
591
                            0, 0, 0, 0, sectors);
592
            extent->flat_start_offset = flat_offset << 9;
593
        } else if (!strcmp(type, "SPARSE")) {
594
            /* SPARSE extent */
595
            ret = vmdk_open_sparse(bs, extent_file, bs->open_flags);
596
            if (ret) {
597
                bdrv_delete(extent_file);
598
                return ret;
599
            }
600
        } else {
601
            fprintf(stderr,
602
                "VMDK: Not supported extent type \"%s\""".\n", type);
603
            return -ENOTSUP;
604
        }
605
next_line:
606
        /* move to next line */
607
        while (*p && *p != '\n') {
608
            p++;
609
        }
610
        p++;
611
    }
612
    return 0;
613
}
614

    
615
static int vmdk_open_desc_file(BlockDriverState *bs, int flags,
616
                               int64_t desc_offset)
617
{
618
    int ret;
619
    char buf[2048];
620
    char ct[128];
621
    BDRVVmdkState *s = bs->opaque;
622

    
623
    ret = bdrv_pread(bs->file, desc_offset, buf, sizeof(buf));
624
    if (ret < 0) {
625
        return ret;
626
    }
627
    buf[2047] = '\0';
628
    if (vmdk_parse_description(buf, "createType", ct, sizeof(ct))) {
629
        return -EINVAL;
630
    }
631
    if (strcmp(ct, "monolithicFlat") &&
632
        strcmp(ct, "twoGbMaxExtentSparse") &&
633
        strcmp(ct, "twoGbMaxExtentFlat")) {
634
        fprintf(stderr,
635
                "VMDK: Not supported image type \"%s\""".\n", ct);
636
        return -ENOTSUP;
637
    }
638
    s->desc_offset = 0;
639
    return vmdk_parse_extents(buf, bs, bs->file->filename);
640
}
641

    
642
static int vmdk_open(BlockDriverState *bs, int flags)
643
{
644
    int ret;
645
    BDRVVmdkState *s = bs->opaque;
646

    
647
    if (vmdk_open_sparse(bs, bs->file, flags) == 0) {
648
        s->desc_offset = 0x200;
649
    } else {
650
        ret = vmdk_open_desc_file(bs, flags, 0);
651
        if (ret) {
652
            goto fail;
653
        }
654
    }
655
    /* try to open parent images, if exist */
656
    ret = vmdk_parent_open(bs);
657
    if (ret) {
658
        goto fail;
659
    }
660
    s->parent_cid = vmdk_read_cid(bs, 1);
661
    qemu_co_mutex_init(&s->lock);
662
    return ret;
663

    
664
fail:
665
    vmdk_free_extents(bs);
666
    return ret;
667
}
668

    
669
static int get_whole_cluster(BlockDriverState *bs,
670
                VmdkExtent *extent,
671
                uint64_t cluster_offset,
672
                uint64_t offset,
673
                bool allocate)
674
{
675
    /* 128 sectors * 512 bytes each = grain size 64KB */
676
    uint8_t  whole_grain[extent->cluster_sectors * 512];
677

    
678
    /* we will be here if it's first write on non-exist grain(cluster).
679
     * try to read from parent image, if exist */
680
    if (bs->backing_hd) {
681
        int ret;
682

    
683
        if (!vmdk_is_cid_valid(bs)) {
684
            return -1;
685
        }
686

    
687
        /* floor offset to cluster */
688
        offset -= offset % (extent->cluster_sectors * 512);
689
        ret = bdrv_read(bs->backing_hd, offset >> 9, whole_grain,
690
                extent->cluster_sectors);
691
        if (ret < 0) {
692
            return -1;
693
        }
694

    
695
        /* Write grain only into the active image */
696
        ret = bdrv_write(extent->file, cluster_offset, whole_grain,
697
                extent->cluster_sectors);
698
        if (ret < 0) {
699
            return -1;
700
        }
701
    }
702
    return 0;
703
}
704

    
705
static int vmdk_L2update(VmdkExtent *extent, VmdkMetaData *m_data)
706
{
707
    /* update L2 table */
708
    if (bdrv_pwrite_sync(
709
                extent->file,
710
                ((int64_t)m_data->l2_offset * 512)
711
                    + (m_data->l2_index * sizeof(m_data->offset)),
712
                &(m_data->offset),
713
                sizeof(m_data->offset)
714
            ) < 0) {
715
        return -1;
716
    }
717
    /* update backup L2 table */
718
    if (extent->l1_backup_table_offset != 0) {
719
        m_data->l2_offset = extent->l1_backup_table[m_data->l1_index];
720
        if (bdrv_pwrite_sync(
721
                    extent->file,
722
                    ((int64_t)m_data->l2_offset * 512)
723
                        + (m_data->l2_index * sizeof(m_data->offset)),
724
                    &(m_data->offset), sizeof(m_data->offset)
725
                ) < 0) {
726
            return -1;
727
        }
728
    }
729

    
730
    return 0;
731
}
732

    
733
static int get_cluster_offset(BlockDriverState *bs,
734
                                    VmdkExtent *extent,
735
                                    VmdkMetaData *m_data,
736
                                    uint64_t offset,
737
                                    int allocate,
738
                                    uint64_t *cluster_offset)
739
{
740
    unsigned int l1_index, l2_offset, l2_index;
741
    int min_index, i, j;
742
    uint32_t min_count, *l2_table, tmp = 0;
743

    
744
    if (m_data) {
745
        m_data->valid = 0;
746
    }
747
    if (extent->flat) {
748
        *cluster_offset = extent->flat_start_offset;
749
        return 0;
750
    }
751

    
752
    offset -= (extent->end_sector - extent->sectors) * SECTOR_SIZE;
753
    l1_index = (offset >> 9) / extent->l1_entry_sectors;
754
    if (l1_index >= extent->l1_size) {
755
        return -1;
756
    }
757
    l2_offset = extent->l1_table[l1_index];
758
    if (!l2_offset) {
759
        return -1;
760
    }
761
    for (i = 0; i < L2_CACHE_SIZE; i++) {
762
        if (l2_offset == extent->l2_cache_offsets[i]) {
763
            /* increment the hit count */
764
            if (++extent->l2_cache_counts[i] == 0xffffffff) {
765
                for (j = 0; j < L2_CACHE_SIZE; j++) {
766
                    extent->l2_cache_counts[j] >>= 1;
767
                }
768
            }
769
            l2_table = extent->l2_cache + (i * extent->l2_size);
770
            goto found;
771
        }
772
    }
773
    /* not found: load a new entry in the least used one */
774
    min_index = 0;
775
    min_count = 0xffffffff;
776
    for (i = 0; i < L2_CACHE_SIZE; i++) {
777
        if (extent->l2_cache_counts[i] < min_count) {
778
            min_count = extent->l2_cache_counts[i];
779
            min_index = i;
780
        }
781
    }
782
    l2_table = extent->l2_cache + (min_index * extent->l2_size);
783
    if (bdrv_pread(
784
                extent->file,
785
                (int64_t)l2_offset * 512,
786
                l2_table,
787
                extent->l2_size * sizeof(uint32_t)
788
            ) != extent->l2_size * sizeof(uint32_t)) {
789
        return -1;
790
    }
791

    
792
    extent->l2_cache_offsets[min_index] = l2_offset;
793
    extent->l2_cache_counts[min_index] = 1;
794
 found:
795
    l2_index = ((offset >> 9) / extent->cluster_sectors) % extent->l2_size;
796
    *cluster_offset = le32_to_cpu(l2_table[l2_index]);
797

    
798
    if (!*cluster_offset) {
799
        if (!allocate) {
800
            return -1;
801
        }
802

    
803
        /* Avoid the L2 tables update for the images that have snapshots. */
804
        *cluster_offset = bdrv_getlength(extent->file);
805
        if (!extent->compressed) {
806
            bdrv_truncate(
807
                extent->file,
808
                *cluster_offset + (extent->cluster_sectors << 9)
809
            );
810
        }
811

    
812
        *cluster_offset >>= 9;
813
        tmp = cpu_to_le32(*cluster_offset);
814
        l2_table[l2_index] = tmp;
815

    
816
        /* First of all we write grain itself, to avoid race condition
817
         * that may to corrupt the image.
818
         * This problem may occur because of insufficient space on host disk
819
         * or inappropriate VM shutdown.
820
         */
821
        if (get_whole_cluster(
822
                bs, extent, *cluster_offset, offset, allocate) == -1) {
823
            return -1;
824
        }
825

    
826
        if (m_data) {
827
            m_data->offset = tmp;
828
            m_data->l1_index = l1_index;
829
            m_data->l2_index = l2_index;
830
            m_data->l2_offset = l2_offset;
831
            m_data->valid = 1;
832
        }
833
    }
834
    *cluster_offset <<= 9;
835
    return 0;
836
}
837

    
838
static VmdkExtent *find_extent(BDRVVmdkState *s,
839
                                int64_t sector_num, VmdkExtent *start_hint)
840
{
841
    VmdkExtent *extent = start_hint;
842

    
843
    if (!extent) {
844
        extent = &s->extents[0];
845
    }
846
    while (extent < &s->extents[s->num_extents]) {
847
        if (sector_num < extent->end_sector) {
848
            return extent;
849
        }
850
        extent++;
851
    }
852
    return NULL;
853
}
854

    
855
static int vmdk_is_allocated(BlockDriverState *bs, int64_t sector_num,
856
                             int nb_sectors, int *pnum)
857
{
858
    BDRVVmdkState *s = bs->opaque;
859
    int64_t index_in_cluster, n, ret;
860
    uint64_t offset;
861
    VmdkExtent *extent;
862

    
863
    extent = find_extent(s, sector_num, NULL);
864
    if (!extent) {
865
        return 0;
866
    }
867
    ret = get_cluster_offset(bs, extent, NULL,
868
                            sector_num * 512, 0, &offset);
869
    /* get_cluster_offset returning 0 means success */
870
    ret = !ret;
871

    
872
    index_in_cluster = sector_num % extent->cluster_sectors;
873
    n = extent->cluster_sectors - index_in_cluster;
874
    if (n > nb_sectors) {
875
        n = nb_sectors;
876
    }
877
    *pnum = n;
878
    return ret;
879
}
880

    
881
static int vmdk_write_extent(VmdkExtent *extent, int64_t cluster_offset,
882
                            int64_t offset_in_cluster, const uint8_t *buf,
883
                            int nb_sectors, int64_t sector_num)
884
{
885
    int ret;
886
    VmdkGrainMarker *data = NULL;
887
    uLongf buf_len;
888
    const uint8_t *write_buf = buf;
889
    int write_len = nb_sectors * 512;
890

    
891
    if (extent->compressed) {
892
        if (!extent->has_marker) {
893
            ret = -EINVAL;
894
            goto out;
895
        }
896
        buf_len = (extent->cluster_sectors << 9) * 2;
897
        data = g_malloc(buf_len + sizeof(VmdkGrainMarker));
898
        if (compress(data->data, &buf_len, buf, nb_sectors << 9) != Z_OK ||
899
                buf_len == 0) {
900
            ret = -EINVAL;
901
            goto out;
902
        }
903
        data->lba = sector_num;
904
        data->size = buf_len;
905
        write_buf = (uint8_t *)data;
906
        write_len = buf_len + sizeof(VmdkGrainMarker);
907
    }
908
    ret = bdrv_pwrite(extent->file,
909
                        cluster_offset + offset_in_cluster,
910
                        write_buf,
911
                        write_len);
912
    if (ret != write_len) {
913
        ret = ret < 0 ? ret : -EIO;
914
        goto out;
915
    }
916
    ret = 0;
917
 out:
918
    g_free(data);
919
    return ret;
920
}
921

    
922
static int vmdk_read_extent(VmdkExtent *extent, int64_t cluster_offset,
923
                            int64_t offset_in_cluster, uint8_t *buf,
924
                            int nb_sectors)
925
{
926
    int ret;
927
    int cluster_bytes, buf_bytes;
928
    uint8_t *cluster_buf, *compressed_data;
929
    uint8_t *uncomp_buf;
930
    uint32_t data_len;
931
    VmdkGrainMarker *marker;
932
    uLongf buf_len;
933

    
934

    
935
    if (!extent->compressed) {
936
        ret = bdrv_pread(extent->file,
937
                          cluster_offset + offset_in_cluster,
938
                          buf, nb_sectors * 512);
939
        if (ret == nb_sectors * 512) {
940
            return 0;
941
        } else {
942
            return -EIO;
943
        }
944
    }
945
    cluster_bytes = extent->cluster_sectors * 512;
946
    /* Read two clusters in case GrainMarker + compressed data > one cluster */
947
    buf_bytes = cluster_bytes * 2;
948
    cluster_buf = g_malloc(buf_bytes);
949
    uncomp_buf = g_malloc(cluster_bytes);
950
    ret = bdrv_pread(extent->file,
951
                cluster_offset,
952
                cluster_buf, buf_bytes);
953
    if (ret < 0) {
954
        goto out;
955
    }
956
    compressed_data = cluster_buf;
957
    buf_len = cluster_bytes;
958
    data_len = cluster_bytes;
959
    if (extent->has_marker) {
960
        marker = (VmdkGrainMarker *)cluster_buf;
961
        compressed_data = marker->data;
962
        data_len = le32_to_cpu(marker->size);
963
    }
964
    if (!data_len || data_len > buf_bytes) {
965
        ret = -EINVAL;
966
        goto out;
967
    }
968
    ret = uncompress(uncomp_buf, &buf_len, compressed_data, data_len);
969
    if (ret != Z_OK) {
970
        ret = -EINVAL;
971
        goto out;
972

    
973
    }
974
    if (offset_in_cluster < 0 ||
975
            offset_in_cluster + nb_sectors * 512 > buf_len) {
976
        ret = -EINVAL;
977
        goto out;
978
    }
979
    memcpy(buf, uncomp_buf + offset_in_cluster, nb_sectors * 512);
980
    ret = 0;
981

    
982
 out:
983
    g_free(uncomp_buf);
984
    g_free(cluster_buf);
985
    return ret;
986
}
987

    
988
static int vmdk_read(BlockDriverState *bs, int64_t sector_num,
989
                    uint8_t *buf, int nb_sectors)
990
{
991
    BDRVVmdkState *s = bs->opaque;
992
    int ret;
993
    uint64_t n, index_in_cluster;
994
    VmdkExtent *extent = NULL;
995
    uint64_t cluster_offset;
996

    
997
    while (nb_sectors > 0) {
998
        extent = find_extent(s, sector_num, extent);
999
        if (!extent) {
1000
            return -EIO;
1001
        }
1002
        ret = get_cluster_offset(
1003
                            bs, extent, NULL,
1004
                            sector_num << 9, 0, &cluster_offset);
1005
        index_in_cluster = sector_num % extent->cluster_sectors;
1006
        n = extent->cluster_sectors - index_in_cluster;
1007
        if (n > nb_sectors) {
1008
            n = nb_sectors;
1009
        }
1010
        if (ret) {
1011
            /* if not allocated, try to read from parent image, if exist */
1012
            if (bs->backing_hd) {
1013
                if (!vmdk_is_cid_valid(bs)) {
1014
                    return -EINVAL;
1015
                }
1016
                ret = bdrv_read(bs->backing_hd, sector_num, buf, n);
1017
                if (ret < 0) {
1018
                    return ret;
1019
                }
1020
            } else {
1021
                memset(buf, 0, 512 * n);
1022
            }
1023
        } else {
1024
            ret = vmdk_read_extent(extent,
1025
                            cluster_offset, index_in_cluster * 512,
1026
                            buf, n);
1027
            if (ret) {
1028
                return ret;
1029
            }
1030
        }
1031
        nb_sectors -= n;
1032
        sector_num += n;
1033
        buf += n * 512;
1034
    }
1035
    return 0;
1036
}
1037

    
1038
static coroutine_fn int vmdk_co_read(BlockDriverState *bs, int64_t sector_num,
1039
                                     uint8_t *buf, int nb_sectors)
1040
{
1041
    int ret;
1042
    BDRVVmdkState *s = bs->opaque;
1043
    qemu_co_mutex_lock(&s->lock);
1044
    ret = vmdk_read(bs, sector_num, buf, nb_sectors);
1045
    qemu_co_mutex_unlock(&s->lock);
1046
    return ret;
1047
}
1048

    
1049
static int vmdk_write(BlockDriverState *bs, int64_t sector_num,
1050
                     const uint8_t *buf, int nb_sectors)
1051
{
1052
    BDRVVmdkState *s = bs->opaque;
1053
    VmdkExtent *extent = NULL;
1054
    int n, ret;
1055
    int64_t index_in_cluster;
1056
    uint64_t cluster_offset;
1057
    VmdkMetaData m_data;
1058

    
1059
    if (sector_num > bs->total_sectors) {
1060
        fprintf(stderr,
1061
                "(VMDK) Wrong offset: sector_num=0x%" PRIx64
1062
                " total_sectors=0x%" PRIx64 "\n",
1063
                sector_num, bs->total_sectors);
1064
        return -EIO;
1065
    }
1066

    
1067
    while (nb_sectors > 0) {
1068
        extent = find_extent(s, sector_num, extent);
1069
        if (!extent) {
1070
            return -EIO;
1071
        }
1072
        ret = get_cluster_offset(
1073
                                bs,
1074
                                extent,
1075
                                &m_data,
1076
                                sector_num << 9, !extent->compressed,
1077
                                &cluster_offset);
1078
        if (extent->compressed) {
1079
            if (ret == 0) {
1080
                /* Refuse write to allocated cluster for streamOptimized */
1081
                fprintf(stderr,
1082
                        "VMDK: can't write to allocated cluster"
1083
                        " for streamOptimized\n");
1084
                return -EIO;
1085
            } else {
1086
                /* allocate */
1087
                ret = get_cluster_offset(
1088
                                        bs,
1089
                                        extent,
1090
                                        &m_data,
1091
                                        sector_num << 9, 1,
1092
                                        &cluster_offset);
1093
            }
1094
        }
1095
        if (ret) {
1096
            return -EINVAL;
1097
        }
1098
        index_in_cluster = sector_num % extent->cluster_sectors;
1099
        n = extent->cluster_sectors - index_in_cluster;
1100
        if (n > nb_sectors) {
1101
            n = nb_sectors;
1102
        }
1103

    
1104
        ret = vmdk_write_extent(extent,
1105
                        cluster_offset, index_in_cluster * 512,
1106
                        buf, n, sector_num);
1107
        if (ret) {
1108
            return ret;
1109
        }
1110
        if (m_data.valid) {
1111
            /* update L2 tables */
1112
            if (vmdk_L2update(extent, &m_data) == -1) {
1113
                return -EIO;
1114
            }
1115
        }
1116
        nb_sectors -= n;
1117
        sector_num += n;
1118
        buf += n * 512;
1119

    
1120
        /* update CID on the first write every time the virtual disk is
1121
         * opened */
1122
        if (!s->cid_updated) {
1123
            ret = vmdk_write_cid(bs, time(NULL));
1124
            if (ret < 0) {
1125
                return ret;
1126
            }
1127
            s->cid_updated = true;
1128
        }
1129
    }
1130
    return 0;
1131
}
1132

    
1133
static coroutine_fn int vmdk_co_write(BlockDriverState *bs, int64_t sector_num,
1134
                                      const uint8_t *buf, int nb_sectors)
1135
{
1136
    int ret;
1137
    BDRVVmdkState *s = bs->opaque;
1138
    qemu_co_mutex_lock(&s->lock);
1139
    ret = vmdk_write(bs, sector_num, buf, nb_sectors);
1140
    qemu_co_mutex_unlock(&s->lock);
1141
    return ret;
1142
}
1143

    
1144

    
1145
static int vmdk_create_extent(const char *filename, int64_t filesize,
1146
                              bool flat, bool compress)
1147
{
1148
    int ret, i;
1149
    int fd = 0;
1150
    VMDK4Header header;
1151
    uint32_t tmp, magic, grains, gd_size, gt_size, gt_count;
1152

    
1153
    fd = open(
1154
        filename,
1155
        O_WRONLY | O_CREAT | O_TRUNC | O_BINARY | O_LARGEFILE,
1156
        0644);
1157
    if (fd < 0) {
1158
        return -errno;
1159
    }
1160
    if (flat) {
1161
        ret = ftruncate(fd, filesize);
1162
        if (ret < 0) {
1163
            ret = -errno;
1164
        }
1165
        goto exit;
1166
    }
1167
    magic = cpu_to_be32(VMDK4_MAGIC);
1168
    memset(&header, 0, sizeof(header));
1169
    header.version = 1;
1170
    header.flags =
1171
        3 | (compress ? VMDK4_FLAG_COMPRESS | VMDK4_FLAG_MARKER : 0);
1172
    header.compressAlgorithm = compress ? VMDK4_COMPRESSION_DEFLATE : 0;
1173
    header.capacity = filesize / 512;
1174
    header.granularity = 128;
1175
    header.num_gtes_per_gte = 512;
1176

    
1177
    grains = (filesize / 512 + header.granularity - 1) / header.granularity;
1178
    gt_size = ((header.num_gtes_per_gte * sizeof(uint32_t)) + 511) >> 9;
1179
    gt_count =
1180
        (grains + header.num_gtes_per_gte - 1) / header.num_gtes_per_gte;
1181
    gd_size = (gt_count * sizeof(uint32_t) + 511) >> 9;
1182

    
1183
    header.desc_offset = 1;
1184
    header.desc_size = 20;
1185
    header.rgd_offset = header.desc_offset + header.desc_size;
1186
    header.gd_offset = header.rgd_offset + gd_size + (gt_size * gt_count);
1187
    header.grain_offset =
1188
       ((header.gd_offset + gd_size + (gt_size * gt_count) +
1189
         header.granularity - 1) / header.granularity) *
1190
        header.granularity;
1191
    /* swap endianness for all header fields */
1192
    header.version = cpu_to_le32(header.version);
1193
    header.flags = cpu_to_le32(header.flags);
1194
    header.capacity = cpu_to_le64(header.capacity);
1195
    header.granularity = cpu_to_le64(header.granularity);
1196
    header.num_gtes_per_gte = cpu_to_le32(header.num_gtes_per_gte);
1197
    header.desc_offset = cpu_to_le64(header.desc_offset);
1198
    header.desc_size = cpu_to_le64(header.desc_size);
1199
    header.rgd_offset = cpu_to_le64(header.rgd_offset);
1200
    header.gd_offset = cpu_to_le64(header.gd_offset);
1201
    header.grain_offset = cpu_to_le64(header.grain_offset);
1202
    header.compressAlgorithm = cpu_to_le16(header.compressAlgorithm);
1203

    
1204
    header.check_bytes[0] = 0xa;
1205
    header.check_bytes[1] = 0x20;
1206
    header.check_bytes[2] = 0xd;
1207
    header.check_bytes[3] = 0xa;
1208

    
1209
    /* write all the data */
1210
    ret = qemu_write_full(fd, &magic, sizeof(magic));
1211
    if (ret != sizeof(magic)) {
1212
        ret = -errno;
1213
        goto exit;
1214
    }
1215
    ret = qemu_write_full(fd, &header, sizeof(header));
1216
    if (ret != sizeof(header)) {
1217
        ret = -errno;
1218
        goto exit;
1219
    }
1220

    
1221
    ret = ftruncate(fd, le64_to_cpu(header.grain_offset) << 9);
1222
    if (ret < 0) {
1223
        ret = -errno;
1224
        goto exit;
1225
    }
1226

    
1227
    /* write grain directory */
1228
    lseek(fd, le64_to_cpu(header.rgd_offset) << 9, SEEK_SET);
1229
    for (i = 0, tmp = le64_to_cpu(header.rgd_offset) + gd_size;
1230
         i < gt_count; i++, tmp += gt_size) {
1231
        ret = qemu_write_full(fd, &tmp, sizeof(tmp));
1232
        if (ret != sizeof(tmp)) {
1233
            ret = -errno;
1234
            goto exit;
1235
        }
1236
    }
1237

    
1238
    /* write backup grain directory */
1239
    lseek(fd, le64_to_cpu(header.gd_offset) << 9, SEEK_SET);
1240
    for (i = 0, tmp = le64_to_cpu(header.gd_offset) + gd_size;
1241
         i < gt_count; i++, tmp += gt_size) {
1242
        ret = qemu_write_full(fd, &tmp, sizeof(tmp));
1243
        if (ret != sizeof(tmp)) {
1244
            ret = -errno;
1245
            goto exit;
1246
        }
1247
    }
1248

    
1249
    ret = 0;
1250
 exit:
1251
    close(fd);
1252
    return ret;
1253
}
1254

    
1255
static int filename_decompose(const char *filename, char *path, char *prefix,
1256
        char *postfix, size_t buf_len)
1257
{
1258
    const char *p, *q;
1259

    
1260
    if (filename == NULL || !strlen(filename)) {
1261
        fprintf(stderr, "Vmdk: no filename provided.\n");
1262
        return -1;
1263
    }
1264
    p = strrchr(filename, '/');
1265
    if (p == NULL) {
1266
        p = strrchr(filename, '\\');
1267
    }
1268
    if (p == NULL) {
1269
        p = strrchr(filename, ':');
1270
    }
1271
    if (p != NULL) {
1272
        p++;
1273
        if (p - filename >= buf_len) {
1274
            return -1;
1275
        }
1276
        pstrcpy(path, p - filename + 1, filename);
1277
    } else {
1278
        p = filename;
1279
        path[0] = '\0';
1280
    }
1281
    q = strrchr(p, '.');
1282
    if (q == NULL) {
1283
        pstrcpy(prefix, buf_len, p);
1284
        postfix[0] = '\0';
1285
    } else {
1286
        if (q - p >= buf_len) {
1287
            return -1;
1288
        }
1289
        pstrcpy(prefix, q - p + 1, p);
1290
        pstrcpy(postfix, buf_len, q);
1291
    }
1292
    return 0;
1293
}
1294

    
1295
static int relative_path(char *dest, int dest_size,
1296
        const char *base, const char *target)
1297
{
1298
    int i = 0;
1299
    int n = 0;
1300
    const char *p, *q;
1301
#ifdef _WIN32
1302
    const char *sep = "\\";
1303
#else
1304
    const char *sep = "/";
1305
#endif
1306

    
1307
    if (!(dest && base && target)) {
1308
        return -1;
1309
    }
1310
    if (path_is_absolute(target)) {
1311
        dest[dest_size - 1] = '\0';
1312
        strncpy(dest, target, dest_size - 1);
1313
        return 0;
1314
    }
1315
    while (base[i] == target[i]) {
1316
        i++;
1317
    }
1318
    p = &base[i];
1319
    q = &target[i];
1320
    while (*p) {
1321
        if (*p == *sep) {
1322
            n++;
1323
        }
1324
        p++;
1325
    }
1326
    dest[0] = '\0';
1327
    for (; n; n--) {
1328
        pstrcat(dest, dest_size, "..");
1329
        pstrcat(dest, dest_size, sep);
1330
    }
1331
    pstrcat(dest, dest_size, q);
1332
    return 0;
1333
}
1334

    
1335
static int vmdk_create(const char *filename, QEMUOptionParameter *options)
1336
{
1337
    int fd, idx = 0;
1338
    char desc[BUF_SIZE];
1339
    int64_t total_size = 0, filesize;
1340
    const char *backing_file = NULL;
1341
    const char *fmt = NULL;
1342
    int flags = 0;
1343
    int ret = 0;
1344
    bool flat, split, compress;
1345
    char ext_desc_lines[BUF_SIZE] = "";
1346
    char path[PATH_MAX], prefix[PATH_MAX], postfix[PATH_MAX];
1347
    const int64_t split_size = 0x80000000;  /* VMDK has constant split size */
1348
    const char *desc_extent_line;
1349
    char parent_desc_line[BUF_SIZE] = "";
1350
    uint32_t parent_cid = 0xffffffff;
1351
    const char desc_template[] =
1352
        "# Disk DescriptorFile\n"
1353
        "version=1\n"
1354
        "CID=%x\n"
1355
        "parentCID=%x\n"
1356
        "createType=\"%s\"\n"
1357
        "%s"
1358
        "\n"
1359
        "# Extent description\n"
1360
        "%s"
1361
        "\n"
1362
        "# The Disk Data Base\n"
1363
        "#DDB\n"
1364
        "\n"
1365
        "ddb.virtualHWVersion = \"%d\"\n"
1366
        "ddb.geometry.cylinders = \"%" PRId64 "\"\n"
1367
        "ddb.geometry.heads = \"16\"\n"
1368
        "ddb.geometry.sectors = \"63\"\n"
1369
        "ddb.adapterType = \"ide\"\n";
1370

    
1371
    if (filename_decompose(filename, path, prefix, postfix, PATH_MAX)) {
1372
        return -EINVAL;
1373
    }
1374
    /* Read out options */
1375
    while (options && options->name) {
1376
        if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
1377
            total_size = options->value.n;
1378
        } else if (!strcmp(options->name, BLOCK_OPT_BACKING_FILE)) {
1379
            backing_file = options->value.s;
1380
        } else if (!strcmp(options->name, BLOCK_OPT_COMPAT6)) {
1381
            flags |= options->value.n ? BLOCK_FLAG_COMPAT6 : 0;
1382
        } else if (!strcmp(options->name, BLOCK_OPT_SUBFMT)) {
1383
            fmt = options->value.s;
1384
        }
1385
        options++;
1386
    }
1387
    if (!fmt) {
1388
        /* Default format to monolithicSparse */
1389
        fmt = "monolithicSparse";
1390
    } else if (strcmp(fmt, "monolithicFlat") &&
1391
               strcmp(fmt, "monolithicSparse") &&
1392
               strcmp(fmt, "twoGbMaxExtentSparse") &&
1393
               strcmp(fmt, "twoGbMaxExtentFlat") &&
1394
               strcmp(fmt, "streamOptimized")) {
1395
        fprintf(stderr, "VMDK: Unknown subformat: %s\n", fmt);
1396
        return -EINVAL;
1397
    }
1398
    split = !(strcmp(fmt, "twoGbMaxExtentFlat") &&
1399
              strcmp(fmt, "twoGbMaxExtentSparse"));
1400
    flat = !(strcmp(fmt, "monolithicFlat") &&
1401
             strcmp(fmt, "twoGbMaxExtentFlat"));
1402
    compress = !strcmp(fmt, "streamOptimized");
1403
    if (flat) {
1404
        desc_extent_line = "RW %lld FLAT \"%s\" 0\n";
1405
    } else {
1406
        desc_extent_line = "RW %lld SPARSE \"%s\"\n";
1407
    }
1408
    if (flat && backing_file) {
1409
        /* not supporting backing file for flat image */
1410
        return -ENOTSUP;
1411
    }
1412
    if (backing_file) {
1413
        char parent_filename[PATH_MAX];
1414
        BlockDriverState *bs = bdrv_new("");
1415
        ret = bdrv_open(bs, backing_file, 0, NULL);
1416
        if (ret != 0) {
1417
            bdrv_delete(bs);
1418
            return ret;
1419
        }
1420
        if (strcmp(bs->drv->format_name, "vmdk")) {
1421
            bdrv_delete(bs);
1422
            return -EINVAL;
1423
        }
1424
        parent_cid = vmdk_read_cid(bs, 0);
1425
        bdrv_delete(bs);
1426
        relative_path(parent_filename, sizeof(parent_filename),
1427
                      filename, backing_file);
1428
        snprintf(parent_desc_line, sizeof(parent_desc_line),
1429
                "parentFileNameHint=\"%s\"", parent_filename);
1430
    }
1431

    
1432
    /* Create extents */
1433
    filesize = total_size;
1434
    while (filesize > 0) {
1435
        char desc_line[BUF_SIZE];
1436
        char ext_filename[PATH_MAX];
1437
        char desc_filename[PATH_MAX];
1438
        int64_t size = filesize;
1439

    
1440
        if (split && size > split_size) {
1441
            size = split_size;
1442
        }
1443
        if (split) {
1444
            snprintf(desc_filename, sizeof(desc_filename), "%s-%c%03d%s",
1445
                    prefix, flat ? 'f' : 's', ++idx, postfix);
1446
        } else if (flat) {
1447
            snprintf(desc_filename, sizeof(desc_filename), "%s-flat%s",
1448
                    prefix, postfix);
1449
        } else {
1450
            snprintf(desc_filename, sizeof(desc_filename), "%s%s",
1451
                    prefix, postfix);
1452
        }
1453
        snprintf(ext_filename, sizeof(ext_filename), "%s%s",
1454
                path, desc_filename);
1455

    
1456
        if (vmdk_create_extent(ext_filename, size, flat, compress)) {
1457
            return -EINVAL;
1458
        }
1459
        filesize -= size;
1460

    
1461
        /* Format description line */
1462
        snprintf(desc_line, sizeof(desc_line),
1463
                    desc_extent_line, size / 512, desc_filename);
1464
        pstrcat(ext_desc_lines, sizeof(ext_desc_lines), desc_line);
1465
    }
1466
    /* generate descriptor file */
1467
    snprintf(desc, sizeof(desc), desc_template,
1468
            (unsigned int)time(NULL),
1469
            parent_cid,
1470
            fmt,
1471
            parent_desc_line,
1472
            ext_desc_lines,
1473
            (flags & BLOCK_FLAG_COMPAT6 ? 6 : 4),
1474
            total_size / (int64_t)(63 * 16 * 512));
1475
    if (split || flat) {
1476
        fd = open(
1477
                filename,
1478
                O_WRONLY | O_CREAT | O_TRUNC | O_BINARY | O_LARGEFILE,
1479
                0644);
1480
    } else {
1481
        fd = open(
1482
                filename,
1483
                O_WRONLY | O_BINARY | O_LARGEFILE,
1484
                0644);
1485
    }
1486
    if (fd < 0) {
1487
        return -errno;
1488
    }
1489
    /* the descriptor offset = 0x200 */
1490
    if (!split && !flat && 0x200 != lseek(fd, 0x200, SEEK_SET)) {
1491
        ret = -errno;
1492
        goto exit;
1493
    }
1494
    ret = qemu_write_full(fd, desc, strlen(desc));
1495
    if (ret != strlen(desc)) {
1496
        ret = -errno;
1497
        goto exit;
1498
    }
1499
    ret = 0;
1500
exit:
1501
    close(fd);
1502
    return ret;
1503
}
1504

    
1505
static void vmdk_close(BlockDriverState *bs)
1506
{
1507
    vmdk_free_extents(bs);
1508
}
1509

    
1510
static coroutine_fn int vmdk_co_flush(BlockDriverState *bs)
1511
{
1512
    int i, ret, err;
1513
    BDRVVmdkState *s = bs->opaque;
1514

    
1515
    ret = bdrv_co_flush(bs->file);
1516
    for (i = 0; i < s->num_extents; i++) {
1517
        err = bdrv_co_flush(s->extents[i].file);
1518
        if (err < 0) {
1519
            ret = err;
1520
        }
1521
    }
1522
    return ret;
1523
}
1524

    
1525
static int64_t vmdk_get_allocated_file_size(BlockDriverState *bs)
1526
{
1527
    int i;
1528
    int64_t ret = 0;
1529
    int64_t r;
1530
    BDRVVmdkState *s = bs->opaque;
1531

    
1532
    ret = bdrv_get_allocated_file_size(bs->file);
1533
    if (ret < 0) {
1534
        return ret;
1535
    }
1536
    for (i = 0; i < s->num_extents; i++) {
1537
        if (s->extents[i].file == bs->file) {
1538
            continue;
1539
        }
1540
        r = bdrv_get_allocated_file_size(s->extents[i].file);
1541
        if (r < 0) {
1542
            return r;
1543
        }
1544
        ret += r;
1545
    }
1546
    return ret;
1547
}
1548

    
1549
static QEMUOptionParameter vmdk_create_options[] = {
1550
    {
1551
        .name = BLOCK_OPT_SIZE,
1552
        .type = OPT_SIZE,
1553
        .help = "Virtual disk size"
1554
    },
1555
    {
1556
        .name = BLOCK_OPT_BACKING_FILE,
1557
        .type = OPT_STRING,
1558
        .help = "File name of a base image"
1559
    },
1560
    {
1561
        .name = BLOCK_OPT_COMPAT6,
1562
        .type = OPT_FLAG,
1563
        .help = "VMDK version 6 image"
1564
    },
1565
    {
1566
        .name = BLOCK_OPT_SUBFMT,
1567
        .type = OPT_STRING,
1568
        .help =
1569
            "VMDK flat extent format, can be one of "
1570
            "{monolithicSparse (default) | monolithicFlat | twoGbMaxExtentSparse | twoGbMaxExtentFlat | streamOptimized} "
1571
    },
1572
    { NULL }
1573
};
1574

    
1575
static BlockDriver bdrv_vmdk = {
1576
    .format_name    = "vmdk",
1577
    .instance_size  = sizeof(BDRVVmdkState),
1578
    .bdrv_probe     = vmdk_probe,
1579
    .bdrv_open      = vmdk_open,
1580
    .bdrv_read      = vmdk_co_read,
1581
    .bdrv_write     = vmdk_co_write,
1582
    .bdrv_close     = vmdk_close,
1583
    .bdrv_create    = vmdk_create,
1584
    .bdrv_co_flush_to_disk  = vmdk_co_flush,
1585
    .bdrv_is_allocated      = vmdk_is_allocated,
1586
    .bdrv_get_allocated_file_size  = vmdk_get_allocated_file_size,
1587

    
1588
    .create_options = vmdk_create_options,
1589
};
1590

    
1591
static void bdrv_vmdk_init(void)
1592
{
1593
    bdrv_register(&bdrv_vmdk);
1594
}
1595

    
1596
block_init(bdrv_vmdk_init);