svn commit: r307838 - head/sys/dev/hyperv/netvsc

Sepherosa Ziehau sephe at FreeBSD.org
Mon Oct 24 03:26:36 UTC 2016


Author: sephe
Date: Mon Oct 24 03:26:34 2016
New Revision: 307838
URL: https://svnweb.freebsd.org/changeset/base/307838

Log:
  hyperv/hn: Move chimney buffer index and size to txdesc.
  
  All RNDIS control messages have used SG list for a while.  This makes
  the send context suitable for further refactoring.
  
  MFC after:	1 week
  Sponsored by:	Microsoft
  Differential Revision:	https://reviews.freebsd.org/D8308

Modified:
  head/sys/dev/hyperv/netvsc/hv_net_vsc.c
  head/sys/dev/hyperv/netvsc/hv_net_vsc.h
  head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c
  head/sys/dev/hyperv/netvsc/hv_rndis_filter.c
  head/sys/dev/hyperv/netvsc/if_hnvar.h

Modified: head/sys/dev/hyperv/netvsc/hv_net_vsc.c
==============================================================================
--- head/sys/dev/hyperv/netvsc/hv_net_vsc.c	Mon Oct 24 01:29:46 2016	(r307837)
+++ head/sys/dev/hyperv/netvsc/hv_net_vsc.c	Mon Oct 24 03:26:34 2016	(r307838)
@@ -117,7 +117,7 @@ hn_nvs_xact_execute(struct hn_softc *sc,
 	/*
 	 * Execute the xact setup by the caller.
 	 */
-	hn_send_ctx_init_simple(&sndc, hn_nvs_sent_xact, xact);
+	hn_send_ctx_init(&sndc, hn_nvs_sent_xact, xact);
 
 	vmbus_xact_activate(xact);
 	error = hn_nvs_send(sc->hn_prichan, VMBUS_CHANPKT_FLAG_RC,
@@ -669,34 +669,6 @@ hn_chim_free(struct hn_softc *sc, uint32
 	atomic_clear_long(&sc->hn_chim_bmap[idx], mask);
 }
 
-/*
- * Net VSC on send
- * Sends a packet on the specified Hyper-V device.
- * Returns 0 on success, non-zero on failure.
- */
-int
-hv_nv_on_send(struct vmbus_channel *chan, uint32_t rndis_mtype,
-    struct hn_send_ctx *sndc, struct vmbus_gpa *gpa, int gpa_cnt)
-{
-	struct hn_nvs_rndis rndis;
-	int ret;
-
-	rndis.nvs_type = HN_NVS_TYPE_RNDIS;
-	rndis.nvs_rndis_mtype = rndis_mtype;
-	rndis.nvs_chim_idx = sndc->hn_chim_idx;
-	rndis.nvs_chim_sz = sndc->hn_chim_sz;
-
-	if (gpa_cnt) {
-		ret = hn_nvs_send_sglist(chan, gpa, gpa_cnt,
-		    &rndis, sizeof(rndis), sndc);
-	} else {
-		ret = hn_nvs_send(chan, VMBUS_CHANPKT_FLAG_RC,
-		    &rndis, sizeof(rndis), sndc);
-	}
-
-	return (ret);
-}
-
 int
 hn_nvs_alloc_subchans(struct hn_softc *sc, int *nsubch0)
 {

Modified: head/sys/dev/hyperv/netvsc/hv_net_vsc.h
==============================================================================
--- head/sys/dev/hyperv/netvsc/hv_net_vsc.h	Mon Oct 24 01:29:46 2016	(r307837)
+++ head/sys/dev/hyperv/netvsc/hv_net_vsc.h	Mon Oct 24 03:26:34 2016	(r307838)
@@ -104,8 +104,8 @@ struct vmbus_channel;
 #define HN_XACT_REQ_SIZE		(HN_XACT_REQ_PGCNT * PAGE_SIZE)
 #define HN_XACT_RESP_SIZE		(HN_XACT_RESP_PGCNT * PAGE_SIZE)
 
-#ifndef HN_USE_TXDESC_BUFRING
 struct hn_txdesc;
+#ifndef HN_USE_TXDESC_BUFRING
 SLIST_HEAD(hn_txdesc_list, hn_txdesc);
 #else
 struct buf_ring;
@@ -179,6 +179,7 @@ struct hn_tx_ring {
 	bus_dma_tag_t	hn_tx_data_dtag;
 	uint64_t	hn_csum_assist;
 
+	int		(*hn_sendpkt)(struct hn_tx_ring *, struct hn_txdesc *);
 	int		hn_suspended;
 	int		hn_gpa_cnt;
 	struct vmbus_gpa hn_gpa[NETVSC_PACKET_MAXPAGE];
@@ -276,13 +277,5 @@ struct hn_softc {
 #define HN_LINK_FLAG_LINKUP		0x0001
 #define HN_LINK_FLAG_NETCHG		0x0002
 
-/*
- * Externs
- */
-struct hn_send_ctx;
-
-int hv_nv_on_send(struct vmbus_channel *chan, uint32_t rndis_mtype,
-	struct hn_send_ctx *sndc, struct vmbus_gpa *gpa, int gpa_cnt);
-
 #endif  /* __HV_NET_VSC_H__ */
 

Modified: head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c
==============================================================================
--- head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c	Mon Oct 24 01:29:46 2016	(r307837)
+++ head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c	Mon Oct 24 03:26:34 2016	(r307838)
@@ -169,6 +169,8 @@ struct hn_txdesc {
 	int		refs;
 	uint32_t	flags;		/* HN_TXD_FLAG_ */
 	struct hn_send_ctx send_ctx;
+	uint32_t	chim_index;
+	int		chim_size;
 
 	bus_dmamap_t	data_dmap;
 
@@ -363,6 +365,8 @@ static void hn_tx_resume(struct hn_softc
 static void hn_tx_ring_qflush(struct hn_tx_ring *);
 static int netvsc_detach(device_t dev);
 static void hn_link_status(struct hn_softc *);
+static int hn_sendpkt_rndis_sglist(struct hn_tx_ring *, struct hn_txdesc *);
+static int hn_sendpkt_rndis_chim(struct hn_tx_ring *, struct hn_txdesc *);
 
 static void hn_nvs_handle_notify(struct hn_softc *sc,
 		const struct vmbus_chanpkt_hdr *pkt);
@@ -399,6 +403,57 @@ hn_set_lro_lenlim(struct hn_softc *sc, i
 }
 #endif
 
+static __inline int
+hn_nvs_send_rndis_sglist1(struct vmbus_channel *chan, uint32_t rndis_mtype,
+    struct hn_send_ctx *sndc, struct vmbus_gpa *gpa, int gpa_cnt)
+{
+	struct hn_nvs_rndis rndis;
+
+	rndis.nvs_type = HN_NVS_TYPE_RNDIS;
+	rndis.nvs_rndis_mtype = rndis_mtype;
+	rndis.nvs_chim_idx = HN_NVS_CHIM_IDX_INVALID;
+	rndis.nvs_chim_sz = 0;
+
+	return (hn_nvs_send_sglist(chan, gpa, gpa_cnt,
+	    &rndis, sizeof(rndis), sndc));
+}
+
+int
+hn_nvs_send_rndis_ctrl(struct vmbus_channel *chan,
+    struct hn_send_ctx *sndc, struct vmbus_gpa *gpa, int gpa_cnt)
+{
+
+	return hn_nvs_send_rndis_sglist1(chan, HN_NVS_RNDIS_MTYPE_CTRL,
+	    sndc, gpa, gpa_cnt);
+}
+
+static int
+hn_sendpkt_rndis_sglist(struct hn_tx_ring *txr, struct hn_txdesc *txd)
+{
+
+	KASSERT(txd->chim_index == HN_NVS_CHIM_IDX_INVALID &&
+	    txd->chim_size == 0, ("invalid rndis sglist txd"));
+	return (hn_nvs_send_rndis_sglist1(txr->hn_chan, HN_NVS_RNDIS_MTYPE_DATA,
+	    &txd->send_ctx, txr->hn_gpa, txr->hn_gpa_cnt));
+}
+
+static int
+hn_sendpkt_rndis_chim(struct hn_tx_ring *txr, struct hn_txdesc *txd)
+{
+	struct hn_nvs_rndis rndis;
+
+	KASSERT(txd->chim_index != HN_NVS_CHIM_IDX_INVALID &&
+	    txd->chim_size > 0, ("invalid rndis chim txd"));
+
+	rndis.nvs_type = HN_NVS_TYPE_RNDIS;
+	rndis.nvs_rndis_mtype = HN_NVS_RNDIS_MTYPE_DATA;
+	rndis.nvs_chim_idx = txd->chim_index;
+	rndis.nvs_chim_sz = txd->chim_size;
+
+	return (hn_nvs_send(txr->hn_chan, VMBUS_CHANPKT_FLAG_RC,
+	    &rndis, sizeof(rndis), &txd->send_ctx));
+}
+
 static int
 hn_get_txswq_depth(const struct hn_tx_ring *txr)
 {
@@ -1038,8 +1093,8 @@ hn_tx_done(struct hn_send_ctx *sndc, str
 	struct hn_txdesc *txd = sndc->hn_cbarg;
 	struct hn_tx_ring *txr;
 
-	if (sndc->hn_chim_idx != HN_NVS_CHIM_IDX_INVALID)
-		hn_chim_free(sc, sndc->hn_chim_idx);
+	if (txd->chim_index != HN_NVS_CHIM_IDX_INVALID)
+		hn_chim_free(sc, txd->chim_index);
 
 	txr = txd->txr;
 	KASSERT(txr->hn_chan == chan,
@@ -1096,9 +1151,8 @@ hn_encap(struct hn_tx_ring *txr, struct 
 	int error, nsegs, i;
 	struct mbuf *m_head = *m_head0;
 	struct rndis_packet_msg *pkt;
-	uint32_t send_buf_section_idx;
-	int send_buf_section_size, pktlen;
 	uint32_t *pi_data;
+	int pktlen;
 
 	/*
 	 * extension points to the area reserved for the
@@ -1211,18 +1265,19 @@ hn_encap(struct hn_tx_ring *txr, struct 
 	 */
 	if (pkt->rm_len < txr->hn_chim_size) {
 		txr->hn_tx_chimney_tried++;
-		send_buf_section_idx = hn_chim_alloc(txr->hn_sc);
-		if (send_buf_section_idx != HN_NVS_CHIM_IDX_INVALID) {
+		txd->chim_index = hn_chim_alloc(txr->hn_sc);
+		if (txd->chim_index != HN_NVS_CHIM_IDX_INVALID) {
 			uint8_t *dest = txr->hn_sc->hn_chim +
-			    (send_buf_section_idx * txr->hn_sc->hn_chim_szmax);
+			    (txd->chim_index * txr->hn_sc->hn_chim_szmax);
 
 			memcpy(dest, pkt, pktlen);
 			dest += pktlen;
 			m_copydata(m_head, 0, m_head->m_pkthdr.len, dest);
 
-			send_buf_section_size = pkt->rm_len;
+			txd->chim_size = pkt->rm_len;
 			txr->hn_gpa_cnt = 0;
 			txr->hn_tx_chimney++;
+			txr->hn_sendpkt = hn_sendpkt_rndis_chim;
 			goto done;
 		}
 	}
@@ -1267,14 +1322,14 @@ hn_encap(struct hn_tx_ring *txr, struct 
 		gpa->gpa_len = segs[i].ds_len;
 	}
 
-	send_buf_section_idx = HN_NVS_CHIM_IDX_INVALID;
-	send_buf_section_size = 0;
+	txd->chim_index = HN_NVS_CHIM_IDX_INVALID;
+	txd->chim_size = 0;
+	txr->hn_sendpkt = hn_sendpkt_rndis_sglist;
 done:
 	txd->m = m_head;
 
 	/* Set the completion routine */
-	hn_send_ctx_init(&txd->send_ctx, hn_tx_done, txd,
-	    send_buf_section_idx, send_buf_section_size);
+	hn_send_ctx_init(&txd->send_ctx, hn_tx_done, txd);
 
 	return 0;
 }
@@ -1294,8 +1349,7 @@ again:
 	 * Make sure that txd is not freed before ETHER_BPF_MTAP.
 	 */
 	hn_txdesc_hold(txd);
-	error = hv_nv_on_send(txr->hn_chan, HN_NVS_RNDIS_MTYPE_DATA,
-	    &txd->send_ctx, txr->hn_gpa, txr->hn_gpa_cnt);
+	error = txr->hn_sendpkt(txr, txd);
 	if (!error) {
 		ETHER_BPF_MTAP(ifp, txd->m);
 		if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1);

Modified: head/sys/dev/hyperv/netvsc/hv_rndis_filter.c
==============================================================================
--- head/sys/dev/hyperv/netvsc/hv_rndis_filter.c	Mon Oct 24 01:29:46 2016	(r307837)
+++ head/sys/dev/hyperv/netvsc/hv_rndis_filter.c	Mon Oct 24 03:26:34 2016	(r307838)
@@ -585,8 +585,7 @@ hn_rndis_xact_exec1(struct hn_softc *sc,
 	 * message.
 	 */
 	vmbus_xact_activate(xact);
-	error = hv_nv_on_send(sc->hn_prichan, HN_NVS_RNDIS_MTYPE_CTRL, sndc,
-	    gpa, gpa_cnt);
+	error = hn_nvs_send_rndis_ctrl(sc->hn_prichan, sndc, gpa, gpa_cnt);
 	if (error) {
 		vmbus_xact_deactivate(xact);
 		if_printf(sc->hn_ifp, "RNDIS ctrl send failed: %d\n", error);
@@ -1165,7 +1164,7 @@ hn_rndis_halt(struct hn_softc *sc)
 	halt->rm_rid = hn_rndis_rid(sc);
 
 	/* No RNDIS completion; rely on NVS message send completion */
-	hn_send_ctx_init_simple(&sndc, hn_nvs_sent_xact, xact);
+	hn_send_ctx_init(&sndc, hn_nvs_sent_xact, xact);
 	hn_rndis_xact_exec1(sc, xact, sizeof(*halt), &sndc, &comp_len);
 
 	vmbus_xact_put(xact);

Modified: head/sys/dev/hyperv/netvsc/if_hnvar.h
==============================================================================
--- head/sys/dev/hyperv/netvsc/if_hnvar.h	Mon Oct 24 01:29:46 2016	(r307837)
+++ head/sys/dev/hyperv/netvsc/if_hnvar.h	Mon Oct 24 03:26:34 2016	(r307838)
@@ -46,8 +46,6 @@ typedef void		(*hn_sent_callback_t)
 struct hn_send_ctx {
 	hn_sent_callback_t	hn_cb;
 	void			*hn_cbarg;
-	uint32_t		hn_chim_idx;
-	int			hn_chim_sz;
 };
 
 struct rndis_hash_info;
@@ -66,31 +64,18 @@ struct hn_recvinfo {
 	uint32_t			hash_value;
 };
 
-#define HN_SEND_CTX_INITIALIZER(cb, cbarg)		\
-{							\
-	.hn_cb		= cb,				\
-	.hn_cbarg	= cbarg,			\
-	.hn_chim_idx	= HN_NVS_CHIM_IDX_INVALID,	\
-	.hn_chim_sz	= 0				\
+#define HN_SEND_CTX_INITIALIZER(cb, cbarg)	\
+{						\
+	.hn_cb		= cb,			\
+	.hn_cbarg	= cbarg			\
 }
 
 static __inline void
-hn_send_ctx_init(struct hn_send_ctx *sndc, hn_sent_callback_t cb,
-    void *cbarg, uint32_t chim_idx, int chim_sz)
+hn_send_ctx_init(struct hn_send_ctx *sndc, hn_sent_callback_t cb, void *cbarg)
 {
 
 	sndc->hn_cb = cb;
 	sndc->hn_cbarg = cbarg;
-	sndc->hn_chim_idx = chim_idx;
-	sndc->hn_chim_sz = chim_sz;
-}
-
-static __inline void
-hn_send_ctx_init_simple(struct hn_send_ctx *sndc, hn_sent_callback_t cb,
-    void *cbarg)
-{
-
-	hn_send_ctx_init(sndc, cb, cbarg, HN_NVS_CHIM_IDX_INVALID, 0);
 }
 
 static __inline int
@@ -134,6 +119,9 @@ void		hn_nvs_detach(struct hn_softc *sc)
 int		hn_nvs_alloc_subchans(struct hn_softc *sc, int *nsubch);
 void		hn_nvs_sent_xact(struct hn_send_ctx *sndc, struct hn_softc *sc,
 		    struct vmbus_channel *chan, const void *data, int dlen);
+int		hn_nvs_send_rndis_ctrl(struct vmbus_channel *chan,
+		    struct hn_send_ctx *sndc, struct vmbus_gpa *gpa,
+		    int gpa_cnt);
 
 int		hn_rxpkt(struct hn_rx_ring *rxr, const void *data, int dlen,
 		    const struct hn_recvinfo *info);


More information about the svn-src-all mailing list