Add osmo_stream_{cli,srv_link}_set_nodelay() function Using this function, the user can configure if sockets related to the respective stream client or server should have the NODELAY socket option set in order to avoid Nagle algorithm or related algorithms that may introduce packet delay on the transmitter side.
Change-Id: Ibeb9ba227bab18f7f4f16518c0022c4f003cc8e9 --- M include/osmocom/netif/stream.h M src/stream.c 2 files changed, 67 insertions(+), 0 deletions(-) git pull ssh://gerrit.osmocom.org:29418/libosmo-netif refs/changes/95/2295/2 diff --git a/include/osmocom/netif/stream.h b/include/osmocom/netif/stream.h index 63eccf8..7afb7af 100644 --- a/include/osmocom/netif/stream.h +++ b/include/osmocom/netif/stream.h @@ -16,6 +16,7 @@ struct osmo_stream_srv_link *osmo_stream_srv_link_create(void *ctx); void osmo_stream_srv_link_destroy(struct osmo_stream_srv_link *link); +void osmo_stream_srv_link_set_nodelay(struct osmo_stream_srv_link *link, bool nodelay); void osmo_stream_srv_link_set_addr(struct osmo_stream_srv_link *link, const char *addr); void osmo_stream_srv_link_set_port(struct osmo_stream_srv_link *link, uint16_t port); void osmo_stream_srv_link_set_proto(struct osmo_stream_srv_link *link, uint16_t proto); @@ -45,6 +46,7 @@ /*! \brief Osmocom Stream Client: Single client connection */ struct osmo_stream_cli; +void osmo_stream_cli_set_nodelay(struct osmo_stream_cli *cli, bool nodelay); void osmo_stream_cli_set_addr(struct osmo_stream_cli *cli, const char *addr); void osmo_stream_cli_set_port(struct osmo_stream_cli *cli, uint16_t port); void osmo_stream_cli_set_proto(struct osmo_stream_cli *cli, uint16_t proto); diff --git a/src/stream.c b/src/stream.c index f5ead17..76886f0 100644 --- a/src/stream.c +++ b/src/stream.c @@ -9,6 +9,7 @@ #include <sys/ioctl.h> #include <arpa/inet.h> #include <netinet/in.h> +#include <netinet/tcp.h> #include <osmocom/core/timer.h> #include <osmocom/core/select.h> @@ -75,6 +76,7 @@ }; #define OSMO_STREAM_CLI_F_RECONF (1 << 0) +#define OSMO_STREAM_CLI_F_NODELAY (1 << 1) struct osmo_stream_cli { struct osmo_fd ofd; @@ -400,6 +402,22 @@ return ret; } + if (cli->flags & OSMO_STREAM_CLI_F_NODELAY) { + int on = 1; + switch (cli->proto) { + case IPPROTO_TCP: + setsockopt(cli->ofd.fd, SOL_TCP, TCP_NODELAY, &on, sizeof(on)); + break; + case IPPROTO_SCTP: + setsockopt(cli->ofd.fd, SOL_SCTP, SCTP_NODELAY, &on, sizeof(on)); + break; + default: + LOGP(DLINP, LOGL_ERROR, "Unknown protocol %u, cannot set NODELAY\n", + cli->proto); + break; + } + } + cli->ofd.fd = ret; if (osmo_fd_register(&cli->ofd) < 0) { close(ret); @@ -409,6 +427,21 @@ return 0; } +/*! \brief Set the NODELAY socket option to avoid Nagle-like behavior + * Setting this to nodelay=true will automatically set the NODELAY + * socket option on any socket established via \ref osmo_stream_cli_open + * or any re-connect. You have to set this _before_ opening the + * socket. + * \param[in] cli Stream client whose sockets are to be configured + * \param[in] nodelay whether to set (true) NODELAY before connect() + */ +void osmo_stream_cli_set_nodelay(struct osmo_stream_cli *cli, bool nodelay) +{ + if (nodelay) + cli->flags |= OSMO_STREAM_CLI_F_NODELAY; + else + cli->flags &= ~OSMO_STREAM_CLI_F_NODELAY; +} /*! \brief Open connection of an Osmocom stream client * \param[in] cli Stream Client to connect */ @@ -473,6 +506,7 @@ */ #define OSMO_STREAM_SRV_F_RECONF (1 << 0) +#define OSMO_STREAM_SRV_F_NODELAY (1 << 1) struct osmo_stream_srv_link { struct osmo_fd ofd; @@ -503,6 +537,22 @@ if (link->proto == IPPROTO_SCTP) sctp_sock_activate_events(ret); + if (link->flags & OSMO_STREAM_SRV_F_NODELAY) { + int on = 1; + switch (link->proto) { + case IPPROTO_SCTP: + setsockopt(ret, SOL_SCTP, SCTP_NODELAY, &on, sizeof(on)); + break; + case IPPROTO_TCP: + setsockopt(ret, SOL_TCP, TCP_NODELAY, &on, sizeof(on)); + break; + default: + LOGP(DLINP, LOGL_ERROR, "Unknown protocol %u, cannot set NODELAY\n", + link->proto); + break; + } + } + if (link->accept_cb) link->accept_cb(link, ret); @@ -532,6 +582,21 @@ return link; } +/*! \brief Set the NODELAY socket option to avoid Nagle-like behavior + * Setting this to nodelay=true will automatically set the NODELAY + * socket option on any socket established via this server link, before + * calling the accept_cb() + * \param[in] link server link whose sockets are to be configured + * \param[in] nodelay whether to set (true) NODELAY after accept + */ +void osmo_stream_srv_link_set_nodelay(struct osmo_stream_srv_link *link, bool nodelay) +{ + if (nodelay) + link->flags |= OSMO_STREAM_SRV_F_NODELAY; + else + link->flags &= ~OSMO_STREAM_SRV_F_NODELAY; +} + /*! \brief Set the local address to which we bind * \param[in] link Stream Server Link to modify * \param[in] addr Local IP address -- To view, visit https://gerrit.osmocom.org/2295 To unsubscribe, visit https://gerrit.osmocom.org/settings Gerrit-MessageType: newpatchset Gerrit-Change-Id: Ibeb9ba227bab18f7f4f16518c0022c4f003cc8e9 Gerrit-PatchSet: 2 Gerrit-Project: libosmo-netif Gerrit-Branch: master Gerrit-Owner: Harald Welte <lafo...@gnumonks.org> Gerrit-Reviewer: Jenkins Builder