Commit 13ce2daa authored by Maciej Fijalkowski's avatar Maciej Fijalkowski Committed by Alexei Starovoitov

xsk: add new netlink attribute dedicated for ZC max frags

Introduce new netlink attribute NETDEV_A_DEV_XDP_ZC_MAX_SEGS that will
carry maximum fragments that underlying ZC driver is able to handle on
TX side. It is going to be included in netlink response only when driver
supports ZC. Any value higher than 1 implies multi-buffer ZC support on
underlying device.
Signed-off-by: default avatarMaciej Fijalkowski <maciej.fijalkowski@intel.com>
Link: https://lore.kernel.org/r/20230719132421.584801-11-maciej.fijalkowski@intel.comSigned-off-by: default avatarAlexei Starovoitov <ast@kernel.org>
parent 07428da9
...@@ -62,6 +62,12 @@ attribute-sets: ...@@ -62,6 +62,12 @@ attribute-sets:
type: u64 type: u64
enum: xdp-act enum: xdp-act
enum-as-flags: true enum-as-flags: true
-
name: xdp_zc_max_segs
doc: max fragment count supported by ZC driver
type: u32
checks:
min: 1
operations: operations:
list: list:
......
...@@ -2250,6 +2250,7 @@ struct net_device { ...@@ -2250,6 +2250,7 @@ struct net_device {
#define GRO_MAX_SIZE (8 * 65535u) #define GRO_MAX_SIZE (8 * 65535u)
unsigned int gro_max_size; unsigned int gro_max_size;
unsigned int gro_ipv4_max_size; unsigned int gro_ipv4_max_size;
unsigned int xdp_zc_max_segs;
rx_handler_func_t __rcu *rx_handler; rx_handler_func_t __rcu *rx_handler;
void __rcu *rx_handler_data; void __rcu *rx_handler_data;
......
...@@ -41,6 +41,7 @@ enum { ...@@ -41,6 +41,7 @@ enum {
NETDEV_A_DEV_IFINDEX = 1, NETDEV_A_DEV_IFINDEX = 1,
NETDEV_A_DEV_PAD, NETDEV_A_DEV_PAD,
NETDEV_A_DEV_XDP_FEATURES, NETDEV_A_DEV_XDP_FEATURES,
NETDEV_A_DEV_XDP_ZC_MAX_SEGS,
__NETDEV_A_DEV_MAX, __NETDEV_A_DEV_MAX,
NETDEV_A_DEV_MAX = (__NETDEV_A_DEV_MAX - 1) NETDEV_A_DEV_MAX = (__NETDEV_A_DEV_MAX - 1)
......
...@@ -10613,6 +10613,7 @@ struct net_device *alloc_netdev_mqs(int sizeof_priv, const char *name, ...@@ -10613,6 +10613,7 @@ struct net_device *alloc_netdev_mqs(int sizeof_priv, const char *name,
dev_net_set(dev, &init_net); dev_net_set(dev, &init_net);
dev->gso_max_size = GSO_LEGACY_MAX_SIZE; dev->gso_max_size = GSO_LEGACY_MAX_SIZE;
dev->xdp_zc_max_segs = 1;
dev->gso_max_segs = GSO_MAX_SEGS; dev->gso_max_segs = GSO_MAX_SEGS;
dev->gro_max_size = GRO_LEGACY_MAX_SIZE; dev->gro_max_size = GRO_LEGACY_MAX_SIZE;
dev->gso_ipv4_max_size = GSO_LEGACY_MAX_SIZE; dev->gso_ipv4_max_size = GSO_LEGACY_MAX_SIZE;
......
...@@ -25,6 +25,14 @@ netdev_nl_dev_fill(struct net_device *netdev, struct sk_buff *rsp, ...@@ -25,6 +25,14 @@ netdev_nl_dev_fill(struct net_device *netdev, struct sk_buff *rsp,
return -EINVAL; return -EINVAL;
} }
if (netdev->xdp_features & NETDEV_XDP_ACT_XSK_ZEROCOPY) {
if (nla_put_u32(rsp, NETDEV_A_DEV_XDP_ZC_MAX_SEGS,
netdev->xdp_zc_max_segs)) {
genlmsg_cancel(rsp, hdr);
return -EINVAL;
}
}
genlmsg_end(rsp, hdr); genlmsg_end(rsp, hdr);
return 0; return 0;
......
...@@ -41,6 +41,7 @@ enum { ...@@ -41,6 +41,7 @@ enum {
NETDEV_A_DEV_IFINDEX = 1, NETDEV_A_DEV_IFINDEX = 1,
NETDEV_A_DEV_PAD, NETDEV_A_DEV_PAD,
NETDEV_A_DEV_XDP_FEATURES, NETDEV_A_DEV_XDP_FEATURES,
NETDEV_A_DEV_XDP_ZC_MAX_SEGS,
__NETDEV_A_DEV_MAX, __NETDEV_A_DEV_MAX,
NETDEV_A_DEV_MAX = (__NETDEV_A_DEV_MAX - 1) NETDEV_A_DEV_MAX = (__NETDEV_A_DEV_MAX - 1)
......
...@@ -1105,9 +1105,10 @@ struct bpf_xdp_query_opts { ...@@ -1105,9 +1105,10 @@ struct bpf_xdp_query_opts {
__u32 skb_prog_id; /* output */ __u32 skb_prog_id; /* output */
__u8 attach_mode; /* output */ __u8 attach_mode; /* output */
__u64 feature_flags; /* output */ __u64 feature_flags; /* output */
__u32 xdp_zc_max_segs; /* output */
size_t :0; size_t :0;
}; };
#define bpf_xdp_query_opts__last_field feature_flags #define bpf_xdp_query_opts__last_field xdp_zc_max_segs
LIBBPF_API int bpf_xdp_attach(int ifindex, int prog_fd, __u32 flags, LIBBPF_API int bpf_xdp_attach(int ifindex, int prog_fd, __u32 flags,
const struct bpf_xdp_attach_opts *opts); const struct bpf_xdp_attach_opts *opts);
......
...@@ -45,6 +45,7 @@ struct xdp_id_md { ...@@ -45,6 +45,7 @@ struct xdp_id_md {
struct xdp_features_md { struct xdp_features_md {
int ifindex; int ifindex;
__u32 xdp_zc_max_segs;
__u64 flags; __u64 flags;
}; };
...@@ -421,6 +422,9 @@ static int parse_xdp_features(struct nlmsghdr *nh, libbpf_dump_nlmsg_t fn, ...@@ -421,6 +422,9 @@ static int parse_xdp_features(struct nlmsghdr *nh, libbpf_dump_nlmsg_t fn,
return NL_CONT; return NL_CONT;
md->flags = libbpf_nla_getattr_u64(tb[NETDEV_A_DEV_XDP_FEATURES]); md->flags = libbpf_nla_getattr_u64(tb[NETDEV_A_DEV_XDP_FEATURES]);
if (tb[NETDEV_A_DEV_XDP_ZC_MAX_SEGS])
md->xdp_zc_max_segs =
libbpf_nla_getattr_u32(tb[NETDEV_A_DEV_XDP_ZC_MAX_SEGS]);
return NL_DONE; return NL_DONE;
} }
...@@ -493,6 +497,7 @@ int bpf_xdp_query(int ifindex, int xdp_flags, struct bpf_xdp_query_opts *opts) ...@@ -493,6 +497,7 @@ int bpf_xdp_query(int ifindex, int xdp_flags, struct bpf_xdp_query_opts *opts)
return libbpf_err(err); return libbpf_err(err);
opts->feature_flags = md.flags; opts->feature_flags = md.flags;
opts->xdp_zc_max_segs = md.xdp_zc_max_segs;
skip_feature_flags: skip_feature_flags:
return 0; return 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment