Skip to content

Commit 4a1037a

Browse files
alardamkernel-patches-bot
authored andcommitted
libbpf: add API to get XSK/XDP caps
Add public xsk API to read supported XDP functions of a netdev: - XDP driver mode (SKB, DRV), - XSK bind mode (COPY, ZEROCOPY). Signed-off-by: Marek Majtyka <[email protected]>
1 parent 61e1a88 commit 4a1037a

File tree

3 files changed

+53
-2
lines changed

3 files changed

+53
-2
lines changed

tools/lib/bpf/libbpf.map

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -345,4 +345,5 @@ LIBBPF_0.3.0 {
345345
btf__parse_split;
346346
btf__new_empty_split;
347347
btf__new_split;
348+
xsk_socket__get_caps;
348349
} LIBBPF_0.2.0;

tools/lib/bpf/xsk.c

Lines changed: 50 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@
1515
#include <arpa/inet.h>
1616
#include <asm/barrier.h>
1717
#include <linux/compiler.h>
18-
#include <linux/ethtool.h>
1918
#include <linux/filter.h>
2019
#include <linux/if_ether.h>
2120
#include <linux/if_link.h>
@@ -31,6 +30,7 @@
3130
#include <sys/types.h>
3231

3332
#include "bpf.h"
33+
#include "ethtool.h"
3434
#include "libbpf.h"
3535
#include "libbpf_internal.h"
3636
#include "xsk.h"
@@ -931,3 +931,52 @@ void xsk_socket__delete(struct xsk_socket *xsk)
931931
close(xsk->fd);
932932
free(xsk);
933933
}
934+
935+
int xsk_socket__get_caps(const char *ifname, __u32 *xdp_caps, __u16 *bind_caps)
936+
{
937+
struct ethnl_params param;
938+
int ret;
939+
940+
if (!xdp_caps || !bind_caps || !ifname ||
941+
(strnlen(ifname, IFNAMSIZ) >= IFNAMSIZ))
942+
return -EINVAL;
943+
944+
param.nl_family = ETHTOOL_GENL_NAME;
945+
param.xdp_zc_flags = 0;
946+
param.ifname = ifname;
947+
param.xdp_flags = 0;
948+
949+
/* First, get the netlink family id */
950+
ret = libbpf_ethnl_get_ethtool_family_id(&param);
951+
if (ret)
952+
return ret;
953+
954+
/* Second, get number of features */
955+
param.features = 0;
956+
ret = libbpf_ethnl_get_netdev_features(&param);
957+
if (ret)
958+
return ret;
959+
960+
/* Third, get the features description */
961+
ret = libbpf_ethnl_get_netdev_features(&param);
962+
if (ret)
963+
return ret;
964+
965+
*xdp_caps = XDP_FLAGS_SKB_MODE;
966+
*bind_caps = XDP_COPY;
967+
968+
if (param.xdp_idx == -1 || param.xdp_zc_idx == -1)
969+
return 0;
970+
971+
/* Finally, get features flags and process it */
972+
ret = libbpf_ethnl_get_active_bits(&param);
973+
if (!ret) {
974+
if (param.xdp_flags) {
975+
*xdp_caps |= XDP_FLAGS_DRV_MODE;
976+
if (param.xdp_zc_flags)
977+
*bind_caps |= XDP_ZEROCOPY;
978+
}
979+
}
980+
981+
return ret;
982+
}

tools/lib/bpf/xsk.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,8 @@ xsk_socket__create_shared(struct xsk_socket **xsk_ptr,
247247
/* Returns 0 for success and -EBUSY if the umem is still in use. */
248248
LIBBPF_API int xsk_umem__delete(struct xsk_umem *umem);
249249
LIBBPF_API void xsk_socket__delete(struct xsk_socket *xsk);
250-
250+
LIBBPF_API int xsk_socket__get_caps(const char *ifname, __u32 *xdp_caps,
251+
__u16 *bind_caps);
251252
#ifdef __cplusplus
252253
} /* extern "C" */
253254
#endif

0 commit comments

Comments
 (0)