Quellcodebibliothek Statistik Leitseite products/sources/formale Sprachen/C/Linux/drivers/net/ethernet/microchip/lan966x/   (Open Source Betriebssystem Version 6.17.9©)  Datei vom 24.10.2025 mit Größe 2 kB image not shown  

Quelle  lan966x_xdp.c   Sprache: C

 
// SPDX-License-Identifier: GPL-2.0+

#include <linux/bpf.h>
#include <linux/bpf_trace.h>
#include <linux/filter.h>

#include "lan966x_main.h"

static int lan966x_xdp_setup(struct net_device *dev, struct netdev_bpf *xdp)
{
 struct lan966x_port *port = netdev_priv(dev);
 struct lan966x *lan966x = port->lan966x;
 struct bpf_prog *old_prog;
 bool old_xdp, new_xdp;
 int err;

 if (!lan966x->fdma) {
  NL_SET_ERR_MSG_MOD(xdp->extack,
       "Allow to set xdp only when using fdma");
  return -EOPNOTSUPP;
 }

 old_xdp = lan966x_xdp_present(lan966x);
 old_prog = xchg(&port->xdp_prog, xdp->prog);
 new_xdp = lan966x_xdp_present(lan966x);

 if (old_xdp == new_xdp)
  goto out;

 err = lan966x_fdma_reload_page_pool(lan966x);
 if (err) {
  xchg(&port->xdp_prog, old_prog);
  return err;
 }

out:
 if (old_prog)
  bpf_prog_put(old_prog);

 return 0;
}

int lan966x_xdp(struct net_device *dev, struct netdev_bpf *xdp)
{
 switch (xdp->command) {
 case XDP_SETUP_PROG:
  return lan966x_xdp_setup(dev, xdp);
 default:
  return -EINVAL;
 }
}

int lan966x_xdp_xmit(struct net_device *dev,
       int n,
       struct xdp_frame **frames,
       u32 flags)
{
 struct lan966x_port *port = netdev_priv(dev);
 int nxmit = 0;

 for (int i = 0; i < n; ++i) {
  struct xdp_frame *xdpf = frames[i];
  int err;

  err = lan966x_fdma_xmit_xdpf(port, xdpf, 0);
  if (err)
   break;

  nxmit++;
 }

 return nxmit;
}

int lan966x_xdp_run(struct lan966x_port *port, struct page *page, u32 data_len)
{
 struct bpf_prog *xdp_prog = port->xdp_prog;
 struct lan966x *lan966x = port->lan966x;
 struct xdp_buff xdp;
 u32 act;

 xdp_init_buff(&xdp, PAGE_SIZE << lan966x->rx.page_order,
        &port->xdp_rxq);
 xdp_prepare_buff(&xdp, page_address(page),
    IFH_LEN_BYTES + XDP_PACKET_HEADROOM,
    data_len - IFH_LEN_BYTES, false);
 act = bpf_prog_run_xdp(xdp_prog, &xdp);
 switch (act) {
 case XDP_PASS:
  return FDMA_PASS;
 case XDP_TX:
  return lan966x_fdma_xmit_xdpf(port, page,
           data_len - IFH_LEN_BYTES) ?
         FDMA_DROP : FDMA_TX;
 case XDP_REDIRECT:
  if (xdp_do_redirect(port->dev, &xdp, xdp_prog))
   return FDMA_DROP;

  return FDMA_REDIRECT;
 default:
  bpf_warn_invalid_xdp_action(port->dev, xdp_prog, act);
  fallthrough;
 case XDP_ABORTED:
  trace_xdp_exception(port->dev, xdp_prog, act);
  fallthrough;
 case XDP_DROP:
  return FDMA_DROP;
 }
}

bool lan966x_xdp_present(struct lan966x *lan966x)
{
 for (int p = 0; p < lan966x->num_phys_ports; ++p) {
  if (!lan966x->ports[p])
   continue;

  if (lan966x_xdp_port_present(lan966x->ports[p]))
   return true;
 }

 return false;
}

int lan966x_xdp_port_init(struct lan966x_port *port)
{
 struct lan966x *lan966x = port->lan966x;

 return xdp_rxq_info_reg(&port->xdp_rxq, port->dev, 0,
    lan966x->napi.napi_id);
}

void lan966x_xdp_port_deinit(struct lan966x_port *port)
{
 if (xdp_rxq_info_is_reg(&port->xdp_rxq))
  xdp_rxq_info_unreg(&port->xdp_rxq);
}

Messung V0.5
C=96 H=94 G=94

¤ Dauer der Verarbeitung: 0.0 Sekunden  (vorverarbeitet)  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.