From 2214e51457974712652d9863761856ae868a51e8 Mon Sep 17 00:00:00 2001 From: "chao.an" Date: Mon, 12 Apr 2021 18:43:32 +0800 Subject: [PATCH] netutls/usrsock_rpmsg_server: add support for send reassemble Signed-off-by: chao.an --- netutils/usrsock_rpmsg/Kconfig | 8 +- netutils/usrsock_rpmsg/usrsock_rpmsg_server.c | 121 ++++++++++++++++-- 2 files changed, 118 insertions(+), 11 deletions(-) diff --git a/netutils/usrsock_rpmsg/Kconfig b/netutils/usrsock_rpmsg/Kconfig index b422e1948..fd1bf88bc 100644 --- a/netutils/usrsock_rpmsg/Kconfig +++ b/netutils/usrsock_rpmsg/Kconfig @@ -25,9 +25,15 @@ config NETUTILS_USRSOCK_RPMSG_STACKSIZE The stack size allocated for the usrsock task. config NETUTILS_USRSOCK_NSOCK_DESCRIPTORS - int "the maximum number of socket descriptors for usrsock monitoring" + int "The maximum number of socket descriptors for usrsock monitoring" default 64 ---help--- The maximum number of socket description for usrsosck monitoring. +config NETUTILS_USRSOCK_NIOVEC + int "The maximum number of I/O vector for reassemble buffer" + default 8 + ---help--- + The maximum number of I/O vector for reassemble buffer. + endif # NETUTILS_USRSOCK_RPMSG diff --git a/netutils/usrsock_rpmsg/usrsock_rpmsg_server.c b/netutils/usrsock_rpmsg/usrsock_rpmsg_server.c index 2efb83789..b9ddb09d3 100644 --- a/netutils/usrsock_rpmsg/usrsock_rpmsg_server.c +++ b/netutils/usrsock_rpmsg/usrsock_rpmsg_server.c @@ -42,6 +42,7 @@ struct usrsock_rpmsg_s pid_t pid; pthread_mutex_t mutex; pthread_cond_t cond; + struct iovec iov[CONFIG_NETUTILS_USRSOCK_NIOVEC]; struct socket socks[CONFIG_NETUTILS_USRSOCK_NSOCK_DESCRIPTORS]; struct rpmsg_endpoint *epts[CONFIG_NETUTILS_USRSOCK_NSOCK_DESCRIPTORS]; struct pollfd pfds[CONFIG_NETUTILS_USRSOCK_NSOCK_DESCRIPTORS]; @@ -320,20 +321,100 @@ static int usrsock_rpmsg_sendto_handler(struct rpmsg_endpoint *ept, void *data, size_t len, uint32_t src, void *priv_) { - struct usrsock_request_sendto_s *req = data; + struct usrsock_request_sendto_s *req; struct usrsock_rpmsg_s *priv = priv_; ssize_t ret = -EBADF; + size_t total; int retr; + int i; - if (req->usockid >= 0 && - req->usockid < CONFIG_NETUTILS_USRSOCK_NSOCK_DESCRIPTORS) + if (priv->iov[0].iov_base) { - ret = psock_sendto(&priv->socks[req->usockid], - (const void *)(req + 1) + req->addrlen, req->buflen, - req->flags, - req->addrlen ? (const struct sockaddr *)(req + 1) : NULL, - req->addrlen); + size_t hlen; + struct msghdr msg = + { + }; + + req = priv->iov[0].iov_base; + hlen = sizeof(*req) + req->addrlen; + + total = len; + for (i = 0; i < CONFIG_NETUTILS_USRSOCK_NIOVEC; i++) + { + if (!priv->iov[i].iov_base) + { + priv->iov[i].iov_base = data; + priv->iov[i].iov_len = len; + rpmsg_hold_rx_buffer(ept, data); + break; + } + + total += priv->iov[i].iov_len; + } + + if (i == CONFIG_NETUTILS_USRSOCK_NIOVEC) + { + ret = -ENOMEM; + goto out; + } + + /* Partial packet ? continue to fetch */ + + if (req->buflen > total - hlen) + { + return 0; + } + else if (req->buflen < total - hlen) + { + ret = -EINVAL; + goto out; + } + + /* Skip the sendto header from I/O vector */ + + priv->iov[0].iov_base = (char *)priv->iov[0].iov_base + hlen; + priv->iov[0].iov_len -= hlen; + + msg.msg_name = req->addrlen ? (void *)(req + 1) : NULL; + msg.msg_namelen = req->addrlen; + msg.msg_iov = priv->iov; + msg.msg_iovlen = i + 1; + + ret = psock_sendmsg(&priv->socks[req->usockid], &msg, req->flags); + + /* Recover the I/O vector */ + + priv->iov[0].iov_base = (char *)priv->iov[0].iov_base - hlen; + priv->iov[0].iov_len += hlen; } + else + { + req = data; + + if (req->usockid >= 0 && + req->usockid < CONFIG_NETUTILS_USRSOCK_NSOCK_DESCRIPTORS) + { + total = sizeof(*req) + req->addrlen + req->buflen; + if (total > len) + { + priv->iov[0].iov_base = data; + priv->iov[0].iov_len = len; + + rpmsg_hold_rx_buffer(ept, data); + return 0; + } + else + { + ret = psock_sendto(&priv->socks[req->usockid], + (const void *)(req + 1) + req->addrlen, req->buflen, + req->flags, + req->addrlen ? (const struct sockaddr *)(req + 1) : NULL, + req->addrlen); + } + } + } + +out: retr = usrsock_rpmsg_send_ack(ept, req->head.xid, ret); if (retr >= 0 && ret >= 0) @@ -351,6 +432,21 @@ static int usrsock_rpmsg_sendto_handler(struct rpmsg_endpoint *ept, pthread_mutex_unlock(&priv->mutex); } + if (priv->iov[0].iov_base) + { + for (i = 0; i < CONFIG_NETUTILS_USRSOCK_NIOVEC; i++) + { + if (priv->iov[i].iov_base == NULL) + { + break; + } + + rpmsg_release_rx_buffer(ept, priv->iov[i].iov_base); + priv->iov[i].iov_base = NULL; + priv->iov[i].iov_len = 0; + } + } + return retr; } @@ -726,11 +822,16 @@ static void usrsock_rpmsg_ns_unbind(struct rpmsg_endpoint *ept) } static int usrsock_rpmsg_ept_cb(struct rpmsg_endpoint *ept, void *data, - size_t len, uint32_t src, void *priv) + size_t len, uint32_t src, void *priv_) { struct usrsock_request_common_s *common = data; + struct usrsock_rpmsg_s *priv = priv_; - if (common->reqid >= 0 && common->reqid < USRSOCK_REQUEST__MAX) + if (priv->iov[0].iov_base) + { + return usrsock_rpmsg_sendto_handler(ept, data, len, src, priv); + } + else if (common->reqid >= 0 && common->reqid < USRSOCK_REQUEST__MAX) { return g_usrsock_rpmsg_handler[common->reqid](ept, data, len, src, priv);