Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 21 Jul 2015 07:20:03 +0000 (UTC)
From:      Roger Pau Monné <royger@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org
Subject:   svn commit: r285737 - stable/10/sys/dev/xen/netfront
Message-ID:  <201507210720.t6L7K3Ol008058@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: royger
Date: Tue Jul 21 07:20:02 2015
New Revision: 285737
URL: https://svnweb.freebsd.org/changeset/base/285737

Log:
  MFC: r285089
  
  netfront: preserve configuration across migrations
  
  Approved by: re (gjb)

Modified:
  stable/10/sys/dev/xen/netfront/netfront.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/sys/dev/xen/netfront/netfront.c
==============================================================================
--- stable/10/sys/dev/xen/netfront/netfront.c	Tue Jul 21 06:48:36 2015	(r285736)
+++ stable/10/sys/dev/xen/netfront/netfront.c	Tue Jul 21 07:20:02 2015	(r285737)
@@ -42,6 +42,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/queue.h>
 #include <sys/lock.h>
 #include <sys/sx.h>
+#include <sys/limits.h>
 
 #include <net/if.h>
 #include <net/if_arp.h>
@@ -286,6 +287,8 @@ struct netfront_info {
 	multicall_entry_t	rx_mcl[NET_RX_RING_SIZE+1];
 	mmu_update_t		rx_mmu[NET_RX_RING_SIZE];
 	struct ifmedia		sc_media;
+
+	bool			xn_resume;
 };
 
 #define rx_mbufs xn_cdata.xn_rx_chain
@@ -501,6 +504,7 @@ netfront_resume(device_t dev)
 {
 	struct netfront_info *info = device_get_softc(dev);
 
+	info->xn_resume = true;
 	netif_disconnect_backend(info);
 	return (0);
 }
@@ -2000,18 +2004,33 @@ xn_query_features(struct netfront_info *
 static int
 xn_configure_features(struct netfront_info *np)
 {
-	int err;
+	int err, cap_enabled;
 
 	err = 0;
+
+	if (np->xn_resume &&
+	    ((np->xn_ifp->if_capenable & np->xn_ifp->if_capabilities)
+	    == np->xn_ifp->if_capenable)) {
+		/* Current options are available, no need to do anything. */
+		return (0);
+	}
+
+	/* Try to preserve as many options as possible. */
+	if (np->xn_resume)
+		cap_enabled = np->xn_ifp->if_capenable;
+	else
+		cap_enabled = UINT_MAX;
+
 #if __FreeBSD_version >= 700000 && (defined(INET) || defined(INET6))
-	if ((np->xn_ifp->if_capenable & IFCAP_LRO) != 0)
+	if ((np->xn_ifp->if_capenable & IFCAP_LRO) == (cap_enabled & IFCAP_LRO))
 		tcp_lro_free(&np->xn_lro);
 #endif
     	np->xn_ifp->if_capenable =
-	    np->xn_ifp->if_capabilities & ~(IFCAP_LRO|IFCAP_TSO4);
+	    np->xn_ifp->if_capabilities & ~(IFCAP_LRO|IFCAP_TSO4) & cap_enabled;
 	np->xn_ifp->if_hwassist &= ~CSUM_TSO;
 #if __FreeBSD_version >= 700000 && (defined(INET) || defined(INET6))
-	if (xn_enable_lro && (np->xn_ifp->if_capabilities & IFCAP_LRO) != 0) {
+	if (xn_enable_lro && (np->xn_ifp->if_capabilities & IFCAP_LRO) ==
+	    (cap_enabled & IFCAP_LRO)) {
 		err = tcp_lro_init(&np->xn_lro);
 		if (err) {
 			device_printf(np->xbdev, "LRO initialization failed\n");
@@ -2020,7 +2039,8 @@ xn_configure_features(struct netfront_in
 			np->xn_ifp->if_capenable |= IFCAP_LRO;
 		}
 	}
-	if ((np->xn_ifp->if_capabilities & IFCAP_TSO4) != 0) {
+	if ((np->xn_ifp->if_capabilities & IFCAP_TSO4) ==
+	    (cap_enabled & IFCAP_TSO4)) {
 		np->xn_ifp->if_capenable |= IFCAP_TSO4;
 		np->xn_ifp->if_hwassist |= CSUM_TSO;
 	}



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201507210720.t6L7K3Ol008058>