2
0
mirror of https://gitlab.isc.org/isc-projects/bind9 synced 2025-08-31 06:25:31 +00:00

Merge branch 'wpk-get-rid-of-socket-v-functions' into 'master'

Get rid of socket *v functions

See merge request isc-projects/bind9!932
This commit is contained in:
Witold Krecicki
2018-10-31 08:57:08 -04:00
10 changed files with 120 additions and 676 deletions

View File

@@ -1,3 +1,8 @@
5074. [cleanup] Remove vector socket functions - isc_socket_recvv(),
isc_socket_sendtov(), isc_socket_sendtov2(),
isc_socket_sendv() - in order to simplify socket code.
[GL #645]
5073. [bug] Destroy a task first when destroying rpzs and catzs.
[GL #84]

View File

@@ -1534,12 +1534,6 @@ clear_query(dig_query_t *query) {
ISC_LIST_UNLINK(lookup->q, query, link);
if (ISC_LINK_LINKED(query, clink))
ISC_LIST_UNLINK(lookup->connecting, query, clink);
if (ISC_LINK_LINKED(&query->recvbuf, link))
ISC_LIST_DEQUEUE(query->recvlist, &query->recvbuf,
link);
if (ISC_LINK_LINKED(&query->lengthbuf, link))
ISC_LIST_DEQUEUE(query->lengthlist, &query->lengthbuf,
link);
INSIST(query->recvspace != NULL);
if (query->sock != NULL) {
@@ -1548,6 +1542,7 @@ clear_query(dig_query_t *query) {
debug("sockcount=%d", sockcount);
}
isc_mempool_put(commctx, query->recvspace);
isc_mempool_put(commctx, query->tmpsendspace);
isc_buffer_invalidate(&query->recvbuf);
isc_buffer_invalidate(&query->lengthbuf);
if (query->waiting_senddone)
@@ -2488,16 +2483,15 @@ setup_lookup(dig_lookup_t *lookup) {
query->msg_count = 0;
query->byte_count = 0;
query->ixfr_axfr = false;
ISC_LIST_INIT(query->recvlist);
ISC_LIST_INIT(query->lengthlist);
query->sock = NULL;
query->recvspace = isc_mempool_get(commctx);
query->tmpsendspace = isc_mempool_get(commctx);
if (query->recvspace == NULL)
fatal("memory allocation failure");
isc_buffer_init(&query->recvbuf, query->recvspace, COMMSIZE);
isc_buffer_init(&query->lengthbuf, query->lengthspace, 2);
isc_buffer_init(&query->slbuf, query->slspace, 2);
isc_buffer_init(&query->tmpsendbuf, query->tmpsendspace, COMMSIZE);
query->sendbuf = lookup->renderbuf;
ISC_LINK_INIT(query, clink);
@@ -2523,8 +2517,6 @@ setup_lookup(dig_lookup_t *lookup) {
*/
static void
send_done(isc_task_t *_task, isc_event_t *event) {
isc_socketevent_t *sevent = (isc_socketevent_t *)event;
isc_buffer_t *b = NULL;
dig_query_t *query, *next;
dig_lookup_t *l;
@@ -2539,13 +2531,6 @@ send_done(isc_task_t *_task, isc_event_t *event) {
debug("sendcount=%d", sendcount);
INSIST(sendcount >= 0);
for (b = ISC_LIST_HEAD(sevent->bufferlist);
b != NULL;
b = ISC_LIST_HEAD(sevent->bufferlist)) {
ISC_LIST_DEQUEUE(sevent->bufferlist, b, link);
isc_mem_free(mctx, b);
}
query = event->ev_arg;
query->waiting_senddone = false;
l = query->lookup;
@@ -2777,17 +2762,6 @@ send_tcp_connect(dig_query_t *query) {
}
}
static isc_buffer_t *
clone_buffer(isc_buffer_t *source) {
isc_buffer_t *buffer;
buffer = isc_mem_allocate(mctx, sizeof(*buffer));
if (buffer == NULL)
fatal("memory allocation failure in %s:%d",
__FILE__, __LINE__);
*buffer = *source;
return (buffer);
}
/*%
* Send a UDP packet to the remote nameserver, possible starting the
* recv action as well. Also make sure that the timer is running and
@@ -2797,8 +2771,9 @@ static void
send_udp(dig_query_t *query) {
dig_lookup_t *l = NULL;
isc_result_t result;
isc_buffer_t *sendbuf;
dig_query_t *next;
isc_region_t r;
isc_socketevent_t *sevent;
debug("send_udp(%p)", query);
@@ -2859,29 +2834,27 @@ send_udp(dig_query_t *query) {
check_result(result, "isc_socket_bind");
query->recv_made = true;
ISC_LINK_INIT(&query->recvbuf, link);
ISC_LIST_ENQUEUE(query->recvlist, &query->recvbuf,
link);
isc_buffer_availableregion(&query->recvbuf, &r);
debug("recving with lookup=%p, query=%p, sock=%p",
query->lookup, query, query->sock);
result = isc_socket_recvv(query->sock, &query->recvlist, 1,
global_task, recv_done, query);
check_result(result, "isc_socket_recvv");
result = isc_socket_recv(query->sock, &r, 1,
global_task, recv_done, query);
check_result(result, "isc_socket_recv");
recvcount++;
debug("recvcount=%d", recvcount);
}
ISC_LIST_INIT(query->sendlist);
sendbuf = clone_buffer(&query->sendbuf);
ISC_LIST_ENQUEUE(query->sendlist, sendbuf, link);
isc_buffer_usedregion(&query->sendbuf, &r);
debug("sending a request");
TIME_NOW(&query->time_sent);
INSIST(query->sock != NULL);
query->waiting_senddone = true;
result = isc_socket_sendtov2(query->sock, &query->sendlist,
global_task, send_done, query,
&query->sockaddr, NULL,
ISC_SOCKFLAG_NORETRY);
check_result(result, "isc_socket_sendtov");
sevent = isc_socket_socketevent(mctx, query->sock,
ISC_SOCKEVENT_SENDDONE,
send_done, query);
result = isc_socket_sendto2(query->sock, &r,
global_task, &query->sockaddr, NULL,
sevent, ISC_SOCKFLAG_NORETRY);
check_result(result, "isc_socket_sendto2");
sendcount++;
}
@@ -2971,7 +2944,8 @@ connect_timeout(isc_task_t *task, isc_event_t *event) {
static void
tcp_length_done(isc_task_t *task, isc_event_t *event) {
isc_socketevent_t *sevent;
isc_buffer_t *b = NULL;
isc_buffer_t b;
isc_region_t r;
isc_result_t result;
dig_query_t *query = NULL;
dig_lookup_t *l, *n;
@@ -2991,10 +2965,6 @@ tcp_length_done(isc_task_t *task, isc_event_t *event) {
recvcount--;
INSIST(recvcount >= 0);
b = ISC_LIST_HEAD(sevent->bufferlist);
INSIST(b == &query->lengthbuf);
ISC_LIST_DEQUEUE(sevent->bufferlist, b, link);
if (sevent->result == ISC_R_CANCELED) {
isc_event_free(&event);
l = query->lookup;
@@ -3027,7 +2997,10 @@ tcp_length_done(isc_task_t *task, isc_event_t *event) {
UNLOCK_LOOKUP;
return;
}
length = isc_buffer_getuint16(b);
isc_buffer_init(&b, sevent->region.base, sevent->n);
isc_buffer_add(&b, sevent->n);
length = isc_buffer_getuint16(&b);
if (length == 0) {
isc_event_free(&event);
launch_next_query(query, false);
@@ -3041,13 +3014,11 @@ tcp_length_done(isc_task_t *task, isc_event_t *event) {
*/
isc_buffer_invalidate(&query->recvbuf);
isc_buffer_init(&query->recvbuf, query->recvspace, length);
ENSURE(ISC_LIST_EMPTY(query->recvlist));
ISC_LINK_INIT(&query->recvbuf, link);
ISC_LIST_ENQUEUE(query->recvlist, &query->recvbuf, link);
isc_buffer_availableregion(&query->recvbuf, &r);
debug("recving with lookup=%p, query=%p", query->lookup, query);
result = isc_socket_recvv(query->sock, &query->recvlist, length, task,
recv_done, query);
check_result(result, "isc_socket_recvv");
result = isc_socket_recv(query->sock, &r, length, task,
recv_done, query);
check_result(result, "isc_socket_recv");
recvcount++;
debug("resubmitted recv request with length %d, recvcount=%d",
length, recvcount);
@@ -3063,7 +3034,7 @@ static void
launch_next_query(dig_query_t *query, bool include_question) {
isc_result_t result;
dig_lookup_t *l;
isc_buffer_t *buffer;
isc_region_t r;
INSIST(!free_now);
@@ -3082,35 +3053,28 @@ launch_next_query(dig_query_t *query, bool include_question) {
return;
}
isc_buffer_clear(&query->slbuf);
isc_buffer_clear(&query->lengthbuf);
isc_buffer_putuint16(&query->slbuf, (uint16_t) query->sendbuf.used);
ISC_LIST_INIT(query->sendlist);
ISC_LINK_INIT(&query->slbuf, link);
if (!query->first_soa_rcvd) {
buffer = clone_buffer(&query->slbuf);
ISC_LIST_ENQUEUE(query->sendlist, buffer, link);
if (include_question) {
buffer = clone_buffer(&query->sendbuf);
ISC_LIST_ENQUEUE(query->sendlist, buffer, link);
}
}
ISC_LINK_INIT(&query->lengthbuf, link);
ISC_LIST_ENQUEUE(query->lengthlist, &query->lengthbuf, link);
result = isc_socket_recvv(query->sock, &query->lengthlist, 0,
global_task, tcp_length_done, query);
check_result(result, "isc_socket_recvv");
isc_buffer_availableregion(&query->lengthbuf, &r);
result = isc_socket_recv(query->sock, &r, 0,
global_task, tcp_length_done, query);
check_result(result, "isc_socket_recv");
recvcount++;
debug("recvcount=%d", recvcount);
if (!query->first_soa_rcvd) {
debug("sending a request in launch_next_query");
TIME_NOW(&query->time_sent);
query->waiting_senddone = true;
result = isc_socket_sendv(query->sock, &query->sendlist,
global_task, send_done, query);
check_result(result, "isc_socket_sendv");
isc_buffer_clear(&query->tmpsendbuf);
isc_buffer_putuint16(&query->tmpsendbuf,
isc_buffer_usedlength(&query->sendbuf));
if (include_question) {
isc_buffer_usedregion(&query->sendbuf, &r);
isc_buffer_copyregion(&query->tmpsendbuf, &r);
}
isc_buffer_usedregion(&query->tmpsendbuf, &r);
result = isc_socket_send(query->sock, &r,
global_task, send_done, query);
check_result(result, "isc_socket_send");
sendcount++;
debug("sendcount=%d", sendcount);
}
@@ -3460,8 +3424,9 @@ ednsvers(dns_rdataset_t *opt) {
static void
recv_done(isc_task_t *task, isc_event_t *event) {
isc_socketevent_t *sevent = NULL;
isc_region_t r;
dig_query_t *query = NULL;
isc_buffer_t *b = NULL;
isc_buffer_t b;
dns_message_t *msg = NULL;
isc_result_t result;
dig_lookup_t *n, *l;
@@ -3491,9 +3456,8 @@ recv_done(isc_task_t *task, isc_event_t *event) {
REQUIRE(event->ev_type == ISC_SOCKEVENT_RECVDONE);
sevent = (isc_socketevent_t *)event;
b = ISC_LIST_HEAD(sevent->bufferlist);
INSIST(b == &query->recvbuf);
ISC_LIST_DEQUEUE(sevent->bufferlist, &query->recvbuf, link);
isc_buffer_init(&b, sevent->region.base, sevent->n);
isc_buffer_add(&b, sevent->n);
if ((l->tcp_mode) && (query->timer != NULL))
isc_timer_touch(query->timer);
@@ -3569,7 +3533,7 @@ recv_done(isc_task_t *task, isc_event_t *event) {
}
}
result = dns_message_peekheader(b, &id, &msgflags);
result = dns_message_peekheader(&b, &id, &msgflags);
if (result != ISC_R_SUCCESS || l->sendmsg->id != id) {
match = false;
if (l->tcp_mode) {
@@ -3638,7 +3602,7 @@ recv_done(isc_task_t *task, isc_event_t *event) {
parseflags |= DNS_MESSAGEPARSE_BESTEFFORT;
parseflags |= DNS_MESSAGEPARSE_IGNORETRUNCATION;
}
result = dns_message_parse(msg, b, parseflags);
result = dns_message_parse(msg, &b, parseflags);
if (result == DNS_R_RECOVERABLE) {
printf(";; Warning: Message parser reports malformed "
"message packet.\n");
@@ -3646,7 +3610,7 @@ recv_done(isc_task_t *task, isc_event_t *event) {
}
if (result != ISC_R_SUCCESS) {
printf(";; Got bad packet: %s\n", isc_result_totext(result));
hex_dump(b);
hex_dump(&b);
query->waiting_connect = false;
dns_message_destroy(&msg);
isc_event_free(&event);
@@ -3800,7 +3764,7 @@ recv_done(isc_task_t *task, isc_event_t *event) {
}
if (tsigkey != NULL) {
result = dns_tsig_verify(&query->recvbuf, msg, NULL, NULL);
result = dns_tsig_verify(&b, msg, NULL, NULL);
if (result != ISC_R_SUCCESS) {
printf(";; Couldn't verify signature: %s\n",
isc_result_totext(result));
@@ -3816,7 +3780,7 @@ recv_done(isc_task_t *task, isc_event_t *event) {
check_result(result,"dns_message_getquerytsig");
}
extrabytes = isc_buffer_remaininglength(b);
extrabytes = isc_buffer_remaininglength(&b);
debug("after parse");
if (l->doing_xfr && l->xfr_q == NULL) {
@@ -3863,8 +3827,8 @@ recv_done(isc_task_t *task, isc_event_t *event) {
(l->origin != NULL || l->need_search)) {
if (!next_origin(query->lookup) || showsearch) {
dighost_printmessage(query, msg, true);
dighost_received(b->used, &sevent->address,
query);
dighost_received(isc_buffer_usedlength(&b),
&sevent->address, query);
}
} else if (!l->trace && !l->ns_search_only) {
dighost_printmessage(query, msg, true);
@@ -3931,7 +3895,8 @@ recv_done(isc_task_t *task, isc_event_t *event) {
} else {
if (msg->rcode == dns_rcode_noerror || l->origin == NULL) {
dighost_received(b->used, &sevent->address, query);
dighost_received(isc_buffer_usedlength(&b),
&sevent->address, query);
}
if (!query->lookup->ns_search_only)
@@ -3954,11 +3919,10 @@ recv_done(isc_task_t *task, isc_event_t *event) {
udp_mismatch:
isc_buffer_invalidate(&query->recvbuf);
isc_buffer_init(&query->recvbuf, query->recvspace, COMMSIZE);
ISC_LIST_ENQUEUE(query->recvlist, &query->recvbuf, link);
result = isc_socket_recvv(query->sock, &query->recvlist, 1,
global_task, recv_done, query);
check_result(result, "isc_socket_recvv");
isc_buffer_availableregion(&query->recvbuf, &r);
result = isc_socket_recv(query->sock, &r, 1,
global_task, recv_done, query);
check_result(result, "isc_socket_recv");
recvcount++;
isc_event_free(&event);
UNLOCK_LOOKUP;

View File

@@ -203,15 +203,12 @@ struct dig_query {
bool ixfr_axfr;
char *servname;
char *userarg;
isc_bufferlist_t sendlist,
recvlist,
lengthlist;
isc_buffer_t recvbuf,
lengthbuf,
slbuf;
char *recvspace,
lengthspace[4],
slspace[4];
tmpsendbuf,
sendbuf;
char *recvspace, *tmpsendspace,
lengthspace[4];
isc_socket_t *sock;
ISC_LINK(dig_query_t) link;
ISC_LINK(dig_query_t) clink;
@@ -219,7 +216,6 @@ struct dig_query {
isc_time_t time_sent;
isc_time_t time_recv;
uint64_t byte_count;
isc_buffer_t sendbuf;
isc_timer_t *timer;
};

View File

@@ -923,12 +923,6 @@ flush_lookup_list(void) {
ISC_SOCKCANCEL_ALL);
isc_socket_detach(&q->sock);
}
if (ISC_LINK_LINKED(&q->recvbuf, link))
ISC_LIST_DEQUEUE(q->recvlist, &q->recvbuf,
link);
if (ISC_LINK_LINKED(&q->lengthbuf, link))
ISC_LIST_DEQUEUE(q->lengthlist, &q->lengthbuf,
link);
isc_buffer_invalidate(&q->recvbuf);
isc_buffer_invalidate(&q->lengthbuf);
qp = q;

View File

@@ -956,7 +956,6 @@ allocate_sevent(dns_dispatch_t *disp, isc_socket_t *sock,
free_sevent, disp->sepool);
ev->result = ISC_R_UNSET;
ISC_LINK_INIT(ev, ev_link);
ISC_LIST_INIT(ev->bufferlist);
ev->region.base = NULL;
ev->n = 0;
ev->offset = 0;

View File

@@ -114,9 +114,9 @@ struct isc_httpd {
* compressed HTTP data, if compression is used.
*
*/
isc_bufferlist_t bufflist;
isc_buffer_t headerbuffer;
isc_buffer_t compbuffer;
isc_buffer_t *sendbuffer;
const char *mimetype;
unsigned int retcode;
@@ -667,10 +667,9 @@ isc_httpd_accept(isc_task_t *task, isc_event_t *ev) {
}
isc_buffer_init(&httpd->headerbuffer, headerdata, HTTP_SENDGROW);
ISC_LIST_INIT(httpd->bufflist);
isc_buffer_initnull(&httpd->compbuffer);
isc_buffer_initnull(&httpd->bodybuffer);
httpd->sendbuffer = NULL;
reset_client(httpd);
r.base = (unsigned char *)httpd->recvbuf;
@@ -840,12 +839,13 @@ isc_httpd_compress(isc_httpd_t *httpd) {
static void
isc_httpd_recvdone(isc_task_t *task, isc_event_t *ev) {
isc_region_t r;
isc_result_t result;
isc_httpd_t *httpd = ev->ev_arg;
isc_socketevent_t *sev = (isc_socketevent_t *)ev;
isc_buffer_t *databuffer;
isc_httpdurl_t *url;
isc_time_t now;
isc_region_t r;
bool is_compressed = false;
char datebuf[ISC_FORMATHTTPTIMESTAMP_SIZE];
@@ -963,22 +963,24 @@ isc_httpd_recvdone(isc_task_t *task, isc_event_t *ev) {
isc_httpd_endheaders(httpd); /* done */
ISC_LIST_APPEND(httpd->bufflist, &httpd->headerbuffer, link);
/*
* Link the data buffer into our send queue, should we have any data
* rendered into it. If no data is present, we won't do anything
* with the buffer.
* Append either the compressed or the non-compressed response body to
* the response headers and store the result in httpd->sendbuffer.
*/
if (is_compressed == true) {
ISC_LIST_APPEND(httpd->bufflist, &httpd->compbuffer, link);
} else {
if (isc_buffer_length(&httpd->bodybuffer) > 0) {
ISC_LIST_APPEND(httpd->bufflist, &httpd->bodybuffer, link);
}
}
isc_buffer_dup(httpd->mgr->mctx,
&httpd->sendbuffer, &httpd->headerbuffer);
isc_buffer_setautorealloc(httpd->sendbuffer, true);
databuffer = (is_compressed ? &httpd->compbuffer : &httpd->bodybuffer);
isc_buffer_usedregion(databuffer, &r);
result = isc_buffer_copyregion(httpd->sendbuffer, &r);
RUNTIME_CHECK(result == ISC_R_SUCCESS);
/*
* Determine total response size.
*/
isc_buffer_usedregion(httpd->sendbuffer, &r);
/* check return code? */
(void)isc_socket_sendv(httpd->sock, &httpd->bufflist, task,
(void)isc_socket_send(httpd->sock, &r, task,
isc_httpd_senddone, httpd);
out:
@@ -1126,13 +1128,7 @@ isc_httpd_senddone(isc_task_t *task, isc_event_t *ev) {
ENTER("senddone");
INSIST(ISC_HTTPD_ISSEND(httpd));
/*
* First, unlink our header buffer from the socket's bufflist. This
* is sort of an evil hack, since we know our buffer will be there,
* and we know it's address, so we can just remove it directly.
*/
NOTICE("senddone unlinked header");
ISC_LIST_UNLINK(sev->bufferlist, &httpd->headerbuffer, link);
isc_buffer_free(&httpd->sendbuffer);
/*
* We will always want to clean up our receive buffer, even if we
@@ -1149,13 +1145,6 @@ isc_httpd_senddone(isc_task_t *task, isc_event_t *ev) {
}
NOTICE("senddone free callback performed");
}
if (ISC_LINK_LINKED(&httpd->bodybuffer, link)) {
ISC_LIST_UNLINK(sev->bufferlist, &httpd->bodybuffer, link);
NOTICE("senddone body buffer unlinked");
} else if (ISC_LINK_LINKED(&httpd->compbuffer, link)) {
ISC_LIST_UNLINK(sev->bufferlist, &httpd->compbuffer, link);
NOTICE("senddone compressed data unlinked and freed");
}
if (sev->result != ISC_R_SUCCESS) {
destroy_client(&httpd);

View File

@@ -204,7 +204,6 @@ struct isc_socketevent {
unsigned int n; /*%< bytes read or written */
unsigned int offset; /*%< offset into buffer list */
isc_region_t region; /*%< for single-buffer i/o */
isc_bufferlist_t bufferlist; /*%< list of buffers */
isc_sockaddr_t address; /*%< source address */
isc_time_t timestamp; /*%< timestamp of packet recv */
struct in6_pktinfo pktinfo; /*%< ipv6 pktinfo */
@@ -742,10 +741,6 @@ isc_result_t
isc_socket_recv(isc_socket_t *sock, isc_region_t *region,
unsigned int minimum,
isc_task_t *task, isc_taskaction_t action, void *arg);
isc_result_t
isc_socket_recvv(isc_socket_t *sock, isc_bufferlist_t *buflist,
unsigned int minimum,
isc_task_t *task, isc_taskaction_t action, void *arg);
isc_result_t
isc_socket_recv2(isc_socket_t *sock, isc_region_t *region,
@@ -775,11 +770,6 @@ isc_socket_recv2(isc_socket_t *sock, isc_region_t *region,
* into this function, or any data they refer to until the completion
* event is received.
*
*\li For isc_socket_recvv():
* On successful completion, '*buflist' will be empty, and the list of
* all buffers will be returned in the done event's 'bufferlist'
* member. On error return, '*buflist' will be unchanged.
*
*\li For isc_socket_recv2():
* 'event' is not NULL, and the non-socket specific fields are
* expected to be initialized.
@@ -834,18 +824,6 @@ isc_socket_sendto(isc_socket_t *sock, isc_region_t *region,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo);
isc_result_t
isc_socket_sendv(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg);
isc_result_t
isc_socket_sendtov(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo);
isc_result_t
isc_socket_sendtov2(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo,
unsigned int flags);
isc_result_t
isc_socket_sendto2(isc_socket_t *sock, isc_region_t *region,
isc_task_t *task,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo,
@@ -866,11 +844,6 @@ isc_socket_sendto2(isc_socket_t *sock, isc_region_t *region,
* into this function, or any data they refer to until the completion
* event is received.
*
*\li For isc_socket_sendv() and isc_socket_sendtov():
* On successful completion, '*buflist' will be empty, and the list of
* all buffers will be returned in the done event's 'bufferlist'
* member. On error return, '*buflist' will be unchanged.
*
*\li For isc_socket_sendto2():
* 'event' is not NULL, and the non-socket specific fields are
* expected to be initialized.

View File

@@ -39,7 +39,6 @@
#include <isc/app.h>
#include <isc/buffer.h>
#include <isc/bufferlist.h>
#include <isc/condition.h>
#include <isc/formatcheck.h>
#include <isc/json.h>
@@ -1197,10 +1196,7 @@ build_msghdr_send(isc__socket_t *sock, char* cmsgbuf, isc_socketevent_t *dev,
struct msghdr *msg, struct iovec *iov, size_t *write_countp)
{
unsigned int iovcount;
isc_buffer_t *buffer;
isc_region_t used;
size_t write_count;
size_t skip_count;
struct cmsghdr *cmsgp;
memset(msg, 0, sizeof(*msg));
@@ -1213,54 +1209,14 @@ build_msghdr_send(isc__socket_t *sock, char* cmsgbuf, isc_socketevent_t *dev,
msg->msg_namelen = 0;
}
buffer = ISC_LIST_HEAD(dev->bufferlist);
write_count = 0;
iovcount = 0;
/*
* Single buffer I/O? Skip what we've done so far in this region.
*/
if (buffer == NULL) {
write_count = dev->region.length - dev->n;
iov[0].iov_base = (void *)(dev->region.base + dev->n);
iov[0].iov_len = write_count;
iovcount = 1;
write_count = dev->region.length - dev->n;
iov[0].iov_base = (void *)(dev->region.base + dev->n);
iov[0].iov_len = write_count;
iovcount = 1;
goto config;
}
/*
* Multibuffer I/O.
* Skip the data in the buffer list that we have already written.
*/
skip_count = dev->n;
while (buffer != NULL) {
REQUIRE(ISC_BUFFER_VALID(buffer));
if (skip_count < isc_buffer_usedlength(buffer))
break;
skip_count -= isc_buffer_usedlength(buffer);
buffer = ISC_LIST_NEXT(buffer, link);
}
while (buffer != NULL) {
INSIST(iovcount < MAXSCATTERGATHER_SEND);
isc_buffer_usedregion(buffer, &used);
if (used.length > 0) {
iov[iovcount].iov_base = (void *)(used.base
+ skip_count);
iov[iovcount].iov_len = used.length - skip_count;
write_count += (used.length - skip_count);
skip_count = 0;
iovcount++;
}
buffer = ISC_LIST_NEXT(buffer, link);
}
INSIST(skip_count == 0U);
config:
msg->msg_iov = iov;
msg->msg_iovlen = iovcount;
msg->msg_control = NULL;
@@ -1416,8 +1372,6 @@ build_msghdr_recv(isc__socket_t *sock, char *cmsgbuf, isc_socketevent_t *dev,
struct msghdr *msg, struct iovec *iov, size_t *read_countp)
{
unsigned int iovcount;
isc_buffer_t *buffer;
isc_region_t available;
size_t read_count;
memset(msg, 0, sizeof(struct msghdr));
@@ -1432,48 +1386,12 @@ build_msghdr_recv(isc__socket_t *sock, char *cmsgbuf, isc_socketevent_t *dev,
dev->address = sock->peer_address;
}
buffer = ISC_LIST_HEAD(dev->bufferlist);
read_count = 0;
/*
* Single buffer I/O? Skip what we've done so far in this region.
*/
if (buffer == NULL) {
read_count = dev->region.length - dev->n;
iov[0].iov_base = (void *)(dev->region.base + dev->n);
iov[0].iov_len = read_count;
iovcount = 1;
goto config;
}
/*
* Multibuffer I/O.
* Skip empty buffers.
*/
while (buffer != NULL) {
REQUIRE(ISC_BUFFER_VALID(buffer));
if (isc_buffer_availablelength(buffer) != 0)
break;
buffer = ISC_LIST_NEXT(buffer, link);
}
iovcount = 0;
while (buffer != NULL) {
INSIST(iovcount < MAXSCATTERGATHER_RECV);
isc_buffer_availableregion(buffer, &available);
if (available.length > 0) {
iov[iovcount].iov_base = (void *)(available.base);
iov[iovcount].iov_len = available.length;
read_count += available.length;
iovcount++;
}
buffer = ISC_LIST_NEXT(buffer, link);
}
config:
read_count = dev->region.length - dev->n;
iov[0].iov_base = (void *)(dev->region.base + dev->n);
iov[0].iov_len = read_count;
iovcount = 1;
/*
* If needed, set up to receive that one extra byte.
@@ -1522,8 +1440,6 @@ static void
destroy_socketevent(isc_event_t *event) {
isc_socketevent_t *ev = (isc_socketevent_t *)event;
INSIST(ISC_LIST_EMPTY(ev->bufferlist));
(ev->destroy)(event);
}
@@ -1543,7 +1459,6 @@ allocate_socketevent(isc_mem_t *mctx, void *sender,
ev->result = ISC_R_UNSET;
ISC_LINK_INIT(ev, ev_link);
ISC_LIST_INIT(ev->bufferlist);
ev->region.base = NULL;
ev->n = 0;
ev->offset = 0;
@@ -1584,9 +1499,7 @@ doio_recv(isc__socket_t *sock, isc_socketevent_t *dev) {
int cc;
struct iovec iov[MAXSCATTERGATHER_RECV];
size_t read_count;
size_t actual_count;
struct msghdr msghdr;
isc_buffer_t *buffer;
int recv_errno;
char strbuf[ISC_STRERRORSIZE];
char cmsgbuf[RECVCMSGBUFLEN] = {0};
@@ -1719,25 +1632,6 @@ doio_recv(isc__socket_t *sock, isc_socketevent_t *dev) {
* update the buffers (if any) and the i/o count
*/
dev->n += cc;
actual_count = cc;
buffer = ISC_LIST_HEAD(dev->bufferlist);
while (buffer != NULL && actual_count > 0U) {
REQUIRE(ISC_BUFFER_VALID(buffer));
if (isc_buffer_availablelength(buffer) <= actual_count) {
actual_count -= isc_buffer_availablelength(buffer);
isc_buffer_add(buffer,
isc_buffer_availablelength(buffer));
} else {
isc_buffer_add(buffer, actual_count);
actual_count = 0;
POST(actual_count);
break;
}
buffer = ISC_LIST_NEXT(buffer, link);
if (buffer == NULL) {
INSIST(actual_count == 0U);
}
}
/*
* If we read less than we expected, update counters,
@@ -4668,61 +4562,6 @@ socket_recv(isc__socket_t *sock, isc_socketevent_t *dev, isc_task_t *task,
return (result);
}
isc_result_t
isc_socket_recvv(isc_socket_t *sock0, isc_bufferlist_t *buflist,
unsigned int minimum, isc_task_t *task,
isc_taskaction_t action, void *arg)
{
isc__socket_t *sock = (isc__socket_t *)sock0;
isc_socketevent_t *dev;
isc__socketmgr_t *manager;
unsigned int iocount;
isc_buffer_t *buffer;
REQUIRE(VALID_SOCKET(sock));
REQUIRE(buflist != NULL);
REQUIRE(!ISC_LIST_EMPTY(*buflist));
REQUIRE(task != NULL);
REQUIRE(action != NULL);
manager = sock->manager;
REQUIRE(VALID_MANAGER(manager));
iocount = isc_bufferlist_availablecount(buflist);
REQUIRE(iocount > 0);
INSIST(sock->bound);
dev = allocate_socketevent(manager->mctx, sock,
ISC_SOCKEVENT_RECVDONE, action, arg);
if (dev == NULL)
return (ISC_R_NOMEMORY);
/*
* UDP sockets are always partial read
*/
if (sock->type == isc_sockettype_udp)
dev->minimum = 1;
else {
if (minimum == 0)
dev->minimum = iocount;
else
dev->minimum = minimum;
}
/*
* Move each buffer from the passed in list to our internal one.
*/
buffer = ISC_LIST_HEAD(*buflist);
while (buffer != NULL) {
ISC_LIST_DEQUEUE(*buflist, buffer, link);
ISC_LIST_ENQUEUE(dev->bufferlist, buffer, link);
buffer = ISC_LIST_HEAD(*buflist);
}
return (socket_recv(sock, dev, task, 0));
}
isc_result_t
isc_socket_recv(isc_socket_t *sock0, isc_region_t *region,
unsigned int minimum, isc_task_t *task,
@@ -4757,7 +4596,6 @@ isc_socket_recv2(isc_socket_t *sock0, isc_region_t *region,
event->ev_sender = sock;
event->result = ISC_R_UNSET;
ISC_LIST_INIT(event->bufferlist);
event->region = *region;
event->n = 0;
event->offset = 0;
@@ -4912,65 +4750,6 @@ isc_socket_sendto(isc_socket_t *sock0, isc_region_t *region,
return (socket_send(sock, dev, task, address, pktinfo, 0));
}
isc_result_t
isc_socket_sendv(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg)
{
return (isc_socket_sendtov2(sock, buflist, task, action, arg, NULL,
NULL, 0));
}
isc_result_t
isc_socket_sendtov(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo)
{
return (isc_socket_sendtov2(sock, buflist, task, action, arg, address,
pktinfo, 0));
}
isc_result_t
isc_socket_sendtov2(isc_socket_t *sock0, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo,
unsigned int flags)
{
isc__socket_t *sock = (isc__socket_t *)sock0;
isc_socketevent_t *dev;
isc__socketmgr_t *manager;
unsigned int iocount;
isc_buffer_t *buffer;
REQUIRE(VALID_SOCKET(sock));
REQUIRE(buflist != NULL);
REQUIRE(!ISC_LIST_EMPTY(*buflist));
REQUIRE(task != NULL);
REQUIRE(action != NULL);
manager = sock->manager;
REQUIRE(VALID_MANAGER(manager));
iocount = isc_bufferlist_usedcount(buflist);
REQUIRE(iocount > 0);
dev = allocate_socketevent(manager->mctx, sock,
ISC_SOCKEVENT_SENDDONE, action, arg);
if (dev == NULL)
return (ISC_R_NOMEMORY);
/*
* Move each buffer from the passed in list to our internal one.
*/
buffer = ISC_LIST_HEAD(*buflist);
while (buffer != NULL) {
ISC_LIST_DEQUEUE(*buflist, buffer, link);
ISC_LIST_ENQUEUE(dev->bufferlist, buffer, link);
buffer = ISC_LIST_HEAD(*buflist);
}
return (socket_send(sock, dev, task, address, pktinfo, flags));
}
isc_result_t
isc_socket_sendto2(isc_socket_t *sock0, isc_region_t *region,
isc_task_t *task,
@@ -4985,7 +4764,6 @@ isc_socket_sendto2(isc_socket_t *sock0, isc_region_t *region,
REQUIRE(sock->type == isc_sockettype_udp);
event->ev_sender = sock;
event->result = ISC_R_UNSET;
ISC_LIST_INIT(event->bufferlist);
event->region = *region;
event->n = 0;
event->offset = 0;

View File

@@ -84,13 +84,9 @@ isc_socket_open
isc_socket_permunix
isc_socket_recv
isc_socket_recv2
isc_socket_recvv
isc_socket_send
isc_socket_sendto
isc_socket_sendto2
isc_socket_sendtov
isc_socket_sendtov2
isc_socket_sendv
isc_socket_setname
isc_socketmgr_create
isc_socketmgr_create2

View File

@@ -47,7 +47,6 @@
#include <isc/app.h>
#include <isc/buffer.h>
#include <isc/bufferlist.h>
#include <isc/condition.h>
#include <isc/list.h>
#include <isc/log.h>
@@ -271,16 +270,6 @@ struct isc_socket {
#define _set_state(sock, _state) do { (sock)->state = (_state); (sock)->state_lineno = __LINE__; } while (0)
/*
* Buffer structure
*/
typedef struct buflist buflist_t;
struct buflist {
void *buf;
unsigned int buflen;
ISC_LINK(buflist_t) link;
};
/*
* I/O Completion ports Info structures
@@ -296,7 +285,8 @@ typedef struct IoCompletionInfo {
DWORD received_bytes;
int request_type;
struct msghdr messagehdr;
ISC_LIST(buflist_t) bufferlist; /*%< list of buffers */
void *buf;
unsigned int buflen;
} IoCompletionInfo;
/*
@@ -950,91 +940,33 @@ build_msghdr_send(isc_socket_t *sock, isc_socketevent_t *dev,
IoCompletionInfo *lpo)
{
unsigned int iovcount;
isc_buffer_t *buffer;
buflist_t *cpbuffer;
isc_region_t used;
size_t write_count;
size_t skip_count;
memset(msg, 0, sizeof(*msg));
memmove(&msg->to_addr, &dev->address.type, dev->address.length);
msg->to_addr_len = dev->address.length;
buffer = ISC_LIST_HEAD(dev->bufferlist);
write_count = 0;
iovcount = 0;
/*
* Single buffer I/O? Skip what we've done so far in this region.
*/
if (buffer == NULL) {
write_count = dev->region.length - dev->n;
cpbuffer = HeapAlloc(hHeapHandle, HEAP_ZERO_MEMORY, sizeof(buflist_t));
RUNTIME_CHECK(cpbuffer != NULL);
cpbuffer->buf = HeapAlloc(hHeapHandle, HEAP_ZERO_MEMORY, write_count);
RUNTIME_CHECK(cpbuffer->buf != NULL);
write_count = dev->region.length - dev->n;
lpo->buf = HeapAlloc(hHeapHandle, HEAP_ZERO_MEMORY, write_count);
RUNTIME_CHECK(lpo->buf != NULL);
socket_log(__LINE__, sock, NULL, TRACE,
isc_msgcat, ISC_MSGSET_SOCKET, ISC_MSG_ACCEPTLOCK,
"alloc_buffer %p %d %p %d", cpbuffer, sizeof(buflist_t),
cpbuffer->buf, write_count);
socket_log(__LINE__, sock, NULL, TRACE,
isc_msgcat, ISC_MSGSET_SOCKET, ISC_MSG_ACCEPTLOCK,
"alloc_buffer %p %d", lpo->buf, write_count);
memmove(cpbuffer->buf,(dev->region.base + dev->n), write_count);
cpbuffer->buflen = (unsigned int)write_count;
ISC_LINK_INIT(cpbuffer, link);
ISC_LIST_ENQUEUE(lpo->bufferlist, cpbuffer, link);
iov[0].buf = cpbuffer->buf;
iov[0].len = (u_long)write_count;
iovcount = 1;
memmove(lpo->buf,(dev->region.base + dev->n), write_count);
lpo->buflen = (unsigned int)write_count;
iov[0].buf = lpo->buf;
iov[0].len = (u_long)write_count;
iovcount = 1;
goto config;
}
/*
* Multibuffer I/O.
* Skip the data in the buffer list that we have already written.
*/
skip_count = dev->n;
while (buffer != NULL) {
REQUIRE(ISC_BUFFER_VALID(buffer));
if (skip_count < isc_buffer_usedlength(buffer))
break;
skip_count -= isc_buffer_usedlength(buffer);
buffer = ISC_LIST_NEXT(buffer, link);
}
while (buffer != NULL) {
INSIST(iovcount < MAXSCATTERGATHER_SEND);
isc_buffer_usedregion(buffer, &used);
if (used.length > 0) {
int uselen = (int)(used.length - skip_count);
cpbuffer = HeapAlloc(hHeapHandle, HEAP_ZERO_MEMORY, sizeof(buflist_t));
RUNTIME_CHECK(cpbuffer != NULL);
cpbuffer->buf = HeapAlloc(hHeapHandle, HEAP_ZERO_MEMORY, uselen);
RUNTIME_CHECK(cpbuffer->buf != NULL);
socket_log(__LINE__, sock, NULL, TRACE,
isc_msgcat, ISC_MSGSET_SOCKET, ISC_MSG_ACCEPTLOCK,
"alloc_buffer %p %d %p %d", cpbuffer, sizeof(buflist_t),
cpbuffer->buf, write_count);
memmove(cpbuffer->buf,(used.base + skip_count), uselen);
cpbuffer->buflen = uselen;
iov[iovcount].buf = cpbuffer->buf;
iov[iovcount].len = (u_long)(used.length - skip_count);
write_count += uselen;
skip_count = 0;
iovcount++;
}
buffer = ISC_LIST_NEXT(buffer, link);
}
INSIST(skip_count == 0);
config:
msg->msg_iov = iov;
msg->msg_iovlen = iovcount;
msg->msg_totallen = (u_int)write_count;
@@ -1059,8 +991,6 @@ static void
destroy_socketevent(isc_event_t *event) {
isc_socketevent_t *ev = (isc_socketevent_t *)event;
INSIST(ISC_LIST_EMPTY(ev->bufferlist));
(ev->destroy)(event);
}
@@ -1079,7 +1009,6 @@ allocate_socketevent(isc_mem_t *mctx, isc_socket_t *sock,
ev->result = ISC_R_IOERROR; // XXXMLG temporary change to detect failure to set
ISC_LINK_INIT(ev, ev_link);
ISC_LIST_INIT(ev->bufferlist);
ev->region.base = NULL;
ev->n = 0;
ev->offset = 0;
@@ -1215,9 +1144,7 @@ map_socket_error(isc_socket_t *sock, int windows_errno, int *isc_errno,
static void
fill_recv(isc_socket_t *sock, isc_socketevent_t *dev) {
isc_region_t r;
int copylen;
isc_buffer_t *buffer;
INSIST(dev->n < dev->minimum);
INSIST(sock->recvbuf.remaining > 0);
@@ -1241,36 +1168,12 @@ fill_recv(isc_socket_t *sock, isc_socketevent_t *dev) {
dev->address = sock->address;
}
/*
* Run through the list of buffers we were given, and find the
* first one with space. Once it is found, loop through, filling
* the buffers as much as possible.
*/
buffer = ISC_LIST_HEAD(dev->bufferlist);
if (buffer != NULL) { // Multi-buffer receive
while (buffer != NULL && sock->recvbuf.remaining > 0) {
REQUIRE(ISC_BUFFER_VALID(buffer));
if (isc_buffer_availablelength(buffer) > 0) {
isc_buffer_availableregion(buffer, &r);
copylen = min(r.length,
sock->recvbuf.remaining);
memmove(r.base, sock->recvbuf.consume_position,
copylen);
sock->recvbuf.consume_position += copylen;
sock->recvbuf.remaining -= copylen;
isc_buffer_add(buffer, copylen);
dev->n += copylen;
}
buffer = ISC_LIST_NEXT(buffer, link);
}
} else { // Single-buffer receive
copylen = min(dev->region.length - dev->n, sock->recvbuf.remaining);
memmove(dev->region.base + dev->n,
sock->recvbuf.consume_position, copylen);
sock->recvbuf.consume_position += copylen;
sock->recvbuf.remaining -= copylen;
dev->n += copylen;
}
copylen = min(dev->region.length - dev->n, sock->recvbuf.remaining);
memmove(dev->region.base + dev->n,
sock->recvbuf.consume_position, copylen);
sock->recvbuf.consume_position += copylen;
sock->recvbuf.remaining -= copylen;
dev->n += copylen;
/*
* UDP receives are all-consuming. That is, if we have 4k worth of
@@ -1377,7 +1280,6 @@ startio_send(isc_socket_t *sock, isc_socketevent_t *dev, int *nbytes,
lpo->dev = dev;
mh = &lpo->messagehdr;
memset(mh, 0, sizeof(struct msghdr));
ISC_LIST_INIT(lpo->bufferlist);
build_msghdr_send(sock, dev, mh, cmsg, sock->iov, lpo);
@@ -2301,8 +2203,6 @@ static void
internal_send(isc_socket_t *sock, isc_socketevent_t *dev,
struct msghdr *messagehdr, int nbytes, int send_errno, IoCompletionInfo *lpo)
{
buflist_t *buffer;
/*
* Find out what socket this is and lock it.
*/
@@ -2315,17 +2215,14 @@ internal_send(isc_socket_t *sock, isc_socketevent_t *dev,
isc_msgcat, ISC_MSGSET_SOCKET, ISC_MSG_INTERNALSEND,
"internal_send: task got socket event %p", dev);
buffer = ISC_LIST_HEAD(lpo->bufferlist);
while (buffer != NULL) {
ISC_LIST_DEQUEUE(lpo->bufferlist, buffer, link);
if (lpo->buf != NULL) {
socket_log(__LINE__, sock, NULL, TRACE,
isc_msgcat, ISC_MSGSET_SOCKET, ISC_MSG_ACCEPTLOCK,
"free_buffer %p %p", buffer, buffer->buf);
"free_buffer %p", lpo->buf);
HeapFree(hHeapHandle, 0, buffer->buf);
HeapFree(hHeapHandle, 0, buffer);
buffer = ISC_LIST_HEAD(lpo->bufferlist);
HeapFree(hHeapHandle, 0, lpo->buf);
lpo->buf = NULL;
lpo->buflen = 0;
}
INSIST(sock->pending_iocp > 0);
@@ -2836,77 +2733,6 @@ socket_recv(isc_socket_t *sock, isc_socketevent_t *dev, isc_task_t *task,
return (result);
}
isc_result_t
isc_socket_recvv(isc_socket_t *sock, isc_bufferlist_t *buflist,
unsigned int minimum, isc_task_t *task,
isc_taskaction_t action, void *arg)
{
isc_socketevent_t *dev;
isc_socketmgr_t *manager;
unsigned int iocount;
isc_buffer_t *buffer;
isc_result_t ret;
REQUIRE(VALID_SOCKET(sock));
LOCK(&sock->lock);
CONSISTENT(sock);
/*
* Make sure that the socket is not closed. XXXMLG change error here?
*/
if (sock->fd == INVALID_SOCKET) {
UNLOCK(&sock->lock);
return (ISC_R_CONNREFUSED);
}
REQUIRE(buflist != NULL);
REQUIRE(!ISC_LIST_EMPTY(*buflist));
REQUIRE(task != NULL);
REQUIRE(action != NULL);
manager = sock->manager;
REQUIRE(VALID_MANAGER(manager));
iocount = isc_bufferlist_availablecount(buflist);
REQUIRE(iocount > 0);
INSIST(sock->bound);
dev = allocate_socketevent(manager->mctx, sock,
ISC_SOCKEVENT_RECVDONE, action, arg);
if (dev == NULL) {
UNLOCK(&sock->lock);
return (ISC_R_NOMEMORY);
}
/*
* UDP sockets are always partial read
*/
if (sock->type == isc_sockettype_udp)
dev->minimum = 1;
else {
if (minimum == 0)
dev->minimum = iocount;
else
dev->minimum = minimum;
}
/*
* Move each buffer from the passed in list to our internal one.
*/
buffer = ISC_LIST_HEAD(*buflist);
while (buffer != NULL) {
ISC_LIST_DEQUEUE(*buflist, buffer, link);
ISC_LIST_ENQUEUE(dev->bufferlist, buffer, link);
buffer = ISC_LIST_HEAD(*buflist);
}
ret = socket_recv(sock, dev, task, 0);
UNLOCK(&sock->lock);
return (ret);
}
isc_result_t
isc_socket_recv(isc_socket_t *sock, isc_region_t *region,
unsigned int minimum, isc_task_t *task,
@@ -2967,7 +2793,6 @@ isc_socket_recv2(isc_socket_t *sock, isc_region_t *region,
return (ISC_R_CONNREFUSED);
}
ISC_LIST_INIT(event->bufferlist);
event->region = *region;
event->n = 0;
event->offset = 0;
@@ -3112,80 +2937,6 @@ isc_socket_sendto(isc_socket_t *sock, isc_region_t *region,
return (ret);
}
isc_result_t
isc_socket_sendv(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg)
{
return (isc_socket_sendtov2(sock, buflist, task, action, arg, NULL,
NULL, 0));
}
isc_result_t
isc_socket_sendtov(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo)
{
return (isc_socket_sendtov2(sock, buflist, task, action, arg, address,
pktinfo, 0));
}
isc_result_t
isc_socket_sendtov2(isc_socket_t *sock, isc_bufferlist_t *buflist,
isc_task_t *task, isc_taskaction_t action, void *arg,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo,
unsigned int flags)
{
isc_socketevent_t *dev;
isc_socketmgr_t *manager;
unsigned int iocount;
isc_buffer_t *buffer;
isc_result_t ret;
REQUIRE(VALID_SOCKET(sock));
LOCK(&sock->lock);
CONSISTENT(sock);
/*
* make sure that the socket's not closed
*/
if (sock->fd == INVALID_SOCKET) {
UNLOCK(&sock->lock);
return (ISC_R_CONNREFUSED);
}
REQUIRE(buflist != NULL);
REQUIRE(!ISC_LIST_EMPTY(*buflist));
REQUIRE(task != NULL);
REQUIRE(action != NULL);
manager = sock->manager;
REQUIRE(VALID_MANAGER(manager));
iocount = isc_bufferlist_usedcount(buflist);
REQUIRE(iocount > 0);
dev = allocate_socketevent(manager->mctx, sock,
ISC_SOCKEVENT_SENDDONE, action, arg);
if (dev == NULL) {
UNLOCK(&sock->lock);
return (ISC_R_NOMEMORY);
}
/*
* Move each buffer from the passed in list to our internal one.
*/
buffer = ISC_LIST_HEAD(*buflist);
while (buffer != NULL) {
ISC_LIST_DEQUEUE(*buflist, buffer, link);
ISC_LIST_ENQUEUE(dev->bufferlist, buffer, link);
buffer = ISC_LIST_HEAD(*buflist);
}
ret = socket_send(sock, dev, task, address, pktinfo, flags);
UNLOCK(&sock->lock);
return (ret);
}
isc_result_t
isc_socket_sendto2(isc_socket_t *sock, isc_region_t *region, isc_task_t *task,
const isc_sockaddr_t *address, struct in6_pktinfo *pktinfo,
@@ -3209,7 +2960,6 @@ isc_socket_sendto2(isc_socket_t *sock, isc_region_t *region, isc_task_t *task,
UNLOCK(&sock->lock);
return (ISC_R_CONNREFUSED);
}
ISC_LIST_INIT(event->bufferlist);
event->region = *region;
event->n = 0;
event->offset = 0;