Merge branch 'for-anthony' of git://repo.or.cz/qemu/kevin
* 'for-anthony' of git://repo.or.cz/qemu/kevin: Fix -snapshot deleting images on disk change block: Use error codes from lower levels for error message block: default to 0 minimal / optiomal I/O size move 'unsafe' to end of caching modes in help virtio-blk: Create exit function to unregister savevm block migration: propagate return value when bdrv_write() returns < 0 ide/atapi: add support for GET EVENT STATUS NOTIFICATION
This commit is contained in:
commit
cdc6f54200
@ -586,6 +586,7 @@ static int block_load(QEMUFile *f, void *opaque, int version_id)
|
||||
addr >>= BDRV_SECTOR_BITS;
|
||||
|
||||
if (flags & BLK_MIG_FLAG_DEVICE_BLOCK) {
|
||||
int ret;
|
||||
/* get device name */
|
||||
len = qemu_get_byte(f);
|
||||
qemu_get_buffer(f, (uint8_t *)device_name, len);
|
||||
@ -601,9 +602,12 @@ static int block_load(QEMUFile *f, void *opaque, int version_id)
|
||||
buf = qemu_malloc(BLOCK_SIZE);
|
||||
|
||||
qemu_get_buffer(f, buf, BLOCK_SIZE);
|
||||
bdrv_write(bs, addr, buf, BDRV_SECTORS_PER_DIRTY_CHUNK);
|
||||
ret = bdrv_write(bs, addr, buf, BDRV_SECTORS_PER_DIRTY_CHUNK);
|
||||
|
||||
qemu_free(buf);
|
||||
if (ret < 0) {
|
||||
return ret;
|
||||
}
|
||||
} else if (flags & BLK_MIG_FLAG_PROGRESS) {
|
||||
if (!banner_printed) {
|
||||
printf("Receiving block device images\n");
|
||||
|
32
block.c
32
block.c
@ -330,7 +330,7 @@ BlockDriver *bdrv_find_protocol(const char *filename)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static BlockDriver *find_image_format(const char *filename)
|
||||
static int find_image_format(const char *filename, BlockDriver **pdrv)
|
||||
{
|
||||
int ret, score, score_max;
|
||||
BlockDriver *drv1, *drv;
|
||||
@ -338,19 +338,27 @@ static BlockDriver *find_image_format(const char *filename)
|
||||
BlockDriverState *bs;
|
||||
|
||||
ret = bdrv_file_open(&bs, filename, 0);
|
||||
if (ret < 0)
|
||||
return NULL;
|
||||
if (ret < 0) {
|
||||
*pdrv = NULL;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Return the raw BlockDriver * to scsi-generic devices or empty drives */
|
||||
if (bs->sg || !bdrv_is_inserted(bs)) {
|
||||
bdrv_delete(bs);
|
||||
return bdrv_find_format("raw");
|
||||
drv = bdrv_find_format("raw");
|
||||
if (!drv) {
|
||||
ret = -ENOENT;
|
||||
}
|
||||
*pdrv = drv;
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = bdrv_pread(bs, 0, buf, sizeof(buf));
|
||||
bdrv_delete(bs);
|
||||
if (ret < 0) {
|
||||
return NULL;
|
||||
*pdrv = NULL;
|
||||
return ret;
|
||||
}
|
||||
|
||||
score_max = 0;
|
||||
@ -364,7 +372,11 @@ static BlockDriver *find_image_format(const char *filename)
|
||||
}
|
||||
}
|
||||
}
|
||||
return drv;
|
||||
if (!drv) {
|
||||
ret = -ENOENT;
|
||||
}
|
||||
*pdrv = drv;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -571,12 +583,11 @@ int bdrv_open(BlockDriverState *bs, const char *filename, int flags,
|
||||
|
||||
/* Find the right image format driver */
|
||||
if (!drv) {
|
||||
drv = find_image_format(filename);
|
||||
ret = find_image_format(filename, &drv);
|
||||
probed = 1;
|
||||
}
|
||||
|
||||
if (!drv) {
|
||||
ret = -ENOENT;
|
||||
goto unlink_and_fail;
|
||||
}
|
||||
|
||||
@ -1800,6 +1811,11 @@ int bdrv_can_snapshot(BlockDriverState *bs)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int bdrv_is_snapshot(BlockDriverState *bs)
|
||||
{
|
||||
return !!(bs->open_flags & BDRV_O_SNAPSHOT);
|
||||
}
|
||||
|
||||
BlockDriverState *bdrv_snapshots(void)
|
||||
{
|
||||
BlockDriverState *bs;
|
||||
|
1
block.h
1
block.h
@ -202,6 +202,7 @@ const char *bdrv_get_encrypted_filename(BlockDriverState *bs);
|
||||
void bdrv_get_backing_filename(BlockDriverState *bs,
|
||||
char *filename, int filename_size);
|
||||
int bdrv_can_snapshot(BlockDriverState *bs);
|
||||
int bdrv_is_snapshot(BlockDriverState *bs);
|
||||
BlockDriverState *bdrv_snapshots(void);
|
||||
int bdrv_snapshot_create(BlockDriverState *bs,
|
||||
QEMUSnapshotInfo *sn_info);
|
||||
|
@ -243,7 +243,7 @@ static inline unsigned int get_physical_block_exp(BlockConf *conf)
|
||||
_conf.logical_block_size, 512), \
|
||||
DEFINE_PROP_UINT16("physical_block_size", _state, \
|
||||
_conf.physical_block_size, 512), \
|
||||
DEFINE_PROP_UINT16("min_io_size", _state, _conf.min_io_size, 512), \
|
||||
DEFINE_PROP_UINT32("opt_io_size", _state, _conf.opt_io_size, 512)
|
||||
DEFINE_PROP_UINT16("min_io_size", _state, _conf.min_io_size, 0), \
|
||||
DEFINE_PROP_UINT32("opt_io_size", _state, _conf.opt_io_size, 0)
|
||||
|
||||
#endif /* BLOCK_INT_H */
|
||||
|
@ -590,6 +590,7 @@ int do_change_block(Monitor *mon, const char *device,
|
||||
return -1;
|
||||
}
|
||||
bdrv_flags = bdrv_is_read_only(bs) ? 0 : BDRV_O_RDWR;
|
||||
bdrv_flags |= bdrv_is_snapshot(bs) ? BDRV_O_SNAPSHOT : 0;
|
||||
if (bdrv_open(bs, filename, bdrv_flags, drv) < 0) {
|
||||
qerror_report(QERR_OPEN_FILE_FAILED, filename);
|
||||
return -1;
|
||||
|
@ -1643,6 +1643,21 @@ static void ide_atapi_cmd(IDEState *s)
|
||||
ide_atapi_cmd_reply(s, len, max_len);
|
||||
break;
|
||||
}
|
||||
case GPCMD_GET_EVENT_STATUS_NOTIFICATION:
|
||||
max_len = ube16_to_cpu(packet + 7);
|
||||
|
||||
if (packet[1] & 0x01) { /* polling */
|
||||
/* We don't support any event class (yet). */
|
||||
cpu_to_ube16(buf, 0x00); /* No event descriptor returned */
|
||||
buf[2] = 0x80; /* No Event Available (NEA) */
|
||||
buf[3] = 0x00; /* Empty supported event classes */
|
||||
ide_atapi_cmd_reply(s, 4, max_len);
|
||||
} else { /* asynchronous mode */
|
||||
/* Only polling is supported, asynchronous mode is not. */
|
||||
ide_atapi_cmd_error(s, SENSE_ILLEGAL_REQUEST,
|
||||
ASC_INV_FIELD_IN_CMD_PACKET);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ide_atapi_cmd_error(s, SENSE_ILLEGAL_REQUEST,
|
||||
ASC_ILLEGAL_OPCODE);
|
||||
|
@ -28,6 +28,7 @@ typedef struct VirtIOBlock
|
||||
BlockConf *conf;
|
||||
unsigned short sector_mask;
|
||||
char sn[BLOCK_SERIAL_STRLEN];
|
||||
DeviceState *qdev;
|
||||
} VirtIOBlock;
|
||||
|
||||
static VirtIOBlock *to_virtio_blk(VirtIODevice *vdev)
|
||||
@ -522,9 +523,16 @@ VirtIODevice *virtio_blk_init(DeviceState *dev, BlockConf *conf)
|
||||
s->vq = virtio_add_queue(&s->vdev, 128, virtio_blk_handle_output);
|
||||
|
||||
qemu_add_vm_change_state_handler(virtio_blk_dma_restart_cb, s);
|
||||
s->qdev = dev;
|
||||
register_savevm(dev, "virtio-blk", virtio_blk_id++, 2,
|
||||
virtio_blk_save, virtio_blk_load, s);
|
||||
bdrv_set_removable(s->bs, 0);
|
||||
|
||||
return &s->vdev;
|
||||
}
|
||||
|
||||
void virtio_blk_exit(VirtIODevice *vdev)
|
||||
{
|
||||
VirtIOBlock *s = to_virtio_blk(vdev);
|
||||
unregister_savevm(s->qdev, "virtio-blk", s);
|
||||
}
|
||||
|
@ -569,6 +569,7 @@ static int virtio_blk_exit_pci(PCIDevice *pci_dev)
|
||||
{
|
||||
VirtIOPCIProxy *proxy = DO_UPCAST(VirtIOPCIProxy, pci_dev, pci_dev);
|
||||
|
||||
virtio_blk_exit(proxy->vdev);
|
||||
blockdev_mark_auto_del(proxy->block.bs);
|
||||
return virtio_exit_pci(pci_dev);
|
||||
}
|
||||
|
@ -194,6 +194,7 @@ VirtIODevice *virtio_9p_init(DeviceState *dev, V9fsConf *conf);
|
||||
|
||||
|
||||
void virtio_net_exit(VirtIODevice *vdev);
|
||||
void virtio_blk_exit(VirtIODevice *vdev);
|
||||
|
||||
#define DEFINE_VIRTIO_COMMON_FEATURES(_state, _field) \
|
||||
DEFINE_PROP_BIT("indirect_desc", _state, _field, \
|
||||
|
@ -118,7 +118,7 @@ ETEXI
|
||||
DEF("drive", HAS_ARG, QEMU_OPTION_drive,
|
||||
"-drive [file=file][,if=type][,bus=n][,unit=m][,media=d][,index=i]\n"
|
||||
" [,cyls=c,heads=h,secs=s[,trans=t]][,snapshot=on|off]\n"
|
||||
" [,cache=writethrough|writeback|unsafe|none][,format=f]\n"
|
||||
" [,cache=writethrough|writeback|none|unsafe][,format=f]\n"
|
||||
" [,serial=s][,addr=A][,id=name][,aio=threads|native]\n"
|
||||
" [,readonly=on|off]\n"
|
||||
" use 'file' as a drive image\n", QEMU_ARCH_ALL)
|
||||
|
Loading…
Reference in New Issue
Block a user