X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=nbd.c;h=2606403a41facd02d5b50d14dcd407b3aa62bd1c;hb=b174de51ae397549f58b1b76efa9026b213a1efd;hp=0698a023add158d36c9a0935848700790b05217b;hpb=34daffa04886444dafd4a6951167225e824003d0;p=qemu.git diff --git a/nbd.c b/nbd.c index 0698a023a..2606403a4 100644 --- a/nbd.c +++ b/nbd.c @@ -98,7 +98,6 @@ struct NBDExport { off_t size; uint32_t nbdflags; QTAILQ_HEAD(, NBDClient) clients; - QSIMPLEQ_HEAD(, NBDRequest) requests; QTAILQ_ENTRY(NBDExport) next; }; @@ -199,22 +198,15 @@ static void combine_addr(char *buf, size_t len, const char* address, } } -int tcp_socket_outgoing(const char *address, uint16_t port) -{ - char address_and_port[128]; - combine_addr(address_and_port, 128, address, port); - return tcp_socket_outgoing_spec(address_and_port); -} - -int tcp_socket_outgoing_spec(const char *address_and_port) +int tcp_socket_outgoing_opts(QemuOpts *opts) { Error *local_err = NULL; - int fd = inet_connect(address_and_port, &local_err); - + int fd = inet_connect_opts(opts, &local_err, NULL, NULL); if (local_err != NULL) { qerror_report_err(local_err); error_free(local_err); } + return fd; } @@ -393,7 +385,7 @@ static int nbd_send_negotiate(NBDClient *client) [28 .. 151] reserved (0) */ - socket_set_block(csock); + qemu_set_block(csock); rc = -EINVAL; TRACE("Beginning negotiation."); @@ -436,7 +428,7 @@ static int nbd_send_negotiate(NBDClient *client) TRACE("Negotiation succeeded."); rc = 0; fail: - socket_set_nonblock(csock); + qemu_set_nonblock(csock); return rc; } @@ -450,7 +442,7 @@ int nbd_receive_negotiate(int csock, const char *name, uint32_t *flags, TRACE("Receiving negotiation."); - socket_set_block(csock); + qemu_set_block(csock); rc = -EINVAL; if (read_sync(csock, buf, 8) != 8) { @@ -565,7 +557,7 @@ int nbd_receive_negotiate(int csock, const char *name, uint32_t *flags, rc = 0; fail: - socket_set_nonblock(csock); + qemu_set_nonblock(csock); return rc; } @@ -852,18 +844,11 @@ void nbd_client_close(NBDClient *client) static NBDRequest *nbd_request_get(NBDClient *client) { NBDRequest *req; - NBDExport *exp = client->exp; assert(client->nb_requests <= MAX_NBD_REQUESTS - 1); client->nb_requests++; - if (QSIMPLEQ_EMPTY(&exp->requests)) { - req = g_malloc0(sizeof(NBDRequest)); - req->data = qemu_blockalign(exp->bs, NBD_BUFFER_SIZE); - } else { - req = QSIMPLEQ_FIRST(&exp->requests); - QSIMPLEQ_REMOVE_HEAD(&exp->requests, entry); - } + req = g_slice_new0(NBDRequest); nbd_client_get(client); req->client = client; return req; @@ -872,7 +857,12 @@ static NBDRequest *nbd_request_get(NBDClient *client) static void nbd_request_put(NBDRequest *req) { NBDClient *client = req->client; - QSIMPLEQ_INSERT_HEAD(&client->exp->requests, req, entry); + + if (req->data) { + qemu_vfree(req->data); + } + g_slice_free(NBDRequest, req); + if (client->nb_requests-- == MAX_NBD_REQUESTS) { qemu_notify_event(); } @@ -884,7 +874,6 @@ NBDExport *nbd_export_new(BlockDriverState *bs, off_t dev_offset, void (*close)(NBDExport *)) { NBDExport *exp = g_malloc0(sizeof(NBDExport)); - QSIMPLEQ_INIT(&exp->requests); exp->refcount = 1; QTAILQ_INIT(&exp->clients); exp->bs = bs; @@ -960,13 +949,6 @@ void nbd_export_put(NBDExport *exp) exp->close(exp); } - while (!QSIMPLEQ_EMPTY(&exp->requests)) { - NBDRequest *first = QSIMPLEQ_FIRST(&exp->requests); - QSIMPLEQ_REMOVE_HEAD(&exp->requests, entry); - qemu_vfree(first->data); - g_free(first); - } - g_free(exp); } } @@ -1025,6 +1007,7 @@ static ssize_t nbd_co_receive_request(NBDRequest *req, struct nbd_request *reque { NBDClient *client = req->client; int csock = client->sock; + uint32_t command; ssize_t rc; client->recv_coroutine = qemu_coroutine_self(); @@ -1036,9 +1019,9 @@ static ssize_t nbd_co_receive_request(NBDRequest *req, struct nbd_request *reque goto out; } - if (request->len > NBD_BUFFER_SIZE) { + if (request->len > NBD_MAX_BUFFER_SIZE) { LOG("len (%u) is larger than max len (%u)", - request->len, NBD_BUFFER_SIZE); + request->len, NBD_MAX_BUFFER_SIZE); rc = -EINVAL; goto out; } @@ -1052,7 +1035,11 @@ static ssize_t nbd_co_receive_request(NBDRequest *req, struct nbd_request *reque TRACE("Decoding type"); - if ((request->type & NBD_CMD_MASK_COMMAND) == NBD_CMD_WRITE) { + command = request->type & NBD_CMD_MASK_COMMAND; + if (command == NBD_CMD_READ || command == NBD_CMD_WRITE) { + req->data = qemu_blockalign(client->exp->bs, request->len); + } + if (command == NBD_CMD_WRITE) { TRACE("Reading %u byte(s)", request->len); if (qemu_co_recv(csock, req->data, request->len) != request->len) {