Message ID | 1453488486-12176-5-git-send-email-stuart.haslam@linaro.org |
---|---|
State | New |
Headers | show |
On Mon, Jan 25, 2016 at 03:15:49PM +0000, Elo, Matias (Nokia - FI/Espoo) wrote: > The same functionality is already implemented in API-NEXT branch. Is this patch mandatory for the whole set? > > -Matias > Without this the validation test in 5/5 fails so I can't just drop it from this series without also dropping 5/5, and that would partly negate the purpose of the series. I'll merge the series to API-NEXT and resend without this patch. > > -----Original Message----- > > From: lng-odp [mailto:lng-odp-bounces@lists.linaro.org] On Behalf Of EXT Stuart > > Haslam > > Sent: Friday, January 22, 2016 8:48 PM > > To: lng-odp@lists.linaro.org > > Subject: [lng-odp] [PATCHv2 4/5] linux-generic: netmap: support segmented > > packets > > > > Replace the nm_inject() helper with our own version so that > > odp_packet_copydata_out() can be used as this understands segmented > > packets. > > > > Signed-off-by: Stuart Haslam <stuart.haslam@linaro.org> > > --- > > platform/linux-generic/pktio/netmap.c | 57 > > ++++++++++++++++++++++++++++++++--- > > 1 file changed, 52 insertions(+), 5 deletions(-) > > > > diff --git a/platform/linux-generic/pktio/netmap.c b/platform/linux- > > generic/pktio/netmap.c > > index 639afa8..b7547e1 100644 > > --- a/platform/linux-generic/pktio/netmap.c > > +++ b/platform/linux-generic/pktio/netmap.c > > @@ -308,23 +308,70 @@ static int netmap_recv(pktio_entry_t *pktio_entry, > > odp_packet_t pkt_table[], > > return num_rx; > > } > > > > +static struct netmap_ring *netmap_tx_ring(struct nm_desc *d) > > +{ > > + unsigned c, n = d->last_tx_ring - d->first_tx_ring + 1; > > + > > + for (c = 0; c < n ; c++) { > > + struct netmap_ring *ring; > > + unsigned ri = d->cur_tx_ring + c; > > + > > + if (ri > d->last_tx_ring) > > + ri = d->first_tx_ring; > > + ring = NETMAP_TXRING(d->nifp, ri); > > + if (nm_ring_empty(ring)) > > + continue; > > + > > + return ring; > > + } > > + > > + return NULL; > > +} > > + > > +static int netmap_inject(struct nm_desc *d, odp_packet_t pkt) > > +{ > > + struct netmap_ring *ring; > > + unsigned i; > > + uint32_t pkt_len = odp_packet_len(pkt); > > + uint32_t offset = 0; > > + char *buf; > > + > > + ring = netmap_tx_ring(d); > > + if (!ring) > > + return 0; > > + > > + if (pkt_len > ring->nr_buf_size) { > > + __odp_errno = -EMSGSIZE; > > + return 0; > > + } > > + > > + i = ring->cur; > > + ring->slot[i].flags = 0; > > + ring->slot[i].len = pkt_len; > > + buf = NETMAP_BUF(ring, ring->slot[i].buf_idx); > > + > > + if (odp_packet_copydata_out(pkt, offset, pkt_len, buf)) > > + return 0; > > + > > + ring->cur = nm_ring_next(ring, i); > > + ring->head = ring->cur; > > + > > + return 1; > > +} > > + > > static int netmap_send(pktio_entry_t *pktio_entry, odp_packet_t pkt_table[], > > unsigned num) > > { > > struct pollfd polld; > > struct nm_desc *nm_desc = pktio_entry->s.pkt_nm.tx_desc; > > unsigned i, nb_tx; > > - uint8_t *frame; > > - uint32_t frame_len; > > > > polld.fd = nm_desc->fd; > > polld.events = POLLOUT; > > > > for (nb_tx = 0; nb_tx < num; nb_tx++) { > > - frame_len = 0; > > - frame = odp_packet_l2_ptr(pkt_table[nb_tx], &frame_len); > > for (i = 0; i < NM_INJECT_RETRIES; i++) { > > - if (nm_inject(nm_desc, frame, frame_len) == 0) > > + if (netmap_inject(nm_desc, pkt_table[nb_tx]) == 0) > > poll(&polld, 1, 0); > > else > > break; > > -- > > 2.1.1 > >
diff --git a/platform/linux-generic/pktio/netmap.c b/platform/linux-generic/pktio/netmap.c index 639afa8..b7547e1 100644 --- a/platform/linux-generic/pktio/netmap.c +++ b/platform/linux-generic/pktio/netmap.c @@ -308,23 +308,70 @@ static int netmap_recv(pktio_entry_t *pktio_entry, odp_packet_t pkt_table[], return num_rx; } +static struct netmap_ring *netmap_tx_ring(struct nm_desc *d) +{ + unsigned c, n = d->last_tx_ring - d->first_tx_ring + 1; + + for (c = 0; c < n ; c++) { + struct netmap_ring *ring; + unsigned ri = d->cur_tx_ring + c; + + if (ri > d->last_tx_ring) + ri = d->first_tx_ring; + ring = NETMAP_TXRING(d->nifp, ri); + if (nm_ring_empty(ring)) + continue; + + return ring; + } + + return NULL; +} + +static int netmap_inject(struct nm_desc *d, odp_packet_t pkt) +{ + struct netmap_ring *ring; + unsigned i; + uint32_t pkt_len = odp_packet_len(pkt); + uint32_t offset = 0; + char *buf; + + ring = netmap_tx_ring(d); + if (!ring) + return 0; + + if (pkt_len > ring->nr_buf_size) { + __odp_errno = -EMSGSIZE; + return 0; + } + + i = ring->cur; + ring->slot[i].flags = 0; + ring->slot[i].len = pkt_len; + buf = NETMAP_BUF(ring, ring->slot[i].buf_idx); + + if (odp_packet_copydata_out(pkt, offset, pkt_len, buf)) + return 0; + + ring->cur = nm_ring_next(ring, i); + ring->head = ring->cur; + + return 1; +} + static int netmap_send(pktio_entry_t *pktio_entry, odp_packet_t pkt_table[], unsigned num) { struct pollfd polld; struct nm_desc *nm_desc = pktio_entry->s.pkt_nm.tx_desc; unsigned i, nb_tx; - uint8_t *frame; - uint32_t frame_len; polld.fd = nm_desc->fd; polld.events = POLLOUT; for (nb_tx = 0; nb_tx < num; nb_tx++) { - frame_len = 0; - frame = odp_packet_l2_ptr(pkt_table[nb_tx], &frame_len); for (i = 0; i < NM_INJECT_RETRIES; i++) { - if (nm_inject(nm_desc, frame, frame_len) == 0) + if (netmap_inject(nm_desc, pkt_table[nb_tx]) == 0) poll(&polld, 1, 0); else break;
Replace the nm_inject() helper with our own version so that odp_packet_copydata_out() can be used as this understands segmented packets. Signed-off-by: Stuart Haslam <stuart.haslam@linaro.org> --- platform/linux-generic/pktio/netmap.c | 57 ++++++++++++++++++++++++++++++++--- 1 file changed, 52 insertions(+), 5 deletions(-)