mirror of https://gitee.com/openkylin/qemu.git
block/nbd: split nbd_handle_updated_info out of nbd_client_handshake()
To be reused in the following patch. Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@virtuozzo.com> Reviewed-by: Roman Kagan <rvkagan@yandex-team.ru> Reviewed-by: Eric Blake <eblake@redhat.com> Message-Id: <20210610100802.5888-23-vsementsov@virtuozzo.com> Signed-off-by: Eric Blake <eblake@redhat.com>
This commit is contained in:
parent
f58b2dfe3e
commit
e9ba7788b0
100
block/nbd.c
100
block/nbd.c
|
@ -314,6 +314,51 @@ static bool nbd_client_connecting_wait(BDRVNBDState *s)
|
|||
return qatomic_load_acquire(&s->state) == NBD_CLIENT_CONNECTING_WAIT;
|
||||
}
|
||||
|
||||
/*
|
||||
* Update @bs with information learned during a completed negotiation process.
|
||||
* Return failure if the server's advertised options are incompatible with the
|
||||
* client's needs.
|
||||
*/
|
||||
static int nbd_handle_updated_info(BlockDriverState *bs, Error **errp)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
int ret;
|
||||
|
||||
if (s->x_dirty_bitmap) {
|
||||
if (!s->info.base_allocation) {
|
||||
error_setg(errp, "requested x-dirty-bitmap %s not found",
|
||||
s->x_dirty_bitmap);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (strcmp(s->x_dirty_bitmap, "qemu:allocation-depth") == 0) {
|
||||
s->alloc_depth = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (s->info.flags & NBD_FLAG_READ_ONLY) {
|
||||
ret = bdrv_apply_auto_read_only(bs, "NBD export is read-only", errp);
|
||||
if (ret < 0) {
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
if (s->info.flags & NBD_FLAG_SEND_FUA) {
|
||||
bs->supported_write_flags = BDRV_REQ_FUA;
|
||||
bs->supported_zero_flags |= BDRV_REQ_FUA;
|
||||
}
|
||||
|
||||
if (s->info.flags & NBD_FLAG_SEND_WRITE_ZEROES) {
|
||||
bs->supported_zero_flags |= BDRV_REQ_MAY_UNMAP;
|
||||
if (s->info.flags & NBD_FLAG_SEND_FAST_ZERO) {
|
||||
bs->supported_zero_flags |= BDRV_REQ_NO_FALLBACK;
|
||||
}
|
||||
}
|
||||
|
||||
trace_nbd_client_handshake_success(s->export);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static coroutine_fn void nbd_reconnect_attempt(BDRVNBDState *s)
|
||||
{
|
||||
int ret;
|
||||
|
@ -1575,49 +1620,13 @@ static int nbd_client_handshake(BlockDriverState *bs, Error **errp)
|
|||
s->sioc = NULL;
|
||||
return ret;
|
||||
}
|
||||
if (s->x_dirty_bitmap) {
|
||||
if (!s->info.base_allocation) {
|
||||
error_setg(errp, "requested x-dirty-bitmap %s not found",
|
||||
s->x_dirty_bitmap);
|
||||
ret = -EINVAL;
|
||||
goto fail;
|
||||
}
|
||||
if (strcmp(s->x_dirty_bitmap, "qemu:allocation-depth") == 0) {
|
||||
s->alloc_depth = true;
|
||||
}
|
||||
}
|
||||
if (s->info.flags & NBD_FLAG_READ_ONLY) {
|
||||
ret = bdrv_apply_auto_read_only(bs, "NBD export is read-only", errp);
|
||||
if (ret < 0) {
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
if (s->info.flags & NBD_FLAG_SEND_FUA) {
|
||||
bs->supported_write_flags = BDRV_REQ_FUA;
|
||||
bs->supported_zero_flags |= BDRV_REQ_FUA;
|
||||
}
|
||||
if (s->info.flags & NBD_FLAG_SEND_WRITE_ZEROES) {
|
||||
bs->supported_zero_flags |= BDRV_REQ_MAY_UNMAP;
|
||||
if (s->info.flags & NBD_FLAG_SEND_FAST_ZERO) {
|
||||
bs->supported_zero_flags |= BDRV_REQ_NO_FALLBACK;
|
||||
}
|
||||
}
|
||||
|
||||
if (!s->ioc) {
|
||||
s->ioc = QIO_CHANNEL(s->sioc);
|
||||
object_ref(OBJECT(s->ioc));
|
||||
}
|
||||
|
||||
trace_nbd_client_handshake_success(s->export);
|
||||
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
/*
|
||||
* We have connected, but must fail for other reasons.
|
||||
* Send NBD_CMD_DISC as a courtesy to the server.
|
||||
*/
|
||||
{
|
||||
ret = nbd_handle_updated_info(bs, errp);
|
||||
if (ret < 0) {
|
||||
/*
|
||||
* We have connected, but must fail for other reasons.
|
||||
* Send NBD_CMD_DISC as a courtesy to the server.
|
||||
*/
|
||||
NBDRequest request = { .type = NBD_CMD_DISC };
|
||||
|
||||
nbd_send_request(s->ioc ?: QIO_CHANNEL(s->sioc), &request);
|
||||
|
@ -1631,6 +1640,13 @@ static int nbd_client_handshake(BlockDriverState *bs, Error **errp)
|
|||
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (!s->ioc) {
|
||||
s->ioc = QIO_CHANNEL(s->sioc);
|
||||
object_ref(OBJECT(s->ioc));
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
Loading…
Reference in New Issue