Any updates? On Sat, Feb 25, 2023 at 6:53 PM Tanzeel-inline wrote: > From: Tanzeel Ahmed > > This patch is new version of [PATCH] lib/net: added push MPLS header API. > I have also added the MPLS strip functionality to address the question > asked in last patch. > > > You should explain why you add this function. > None of the foundational NICs currently supports MPLS insertion and > stripping, this functionality can help users who rely on MPLS in their > network application. > > > I'm not sure it should be inline > I did for performance in high-traffic application. > > Signed-off-by: Tanzeel Ahmed > > --- > v4: > * Removed extra void cast. > * rte_pktmbuf_append/mtod now return void*. > The memmove result is casted to rte_ether_hdr*. > > v3: > * fixed patch check failure issue > > v2: > * marked experimental > * coding style fixed > * changed rte_memcpy to memcpy > * mpls header marked as const in parameter > * added MPLS stripping functionality > --- > .mailmap | 1 + > lib/net/rte_mpls.h | 97 > ++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 2 files changed, 98 insertions(+) > > diff --git a/.mailmap b/.mailmap > index a9f4f28..2af4e0d 100644 > --- a/.mailmap > +++ b/.mailmap > @@ -1312,6 +1312,7 @@ Takeshi Yoshimura < > t.yoshimura8869@gmail.com> > Takuya Asada > Tal Avraham > Tal Shnaiderman > +Tanzeel Ahmed > Tao Y Yang > Tao Zhu > Taripin Samuel > diff --git a/lib/net/rte_mpls.h b/lib/net/rte_mpls.h > index 51523e7..d7e267f 100644 > --- a/lib/net/rte_mpls.h > +++ b/lib/net/rte_mpls.h > @@ -13,6 +13,8 @@ > > #include > #include > +#include > +#include > > #ifdef __cplusplus > extern "C" { > @@ -36,6 +38,101 @@ struct rte_mpls_hdr { > uint8_t ttl; /**< Time to live. */ > } __rte_packed; > > +#define RTE_MPLS_HLEN 4 /**< Length of MPLS header. */ > + > +/** > + * @warning > + * @b EXPERIMENTAL: this API may change without prior notice. > + * > + * Insert MPLS header into the packet. > + * If it's first MPLS header to be inserted in the packet, > + * - Updates the ether type. > + * - Sets the MPLS bottom-of-stack bit to 1. > + * > + * @param m > + * The pointer to the mbuf. > + * @param mp > + * The pointer to the MPLS header. > + * @return > + * 0 on success, -1 on error > + */ > +__rte_experimental > +static inline int > +rte_mpls_push_over_l2(struct rte_mbuf **m, const struct rte_mpls_hdr *mp) > +{ > + void *os, *ns; > + struct rte_ether_hdr *nh; > + struct rte_mpls_hdr *mph; > + > + /* Can't insert header if mbuf is shared */ > + if (!RTE_MBUF_DIRECT(*m) || rte_mbuf_refcnt_read(*m) > 1) > + return -EINVAL; > + > + /* Can't insert header if ethernet frame doesn't exist */ > + if (rte_pktmbuf_data_len(*m) < RTE_ETHER_HDR_LEN) > + return -EINVAL; > + > + os = rte_pktmbuf_mtod(*m, void *); > + ns = (void *)rte_pktmbuf_prepend(*m, sizeof(struct rte_mpls_hdr)); > + if (ns == NULL) > + return -ENOSPC; > + > + nh = (struct rte_ether_hdr *)memmove(ns, os, RTE_ETHER_HDR_LEN); > + > + /* Copy the MPLS header after ethernet frame */ > + mph = rte_pktmbuf_mtod_offset(*m, struct rte_mpls_hdr*, > + sizeof(struct rte_ether_hdr)); > + memcpy(mph, mp, RTE_MPLS_HLEN); > + > + mph->tag_msb = rte_cpu_to_be_16(mp->tag_msb); > + > + /* If first MPLS header, update ether type and bottom-of-stack bit > */ > + if (nh->ether_type != rte_cpu_to_be_16(RTE_ETHER_TYPE_MPLS)) { > + nh->ether_type = rte_cpu_to_be_16(RTE_ETHER_TYPE_MPLS); > + mph->bs = 1; > + } else { > + mph->bs = 0; > + } > + > + return 0; > +} > + > +/** > + * @warning > + * @b EXPERIMENTAL: this API may change without prior notice. > + * > + * Strips MPLS from the packet. Doesn't update the ether type > + * > + * @param m > + * The pointer to the mbuf. > + * @return > + * 0 on success, -1 on error > + */ > +__rte_experimental > +static inline int > +rte_mpls_strip_over_l2(struct rte_mbuf *m) > +{ > + struct rte_ether_hdr *eh = rte_pktmbuf_mtod(m, struct > rte_ether_hdr *); > + struct rte_mpls_hdr *mph; > + bool mpls_exist = true; > + > + if (eh->ether_type != rte_cpu_to_be_16(RTE_ETHER_TYPE_MPLS)) > + return -1; > + > + /* Stripping all MPLS header */ > + while (mpls_exist) { > + mph = rte_pktmbuf_mtod_offset(m, struct rte_mpls_hdr*, > + sizeof(struct rte_ether_hdr)); > + if (mph->bs & 1) > + mpls_exist = false; > + memmove(rte_pktmbuf_adj(m, sizeof(struct rte_mpls_hdr)), > + eh, sizeof(struct rte_ether_hdr)); > + eh = rte_pktmbuf_mtod(m, struct rte_ether_hdr *); > + } > + > + return 0; > +} > + > #ifdef __cplusplus > } > #endif > -- > 1.8.3.1 > >