Revision b64ec4e4 block.c

b/block.c
328 328
    return NULL;
329 329
}
330 330

  
331
static int bdrv_is_whitelisted(BlockDriver *drv)
331
static int bdrv_is_whitelisted(BlockDriver *drv, bool read_only)
332 332
{
333
    static const char *whitelist[] = {
334
        CONFIG_BDRV_WHITELIST
333
    static const char *whitelist_rw[] = {
334
        CONFIG_BDRV_RW_WHITELIST
335
    };
336
    static const char *whitelist_ro[] = {
337
        CONFIG_BDRV_RO_WHITELIST
335 338
    };
336 339
    const char **p;
337 340

  
338
    if (!whitelist[0])
341
    if (!whitelist_rw[0] && !whitelist_ro[0]) {
339 342
        return 1;               /* no whitelist, anything goes */
343
    }
340 344

  
341
    for (p = whitelist; *p; p++) {
345
    for (p = whitelist_rw; *p; p++) {
342 346
        if (!strcmp(drv->format_name, *p)) {
343 347
            return 1;
344 348
        }
345 349
    }
350
    if (read_only) {
351
        for (p = whitelist_ro; *p; p++) {
352
            if (!strcmp(drv->format_name, *p)) {
353
                return 1;
354
            }
355
        }
356
    }
346 357
    return 0;
347 358
}
348 359

  
349
BlockDriver *bdrv_find_whitelisted_format(const char *format_name)
360
BlockDriver *bdrv_find_whitelisted_format(const char *format_name,
361
                                          bool read_only)
350 362
{
351 363
    BlockDriver *drv = bdrv_find_format(format_name);
352
    return drv && bdrv_is_whitelisted(drv) ? drv : NULL;
364
    return drv && bdrv_is_whitelisted(drv, read_only) ? drv : NULL;
353 365
}
354 366

  
355 367
typedef struct CreateCo {
......
684 696

  
685 697
    trace_bdrv_open_common(bs, filename ?: "", flags, drv->format_name);
686 698

  
687
    if (use_bdrv_whitelist && !bdrv_is_whitelisted(drv)) {
688
        return -ENOTSUP;
689
    }
690

  
691 699
    /* bdrv_open() with directly using a protocol as drv. This layer is already
692 700
     * opened, so assign it to bs (while file becomes a closed BlockDriverState)
693 701
     * and return immediately. */
......
698 706

  
699 707
    bs->open_flags = flags;
700 708
    bs->buffer_alignment = 512;
709
    open_flags = bdrv_open_flags(bs, flags);
710
    bs->read_only = !(open_flags & BDRV_O_RDWR);
711

  
712
    if (use_bdrv_whitelist && !bdrv_is_whitelisted(drv, bs->read_only)) {
713
        return -ENOTSUP;
714
    }
701 715

  
702 716
    assert(bs->copy_on_read == 0); /* bdrv_new() and bdrv_close() make it so */
703
    if ((flags & BDRV_O_RDWR) && (flags & BDRV_O_COPY_ON_READ)) {
717
    if (!bs->read_only && (flags & BDRV_O_COPY_ON_READ)) {
704 718
        bdrv_enable_copy_on_read(bs);
705 719
    }
706 720

  
......
714 728
    bs->opaque = g_malloc0(drv->instance_size);
715 729

  
716 730
    bs->enable_write_cache = !!(flags & BDRV_O_CACHE_WB);
717
    open_flags = bdrv_open_flags(bs, flags);
718

  
719
    bs->read_only = !(open_flags & BDRV_O_RDWR);
720 731

  
721 732
    /* Open the image, either directly or using a protocol */
722 733
    if (drv->bdrv_file_open) {
......
801 812
    /* Find the right block driver */
802 813
    drvname = qdict_get_try_str(options, "driver");
803 814
    if (drvname) {
804
        drv = bdrv_find_whitelisted_format(drvname);
815
        drv = bdrv_find_whitelisted_format(drvname, !(flags & BDRV_O_RDWR));
805 816
        qdict_del(options, "driver");
806 817
    } else if (filename) {
807 818
        drv = bdrv_find_protocol(filename);

Also available in: Unified diff