aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGarrett D'Amore <garrett@damore.org>2024-12-29 17:24:59 -0800
committerGarrett D'Amore <garrett@damore.org>2024-12-29 17:36:47 -0800
commit9b42f5cb39faf83f9f5e0d6c2cf490cc4420901a (patch)
tree67ba696bdfddeefcea8aeba0d4b8cf05e688934b
parent330c4907544ac1c1f42e22bde45d9c7e49a8e333 (diff)
downloadnng-9b42f5cb39faf83f9f5e0d6c2cf490cc4420901a.tar.gz
nng-9b42f5cb39faf83f9f5e0d6c2cf490cc4420901a.tar.bz2
nng-9b42f5cb39faf83f9f5e0d6c2cf490cc4420901a.zip
posix: fall back to send if sendmsg is unavailable for ipc and tcp
This will be slower, as each vector element has to be sent in a single system call, but for platforms that lack sendmsg it will at least work.
-rw-r--r--src/platform/posix/posix_ipcconn.c29
-rw-r--r--src/platform/posix/posix_tcpconn.c31
2 files changed, 30 insertions, 30 deletions
diff --git a/src/platform/posix/posix_ipcconn.c b/src/platform/posix/posix_ipcconn.c
index 72fe660b..b3376815 100644
--- a/src/platform/posix/posix_ipcconn.c
+++ b/src/platform/posix/posix_ipcconn.c
@@ -39,22 +39,18 @@ ipc_dowrite(ipc_conn *c)
}
while ((aio = nni_list_first(&c->writeq)) != NULL) {
- unsigned i;
- int n;
- int niov;
- unsigned naiov;
- nni_iov *aiov;
- struct msghdr hdr;
- struct iovec iovec[16];
+ int n;
+ unsigned naiov;
+ nni_iov *aiov;
- memset(&hdr, 0, sizeof(hdr));
nni_aio_get_iov(aio, &naiov, &aiov);
+ NNI_ASSERT(naiov <= NNI_AIO_MAX_IOV);
- if (naiov > NNI_NUM_ELEMENTS(iovec)) {
- nni_aio_list_remove(aio);
- nni_aio_finish_error(aio, NNG_EINVAL);
- continue;
- }
+#ifdef NNG_HAVE_SENDMSG
+ struct msghdr hdr = { 0 };
+ struct iovec iovec[NNI_AIO_MAX_IOV];
+ int niov;
+ unsigned i;
for (niov = 0, i = 0; i < naiov; i++) {
if (aiov[i].iov_len > 0) {
@@ -67,7 +63,12 @@ ipc_dowrite(ipc_conn *c)
hdr.msg_iovlen = niov;
hdr.msg_iov = iovec;
- if ((n = sendmsg(fd, &hdr, MSG_NOSIGNAL)) < 0) {
+ n = sendmsg(fd, &hdr, MSG_NOSIGNAL);
+#else
+ // We have to send a bit at a time.
+ n = send(fd, aiov[0].iov_buf, aiov[0].iov_len, MSG_NOSIGNAL);
+#endif
+ if (n < 0) {
switch (errno) {
case EINTR:
continue;
diff --git a/src/platform/posix/posix_tcpconn.c b/src/platform/posix/posix_tcpconn.c
index 9837a839..920c3ff9 100644
--- a/src/platform/posix/posix_tcpconn.c
+++ b/src/platform/posix/posix_tcpconn.c
@@ -39,23 +39,19 @@ tcp_dowrite(nni_tcp_conn *c)
}
while ((aio = nni_list_first(&c->writeq)) != NULL) {
- unsigned i;
- int n;
- int niov;
- unsigned naiov;
- nni_iov *aiov;
- struct msghdr hdr;
- struct iovec iovec[16];
+ int n;
+ unsigned naiov;
+ nni_iov *aiov;
- memset(&hdr, 0, sizeof(hdr));
nni_aio_get_iov(aio, &naiov, &aiov);
- if (naiov > NNI_NUM_ELEMENTS(iovec)) {
- nni_aio_list_remove(aio);
- nni_aio_finish_error(aio, NNG_EINVAL);
- continue;
- }
+ NNI_ASSERT(naiov <= NNI_AIO_MAX_IOV);
+#ifdef NNG_HAVE_SENDMSG
+ struct msghdr hdr = { 0 };
+ struct iovec iovec[NNI_AIO_MAX_IOV];
+ int niov;
+ unsigned i;
for (niov = 0, i = 0; i < naiov; i++) {
if (aiov[i].iov_len > 0) {
iovec[niov].iov_len = aiov[i].iov_len;
@@ -67,7 +63,12 @@ tcp_dowrite(nni_tcp_conn *c)
hdr.msg_iovlen = niov;
hdr.msg_iov = iovec;
- if ((n = sendmsg(fd, &hdr, MSG_NOSIGNAL)) < 0) {
+ n = sendmsg(fd, &hdr, MSG_NOSIGNAL);
+#else
+ // We have to send a bit at a time.
+ n = send(fd, aiov[0].iov_buf, aiov[0].iov_len, MSG_NOSIGNAL);
+#endif
+ if (n < 0) {
switch (errno) {
case EINTR:
continue;
@@ -87,8 +88,6 @@ tcp_dowrite(nni_tcp_conn *c)
}
nni_aio_bump_count(aio, n);
- // We completed the entire operation on this aio.
- // (Sendmsg never returns a partial result.)
nni_aio_list_remove(aio);
nni_aio_finish(aio, 0, nni_aio_count(aio));