From owner-svn-soc-all@freebsd.org Mon Jun 27 09:33:18 2016 Return-Path: Delivered-To: svn-soc-all@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 EC6A5B84EED for ; Mon, 27 Jun 2016 09:33:18 +0000 (UTC) (envelope-from vincenzo@FreeBSD.org) Received: from socsvn.freebsd.org (socsvn.freebsd.org [IPv6:2001:1900:2254:206a::50:2]) (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 E00E8213D for ; Mon, 27 Jun 2016 09:33:18 +0000 (UTC) (envelope-from vincenzo@FreeBSD.org) Received: from socsvn.freebsd.org ([127.0.1.124]) by socsvn.freebsd.org (8.15.2/8.15.2) with ESMTP id u5R9XITV025907 for ; Mon, 27 Jun 2016 09:33:18 GMT (envelope-from vincenzo@FreeBSD.org) Received: (from www@localhost) by socsvn.freebsd.org (8.15.2/8.15.2/Submit) id u5R9XILq025874 for svn-soc-all@FreeBSD.org; Mon, 27 Jun 2016 09:33:18 GMT (envelope-from vincenzo@FreeBSD.org) Date: Mon, 27 Jun 2016 09:33:18 GMT Message-Id: <201606270933.u5R9XILq025874@socsvn.freebsd.org> X-Authentication-Warning: socsvn.freebsd.org: www set sender to vincenzo@FreeBSD.org using -f From: vincenzo@FreeBSD.org To: svn-soc-all@FreeBSD.org Subject: socsvn commit: r305574 - soc2016/vincenzo/head/sys/dev/netmap MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-soc-all@freebsd.org X-Mailman-Version: 2.1.22 Precedence: list List-Id: SVN commit messages for the entire Summer of Code repository List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 27 Jun 2016 09:33:19 -0000 Author: vincenzo Date: Mon Jun 27 09:33:17 2016 New Revision: 305574 URL: http://svnweb.FreeBSD.org/socsvn/?view=rev&rev=305574 Log: freebsd: ptnet_transmit: handle multiple mbufs Modified: soc2016/vincenzo/head/sys/dev/netmap/if_ptnet.c Modified: soc2016/vincenzo/head/sys/dev/netmap/if_ptnet.c ============================================================================== --- soc2016/vincenzo/head/sys/dev/netmap/if_ptnet.c Mon Jun 27 09:33:05 2016 (r305573) +++ soc2016/vincenzo/head/sys/dev/netmap/if_ptnet.c Mon Jun 27 09:33:17 2016 (r305574) @@ -793,6 +793,7 @@ struct netmap_ring *ring; struct netmap_slot *slot; struct ptnet_queue *pq; + unsigned int prev_head; unsigned int head; unsigned int lim; struct mbuf *mf; @@ -839,75 +840,88 @@ nmbuf = NMB(na, slot); nmbuf_bytes = 0; - m = drbr_peek(ifp, pq->bufring); - if (!m) { - device_printf(sc->dev, "%s: Empty drbr\n", __func__); - goto out; - } + while (head != ring->tail) { + m = drbr_peek(ifp, pq->bufring); + if (!m) { + break; + } - if (head == ring->tail) { - device_printf(sc->dev, "%s: Drop, no free slots\n", __func__); - drbr_putback(ifp, pq->bufring, m); - ptring->guest_need_kick = 1; - goto out; - } + for (prev_head = head, mf = m; mf; mf = mf->m_next) { + uint8_t *mdata = mf->m_data; + int mlen = mf->m_len; - drbr_advance(ifp, pq->bufring); + for (;;) { + int copy = NETMAP_BUF_SIZE(na) - nmbuf_bytes; - for (mf = m; mf; mf = mf->m_next) { - uint8_t *mdata = mf->m_data; - int mlen = mf->m_len; + if (mlen < copy) { + copy = mlen; + } + memcpy(nmbuf, mdata, copy); - for (;;) { - int copy = NETMAP_BUF_SIZE(na) - nmbuf_bytes; + mdata += copy; + mlen -= copy; + nmbuf += copy; + nmbuf_bytes += copy; - if (mlen < copy) { - copy = mlen; - } - memcpy(nmbuf, mdata, copy); + if (!mlen) { + break; + } - mdata += copy; - mlen -= copy; - nmbuf += copy; - nmbuf_bytes += copy; + slot->len = nmbuf_bytes; + slot->flags = NS_MOREFRAG; - if (!mlen) { - break; + head = nm_next(head, lim); + if (head == ring->tail) { + /* Run out of slots while processing + * a packet. Reset head to the previous + * position and requeue the mbuf. */ + device_printf(sc->dev, "%s: Drop, " + " no free slots\n", + __func__); + head = prev_head; + drbr_putback(ifp, pq->bufring, m); + goto escape; + } + slot = ring->slot + head; + nmbuf = NMB(na, slot); + nmbuf_bytes = 0; } - - slot->len = nmbuf_bytes; - slot->flags = NS_MOREFRAG; - head = nm_next(head, lim); - slot = ring->slot + head; - nmbuf = NMB(na, slot); - nmbuf_bytes = 0; } - } - m_freem(m); + /* Complete last slot and update head. */ + slot->len = nmbuf_bytes; + slot->flags = 0; + head = nm_next(head, lim); - /* Complete last slot and update head. */ - slot->len = nmbuf_bytes; - slot->flags = 0; - ring->head = ring->cur = nm_next(head, lim); + /* Consume the packet just processed. */ + drbr_advance(ifp, pq->bufring); + m_freem(m); + } +escape: + if (head != ring->head) { + /* Some packets have been pushed to the netmap ring. We have + * to tell the host to process the new packets, updating cur + * and head in the CSB. */ + ring->head = ring->cur = head; - /* nm_txsync_prologue */ - kring->rcur = kring->rhead = ring->head; + /* nm_txsync_prologue */ + kring->rcur = kring->rhead = ring->head; - /* Tell the host to process the new packets, updating cur and - * head in the CSB. */ - ptnetmap_guest_write_kring_csb(ptring, kring->rcur, kring->rhead); + ptnetmap_guest_write_kring_csb(ptring, kring->rcur, kring->rhead); - /* Kick the host if needed. */ - if (NM_ACCESS_ONCE(ptring->host_need_kick)) { - ptring->sync_flags = NAF_FORCE_RECLAIM; - bus_write_4(sc->iomem, pq->kick, 0); + /* Kick the host if needed. */ + if (NM_ACCESS_ONCE(ptring->host_need_kick)) { + ptring->sync_flags = NAF_FORCE_RECLAIM; + bus_write_4(sc->iomem, pq->kick, 0); + } } - if (0) { + if (head == ring->tail) { + /* Reactivate the interrupts so that we can be notified + * when some netmap slots are made available by the host. */ ptring->guest_need_kick = 1; } -out: + PTNET_Q_UNLOCK(pq); return 0;