From owner-svn-src-head@freebsd.org Wed Sep 6 13:56:20 2017 Return-Path: Delivered-To: svn-src-head@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id 7AB8EE0407A; Wed, 6 Sep 2017 13:56:20 +0000 (UTC) (envelope-from hselasky@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id E7CB02585; Wed, 6 Sep 2017 13:56:19 +0000 (UTC) (envelope-from hselasky@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id v86DuIXd074935; Wed, 6 Sep 2017 13:56:18 GMT (envelope-from hselasky@FreeBSD.org) Received: (from hselasky@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id v86DuIjQ074932; Wed, 6 Sep 2017 13:56:18 GMT (envelope-from hselasky@FreeBSD.org) Message-Id: <201709061356.v86DuIjQ074932@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: hselasky set sender to hselasky@FreeBSD.org using -f From: Hans Petter Selasky Date: Wed, 6 Sep 2017 13:56:18 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r323219 - in head/sys: net netinet X-SVN-Group: head X-SVN-Commit-Author: hselasky X-SVN-Commit-Paths: in head/sys: net netinet X-SVN-Commit-Revision: 323219 X-SVN-Commit-Repository: base MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 06 Sep 2017 13:56:20 -0000 Author: hselasky Date: Wed Sep 6 13:56:18 2017 New Revision: 323219 URL: https://svnweb.freebsd.org/changeset/base/323219 Log: Add support for generic backpressure indicator for ratelimited transmit queues aswell as non-ratelimited ones. Add the required structure bits in order to support a backpressure indication with ratelimited connections aswell as non-ratelimited ones. The backpressure indicator is a value between zero and 65535 inclusivly, indicating if the destination transmit queue is empty or full respectivly. Applications can use this value as a decision point for when to stop transmitting data to avoid endless ENOBUFS error codes upon transmitting an mbuf. This indicator is also useful to reduce the latency for ratelimited queues. Reviewed by: gallatin, kib, gnn Differential Revision: https://reviews.freebsd.org/D11518 Sponsored by: Mellanox Technologies Modified: head/sys/net/if_var.h head/sys/netinet/in_pcb.c head/sys/netinet/in_pcb.h Modified: head/sys/net/if_var.h ============================================================================== --- head/sys/net/if_var.h Wed Sep 6 13:10:33 2017 (r323218) +++ head/sys/net/if_var.h Wed Sep 6 13:56:18 2017 (r323219) @@ -183,7 +183,8 @@ struct if_encap_req { struct m_snd_tag; #define IF_SND_TAG_TYPE_RATE_LIMIT 0 -#define IF_SND_TAG_TYPE_MAX 1 +#define IF_SND_TAG_TYPE_UNLIMITED 1 +#define IF_SND_TAG_TYPE_MAX 2 struct if_snd_tag_alloc_header { uint32_t type; /* send tag type, see IF_SND_TAG_XXX */ @@ -198,19 +199,26 @@ struct if_snd_tag_alloc_rate_limit { struct if_snd_tag_rate_limit_params { uint64_t max_rate; /* in bytes/s */ + uint32_t queue_level; /* 0 (empty) .. 65535 (full) */ +#define IF_SND_QUEUE_LEVEL_MIN 0 +#define IF_SND_QUEUE_LEVEL_MAX 65535 + uint32_t reserved; /* padding */ }; union if_snd_tag_alloc_params { struct if_snd_tag_alloc_header hdr; struct if_snd_tag_alloc_rate_limit rate_limit; + struct if_snd_tag_alloc_rate_limit unlimited; }; union if_snd_tag_modify_params { struct if_snd_tag_rate_limit_params rate_limit; + struct if_snd_tag_rate_limit_params unlimited; }; union if_snd_tag_query_params { struct if_snd_tag_rate_limit_params rate_limit; + struct if_snd_tag_rate_limit_params unlimited; }; typedef int (if_snd_tag_alloc_t)(struct ifnet *, union if_snd_tag_alloc_params *, Modified: head/sys/netinet/in_pcb.c ============================================================================== --- head/sys/netinet/in_pcb.c Wed Sep 6 13:10:33 2017 (r323218) +++ head/sys/netinet/in_pcb.c Wed Sep 6 13:56:18 2017 (r323219) @@ -2797,6 +2797,35 @@ in_pcbquery_txrtlmt(struct inpcb *inp, uint32_t *p_max } /* + * Query existing TX queue level based on the existing + * "inp->inp_snd_tag", if any. + */ +int +in_pcbquery_txrlevel(struct inpcb *inp, uint32_t *p_txqueue_level) +{ + union if_snd_tag_query_params params = { }; + struct m_snd_tag *mst; + struct ifnet *ifp; + int error; + + mst = inp->inp_snd_tag; + if (mst == NULL) + return (EINVAL); + + ifp = mst->ifp; + if (ifp == NULL) + return (EINVAL); + + if (ifp->if_snd_tag_query == NULL) + return (EOPNOTSUPP); + + error = ifp->if_snd_tag_query(mst, ¶ms); + if (error == 0 && p_txqueue_level != NULL) + *p_txqueue_level = params.rate_limit.queue_level; + return (error); +} + +/* * Allocate a new TX rate limit send tag from the network interface * given by the "ifp" argument and save it in "inp->inp_snd_tag": */ @@ -2805,7 +2834,8 @@ in_pcbattach_txrtlmt(struct inpcb *inp, struct ifnet * uint32_t flowtype, uint32_t flowid, uint32_t max_pacing_rate) { union if_snd_tag_alloc_params params = { - .rate_limit.hdr.type = IF_SND_TAG_TYPE_RATE_LIMIT, + .rate_limit.hdr.type = (max_pacing_rate == -1U) ? + IF_SND_TAG_TYPE_UNLIMITED : IF_SND_TAG_TYPE_RATE_LIMIT, .rate_limit.hdr.flowid = flowid, .rate_limit.hdr.flowtype = flowtype, .rate_limit.max_rate = max_pacing_rate, Modified: head/sys/netinet/in_pcb.h ============================================================================== --- head/sys/netinet/in_pcb.h Wed Sep 6 13:10:33 2017 (r323218) +++ head/sys/netinet/in_pcb.h Wed Sep 6 13:56:18 2017 (r323219) @@ -761,6 +761,7 @@ int in_pcbattach_txrtlmt(struct inpcb *, struct ifnet void in_pcbdetach_txrtlmt(struct inpcb *); int in_pcbmodify_txrtlmt(struct inpcb *, uint32_t); int in_pcbquery_txrtlmt(struct inpcb *, uint32_t *); +int in_pcbquery_txrlevel(struct inpcb *, uint32_t *); void in_pcboutput_txrtlmt(struct inpcb *, struct ifnet *, struct mbuf *); void in_pcboutput_eagain(struct inpcb *); #endif