Date: Wed, 21 Sep 2016 06:27:42 +0000 (UTC) From: Sepherosa Ziehau <sephe@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r306073 - head/sys/dev/hyperv/netvsc Message-ID: <201609210627.u8L6Rgg7006086@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: sephe Date: Wed Sep 21 06:27:42 2016 New Revision: 306073 URL: https://svnweb.freebsd.org/changeset/base/306073 Log: hyperv/hn: Allocate bufrings in attach DEVMETHOD. So that reinitialization, e.g. MTU change, will not fail when the system memory is excessively fragmented. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7961 Modified: head/sys/dev/hyperv/netvsc/hv_net_vsc.h head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c Modified: head/sys/dev/hyperv/netvsc/hv_net_vsc.h ============================================================================== --- head/sys/dev/hyperv/netvsc/hv_net_vsc.h Wed Sep 21 05:56:47 2016 (r306072) +++ head/sys/dev/hyperv/netvsc/hv_net_vsc.h Wed Sep 21 06:27:42 2016 (r306073) @@ -136,6 +136,9 @@ struct hn_rx_ring { /* Rarely used stuffs */ struct sysctl_oid *hn_rx_sysctl_tree; int hn_rx_flags; + + void *hn_br; /* TX/RX bufring */ + struct hyperv_dma hn_br_dma; } __aligned(CACHE_LINE_SIZE); #define HN_TRUST_HCSUM_IP 0x0001 Modified: head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c ============================================================================== --- head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c Wed Sep 21 05:56:47 2016 (r306072) +++ head/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c Wed Sep 21 06:27:42 2016 (r306073) @@ -2372,6 +2372,16 @@ hn_create_rx_data(struct hn_softc *sc, i for (i = 0; i < sc->hn_rx_ring_cnt; ++i) { struct hn_rx_ring *rxr = &sc->hn_rx_ring[i]; + rxr->hn_br = hyperv_dmamem_alloc(bus_get_dma_tag(dev), + PAGE_SIZE, 0, + NETVSC_DEVICE_RING_BUFFER_SIZE + + NETVSC_DEVICE_RING_BUFFER_SIZE, + &rxr->hn_br_dma, BUS_DMA_WAITOK); + if (rxr->hn_br == NULL) { + device_printf(dev, "allocate bufring failed\n"); + return (ENOMEM); + } + if (hn_trust_hosttcp) rxr->hn_trust_hcsum |= HN_TRUST_HCSUM_TCP; if (hn_trust_hostudp) @@ -2520,6 +2530,11 @@ hn_destroy_rx_data(struct hn_softc *sc) for (i = 0; i < sc->hn_rx_ring_cnt; ++i) { struct hn_rx_ring *rxr = &sc->hn_rx_ring[i]; + if (rxr->hn_br == NULL) + continue; + hyperv_dmamem_free(&rxr->hn_br_dma, rxr->hn_br); + rxr->hn_br = NULL; + #if defined(INET) || defined(INET6) tcp_lro_free(&rxr->hn_lro); #endif @@ -3125,6 +3140,7 @@ hn_xmit_txeof_taskfunc(void *xtxr, int p static int hn_chan_attach(struct hn_softc *sc, struct vmbus_channel *chan) { + struct vmbus_chan_br cbr; struct hn_rx_ring *rxr; struct hn_tx_ring *txr = NULL; int idx, error; @@ -3163,9 +3179,14 @@ hn_chan_attach(struct hn_softc *sc, stru /* Bind this channel to a proper CPU. */ vmbus_chan_cpu_set(chan, (sc->hn_cpu + idx) % mp_ncpus); - /* Open this channel */ - error = vmbus_chan_open(chan, NETVSC_DEVICE_RING_BUFFER_SIZE, - NETVSC_DEVICE_RING_BUFFER_SIZE, NULL, 0, hn_chan_callback, rxr); + /* + * Open this channel + */ + cbr.cbr = rxr->hn_br; + cbr.cbr_paddr = rxr->hn_br_dma.hv_paddr; + cbr.cbr_txsz = NETVSC_DEVICE_RING_BUFFER_SIZE; + cbr.cbr_rxsz = NETVSC_DEVICE_RING_BUFFER_SIZE; + error = vmbus_chan_open_br(chan, &cbr, NULL, 0, hn_chan_callback, rxr); if (error) { if_printf(sc->hn_ifp, "open chan%u failed: %d\n", vmbus_chan_id(chan), error);
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201609210627.u8L6Rgg7006086>