mirror of
https://github.com/torvalds/linux.git
synced 2026-10-23 23:51:02 +02:00
netfilter pull request 26-09-30
-----BEGIN PGP SIGNATURE----- iQIzBAABCgAdFiEEjF9xRqF1emXiQiqU1w0aZmrPKyEFAmq8vB8ACgkQ1w0aZmrP KyFFVRAAodpV3MdxxjHIk4FOU6IY7e4PGx4HCqbRtEE9/WKDFKjUCpGxJuTNwuKS HIdU9W0ypdwyuNKTBhWcgbCqg9GbbZkmwJM3wBbsjPtBMJ13TcI0SYoJNp+MUCNu WlcrJrsdfkwMD3rNilx8iuCKrFcLx/l8qe6JWZNdP0lRu9dhkxEiqXgkKP+XB4CI mlV3TnP6MkG25GI9QmtKEtbIYrH4688bxO3LemzoVLm2vOvvrMG7cwqGr2XU7fYB IH8VocIVdzp6/w8JAxLbJNGR0bwGjdqJorz3ysmQ8jQPOt19PyP4WLmCbNuAoGMm XdLZPlDMqdoEe+KQhjlb7isPedoun7koNiOtqBQhjRvcCv03MH7LTmMgmV702+ex Hfm6EuaWINHeVGxNDADWebUyLy7jx3xYPqEpMA+UhgnbIicVGTJGGYiq5dGvObZE ek68iqmaoMRNay94sReakOtvHVz8iaXUhO60xdF0efrsDRnr7Yv6Ztxdl9nPCRIW fUz1/l7Z4j3gfTbmO1CKDK8aHlnibseYpQygLo53nkKWPcexJzYHbVl2tnjYUDZ6 dryGhLokthdAZW4W7hONvwlU+zT/eKfa4IesxgDglwGC9Hjxtwq2kuPrIuehMH/0 oEdVw6x4L+SBIrhnM9PaBBgp/dQarXZJQss3XfUxzmMPViScSxg= =cSG8 -----END PGP SIGNATURE----- Merge tag 'nf-26-09-30' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf Pablo Neira Ayuso says: ==================== Netfilter/IPVS fixes for net The following batch contains Netfilter fixes for net. This batch fixes crashes as recent feature regression, one of the due to a dependency that has been pulled into -stable: 1) Expand existing ipset fix for bitmap sets to disallow comments updates from kernel-side adds, from Florian Westphal. 2) Drop flowtable reference if nf_ct_netns_get() fails, otherwise flowtable cannot ever be removed, from Aohan Mei. 3) nft_rbtree GC should collect end elements that contained in this transaction batch, new or deleted elements are never expired. From Weiming Shi. 4) Restrict nf_nat_bpf so it does not set unknown NF_NAT_MANIP_* values, from Fernando F. Mancera. 5) Flowtable GC must skip flows that are pending hardware updates, generalize the PENDING flag and use it to inhibit GC. 6) Restore flowtable with ieee80211 which broke due to a relatively recent commit, which was pulled in by -stable, causing a regression in 6.18 kernels. And the following IPVS fixes: 1) Fix accounting of cache entries in IPVS LBLC for destinations, which eventually fills up the table and trigger recurrent resizing, from Julian Anastasov. 2) Limit IPVS cache growth for LBLCR and LBLC schedulers, from Zhiling Zou. 3) Restrict IP_VS_CONN_F_ONE_PACKET for normal connections, do not allow to use it with templates. Also from Julian. 4) Sanitize flags in IPVS sync messages received in the backup. From Julian Anastasov. netfilter pull request 26-09-30 * tag 'nf-26-09-30' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf: netfilter: flowtable: restore ieee80211 forward path netfilter: flowtable: generalize pending status bit netfilter: bpf: reject invalid NAT manipulation types netfilter: nft_set_rbtree: skip transaction elements during GC ipvs: filter some flags received in the backup server ipvs: do not create invisible templates ipvs: bound LBLCR and LBLC cache growth ipvs: fix missing counter decrement in lblc netfilter: nft_flow_offload: drop flowtable reference on init error path netfilter: ipset: do not update comments from kernel-side adds ==================== Link: https://patch.msgid.link/20260930074142.298353-1-pablo@netfilter.org Signed-off-by: Paolo Abeni <pabeni@redhat.com>
This commit is contained in:
commit
e23a64eb24
|
|
@ -887,6 +887,7 @@ enum net_device_path_type {
|
|||
DEV_PATH_DSA,
|
||||
DEV_PATH_MTK_WDMA,
|
||||
DEV_PATH_TUN,
|
||||
DEV_PATH_IEEE80211,
|
||||
};
|
||||
|
||||
struct net_device_path {
|
||||
|
|
@ -953,6 +954,8 @@ struct net_device_path_ctx {
|
|||
u16 id;
|
||||
__be16 proto;
|
||||
} vlan[NET_DEVICE_PATH_VLAN_MAX];
|
||||
|
||||
bool ieee80211;
|
||||
};
|
||||
|
||||
enum tc_setup_type {
|
||||
|
|
|
|||
|
|
@ -183,10 +183,10 @@ enum nf_flow_flags {
|
|||
NF_FLOW_DNAT,
|
||||
NF_FLOW_CLOSING,
|
||||
NF_FLOW_TEARDOWN,
|
||||
NF_FLOW_PENDING,
|
||||
NF_FLOW_HW,
|
||||
NF_FLOW_HW_DYING,
|
||||
NF_FLOW_HW_DEAD,
|
||||
NF_FLOW_HW_PENDING,
|
||||
NF_FLOW_HW_BIDIRECTIONAL,
|
||||
NF_FLOW_HW_ESTABLISHED,
|
||||
};
|
||||
|
|
|
|||
|
|
@ -1023,6 +1023,13 @@ static int ieee80211_netdev_fill_forward_path(struct net_device_path_ctx *ctx,
|
|||
struct sta_info *sta;
|
||||
int ret = -ENOENT;
|
||||
|
||||
if (ctx->ieee80211) {
|
||||
path->type = DEV_PATH_IEEE80211;
|
||||
path->dev = ctx->dev;
|
||||
ctx->dev = NULL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
sdata = IEEE80211_DEV_TO_SUB_IF(ctx->dev);
|
||||
local = sdata->local;
|
||||
|
||||
|
|
|
|||
|
|
@ -159,7 +159,7 @@ mtype_add(struct ip_set *set, void *value, const struct ip_set_ext *ext,
|
|||
|
||||
if (SET_WITH_COUNTER(set))
|
||||
ip_set_init_counter(ext_counter(x, set), ext);
|
||||
if (SET_WITH_COMMENT(set))
|
||||
if (SET_WITH_COMMENT(set) && !ext->target)
|
||||
ip_set_init_comment(set, ext_comment(x, set), ext);
|
||||
if (SET_WITH_SKBINFO(set))
|
||||
ip_set_init_skbinfo(ext_skbinfo(x, set), ext);
|
||||
|
|
|
|||
|
|
@ -1102,6 +1102,9 @@ ip_vs_bind_dest(struct ip_vs_conn *cp, struct ip_vs_dest *dest)
|
|||
if (cp->protocol != IPPROTO_UDP)
|
||||
conn_flags &= ~IP_VS_CONN_F_ONE_PACKET;
|
||||
flags = cp->flags;
|
||||
/* Only visible templates can control multiple connections */
|
||||
if (flags & IP_VS_CONN_F_TEMPLATE)
|
||||
conn_flags &= ~IP_VS_CONN_F_ONE_PACKET;
|
||||
/* Bind with the destination and its corresponding transmitter */
|
||||
if (flags & IP_VS_CONN_F_SYNC) {
|
||||
/* Synced conns are hashed, so they can not get this flag */
|
||||
|
|
|
|||
|
|
@ -203,7 +203,11 @@ ip_vs_lblc_new(struct ip_vs_lblc_table *tbl, const union nf_inet_addr *daddr,
|
|||
if (en->dest == dest)
|
||||
return en;
|
||||
ip_vs_lblc_del(en);
|
||||
atomic_dec(&tbl->entries);
|
||||
}
|
||||
if (atomic_read(&tbl->entries) >= tbl->max_size * 3 / 2)
|
||||
return NULL;
|
||||
|
||||
en = kmalloc_obj(*en, GFP_ATOMIC);
|
||||
if (!en)
|
||||
return NULL;
|
||||
|
|
|
|||
|
|
@ -363,6 +363,9 @@ ip_vs_lblcr_new(struct ip_vs_lblcr_table *tbl, const union nf_inet_addr *daddr,
|
|||
|
||||
en = ip_vs_lblcr_get(af, tbl, daddr);
|
||||
if (!en) {
|
||||
if (atomic_read(&tbl->entries) >= tbl->max_size * 3 / 2)
|
||||
return NULL;
|
||||
|
||||
en = kmalloc_obj(*en, GFP_ATOMIC);
|
||||
if (!en)
|
||||
return NULL;
|
||||
|
|
|
|||
|
|
@ -949,6 +949,21 @@ static void ip_vs_proc_conn(struct netns_ipvs *ipvs, struct ip_vs_conn_param *pa
|
|||
ip_vs_conn_put(cp);
|
||||
}
|
||||
|
||||
/* Check for incompatible flags */
|
||||
static bool ip_vs_sync_validate_flags(u32 flags)
|
||||
{
|
||||
/* We do not expect NO_CPORT, especially to allow lookups
|
||||
* to hit templates
|
||||
*/
|
||||
if (flags & IP_VS_CONN_F_NO_CPORT) {
|
||||
if (flags & IP_VS_CONN_F_TEMPLATE)
|
||||
return false;
|
||||
}
|
||||
if (flags & IP_VS_CONN_F_ONE_PACKET)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
* Process received multicast message for Version 0
|
||||
*/
|
||||
|
|
@ -972,8 +987,7 @@ static void ip_vs_process_message_v0(struct netns_ipvs *ipvs, const char *buffer
|
|||
return;
|
||||
}
|
||||
s = (struct ip_vs_sync_conn_v0 *) p;
|
||||
flags = ntohs(s->flags) | IP_VS_CONN_F_SYNC;
|
||||
flags &= ~IP_VS_CONN_F_HASHED;
|
||||
flags = ntohs(s->flags);
|
||||
if (flags & IP_VS_CONN_F_SEQ_MASK) {
|
||||
opt = (struct ip_vs_sync_conn_options *)&s[1];
|
||||
p += FULL_CONN_SIZE;
|
||||
|
|
@ -986,6 +1000,13 @@ static void ip_vs_process_message_v0(struct netns_ipvs *ipvs, const char *buffer
|
|||
p += SIMPLE_CONN_SIZE;
|
||||
}
|
||||
|
||||
if (!ip_vs_sync_validate_flags(flags)) {
|
||||
IP_VS_DBG(2, "BACKUP v0, Invalid flags 0x%X\n", flags);
|
||||
continue;
|
||||
}
|
||||
flags &= IP_VS_CONN_F_BACKUP_MASK;
|
||||
flags |= IP_VS_CONN_F_SYNC;
|
||||
|
||||
state = ntohs(s->state);
|
||||
if (!(flags & IP_VS_CONN_F_TEMPLATE)) {
|
||||
pp = ip_vs_proto_get(s->protocol);
|
||||
|
|
@ -1141,7 +1162,13 @@ static inline int ip_vs_proc_sync_conn(struct netns_ipvs *ipvs, __u8 *p, __u8 *m
|
|||
}
|
||||
|
||||
/* Get flags and Mask off unsupported */
|
||||
flags = ntohl(s->v4.flags) & IP_VS_CONN_F_BACKUP_MASK;
|
||||
flags = ntohl(s->v4.flags);
|
||||
if (!ip_vs_sync_validate_flags(flags)) {
|
||||
IP_VS_DBG(3, "BACKUP, Invalid flags 0x%X\n", flags);
|
||||
retc = 25;
|
||||
goto out;
|
||||
}
|
||||
flags &= IP_VS_CONN_F_BACKUP_MASK;
|
||||
flags |= IP_VS_CONN_F_SYNC;
|
||||
state = ntohs(s->v4.state);
|
||||
|
||||
|
|
|
|||
|
|
@ -575,7 +575,12 @@ static void nf_flow_table_extend_ct_timeout(struct nf_conn *ct)
|
|||
static void nf_flow_offload_gc_step(struct nf_flowtable *flow_table,
|
||||
struct flow_offload *flow, void *data)
|
||||
{
|
||||
bool teardown = test_bit(NF_FLOW_TEARDOWN, &flow->flags);
|
||||
bool teardown;
|
||||
|
||||
if (test_bit(NF_FLOW_PENDING, &flow->flags))
|
||||
return;
|
||||
|
||||
teardown = test_bit(NF_FLOW_TEARDOWN, &flow->flags);
|
||||
|
||||
if (nf_flow_has_expired(flow) ||
|
||||
nf_ct_is_dying(flow->ct) ||
|
||||
|
|
|
|||
|
|
@ -995,6 +995,7 @@ static void flow_offload_work_del(struct flow_offload_work *offload)
|
|||
flow_offload_tuple_del(offload, FLOW_OFFLOAD_DIR_ORIGINAL);
|
||||
if (test_bit(NF_FLOW_HW_BIDIRECTIONAL, &offload->flow->flags))
|
||||
flow_offload_tuple_del(offload, FLOW_OFFLOAD_DIR_REPLY);
|
||||
set_bit(NF_FLOW_HW_DEAD, &offload->flow->flags);
|
||||
}
|
||||
|
||||
static void flow_offload_tuple_stats(struct flow_offload_work *offload,
|
||||
|
|
@ -1056,13 +1057,8 @@ static void flow_offload_work_handler(struct work_struct *work)
|
|||
default:
|
||||
WARN_ON_ONCE(1);
|
||||
}
|
||||
|
||||
clear_bit(NF_FLOW_HW_PENDING, &offload->flow->flags);
|
||||
if (offload->cmd == FLOW_CLS_DESTROY) {
|
||||
/* Publish after the worker's last flow access. */
|
||||
smp_mb__before_atomic();
|
||||
set_bit(NF_FLOW_HW_DEAD, &offload->flow->flags);
|
||||
}
|
||||
smp_mb__before_atomic();
|
||||
clear_bit(NF_FLOW_PENDING, &offload->flow->flags);
|
||||
|
||||
kfree(offload);
|
||||
}
|
||||
|
|
@ -1089,12 +1085,12 @@ nf_flow_offload_work_alloc(struct nf_flowtable *flowtable,
|
|||
{
|
||||
struct flow_offload_work *offload;
|
||||
|
||||
if (test_and_set_bit(NF_FLOW_HW_PENDING, &flow->flags))
|
||||
if (test_and_set_bit(NF_FLOW_PENDING, &flow->flags))
|
||||
return NULL;
|
||||
|
||||
offload = kmalloc_obj(struct flow_offload_work, GFP_ATOMIC);
|
||||
if (!offload) {
|
||||
clear_bit(NF_FLOW_HW_PENDING, &flow->flags);
|
||||
clear_bit(NF_FLOW_PENDING, &flow->flags);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -53,6 +53,7 @@ static int nft_dev_fill_forward_path(const struct dst_entry *dst_cache,
|
|||
struct net_device_path_ctx ctx = {
|
||||
.dev = dev,
|
||||
.ether_type = ether_type,
|
||||
.ieee80211 = true,
|
||||
};
|
||||
struct neighbour *n;
|
||||
u8 nud_state;
|
||||
|
|
@ -114,6 +115,7 @@ static int nft_dev_path_info(struct net_device_path_stack *stack,
|
|||
path = &stack->path[i];
|
||||
switch (path->type) {
|
||||
case DEV_PATH_ETHERNET:
|
||||
case DEV_PATH_IEEE80211:
|
||||
case DEV_PATH_DSA:
|
||||
case DEV_PATH_VLAN:
|
||||
case DEV_PATH_PPPOE:
|
||||
|
|
@ -123,6 +125,7 @@ static int nft_dev_path_info(struct net_device_path_stack *stack,
|
|||
memcpy(info->h_source, path->dev->dev_addr, ETH_ALEN);
|
||||
|
||||
if (path->type == DEV_PATH_ETHERNET ||
|
||||
path->type == DEV_PATH_IEEE80211 ||
|
||||
path->type == DEV_PATH_DSA)
|
||||
break;
|
||||
|
||||
|
|
|
|||
|
|
@ -39,6 +39,9 @@ __bpf_kfunc int bpf_ct_set_nat_info(struct nf_conn___init *nfct,
|
|||
if (proto != NFPROTO_IPV4 && proto != NFPROTO_IPV6)
|
||||
return -EINVAL;
|
||||
|
||||
if (manip != NF_NAT_MANIP_SRC && manip != NF_NAT_MANIP_DST)
|
||||
return -EINVAL;
|
||||
|
||||
memset(&range, 0, sizeof(struct nf_nat_range2));
|
||||
range.flags = NF_NAT_RANGE_MAP_IPS;
|
||||
range.min_addr = *addr;
|
||||
|
|
|
|||
|
|
@ -767,8 +767,9 @@ nf_nat_setup_info(struct nf_conn *ct,
|
|||
if (nf_ct_is_confirmed(ct))
|
||||
return NF_ACCEPT;
|
||||
|
||||
WARN_ON(maniptype != NF_NAT_MANIP_SRC &&
|
||||
maniptype != NF_NAT_MANIP_DST);
|
||||
if (WARN_ON(maniptype != NF_NAT_MANIP_SRC &&
|
||||
maniptype != NF_NAT_MANIP_DST))
|
||||
return NF_DROP;
|
||||
|
||||
if (WARN_ON(nf_nat_initialized(ct, maniptype)))
|
||||
return NF_DROP;
|
||||
|
|
|
|||
|
|
@ -160,6 +160,7 @@ static int nft_flow_offload_init(const struct nft_ctx *ctx,
|
|||
struct nft_flow_offload *priv = nft_expr_priv(expr);
|
||||
u8 genmask = nft_genmask_next(ctx->net);
|
||||
struct nft_flowtable *flowtable;
|
||||
int err;
|
||||
|
||||
if (!tb[NFTA_FLOW_TABLE_NAME])
|
||||
return -EINVAL;
|
||||
|
|
@ -174,7 +175,11 @@ static int nft_flow_offload_init(const struct nft_ctx *ctx,
|
|||
|
||||
priv->flowtable = flowtable;
|
||||
|
||||
return nf_ct_netns_get(ctx->net, ctx->family);
|
||||
err = nf_ct_netns_get(ctx->net, ctx->family);
|
||||
if (err < 0)
|
||||
nft_use_dec(&flowtable->use);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static void nft_flow_offload_deactivate(const struct nft_ctx *ctx,
|
||||
|
|
|
|||
|
|
@ -900,6 +900,8 @@ static void nft_rbtree_gc_scan(struct nft_set *set)
|
|||
next = rb_next(node);
|
||||
|
||||
rbe = rb_entry(node, struct nft_rbtree_elem, node);
|
||||
if (!nft_set_elem_active(&rbe->ext, NFT_GENMASK_ANY))
|
||||
continue;
|
||||
|
||||
/* elements are reversed in the rbtree for historical reasons,
|
||||
* from highest to lowest value, that is why end element is
|
||||
|
|
|
|||
|
|
@ -289,7 +289,7 @@ static bool tcf_ct_flow_is_outdated(const struct flow_offload *flow)
|
|||
{
|
||||
return test_bit(IPS_SEEN_REPLY_BIT, &flow->ct->status) &&
|
||||
test_bit(IPS_HW_OFFLOAD_BIT, &flow->ct->status) &&
|
||||
!test_bit(NF_FLOW_HW_PENDING, &flow->flags) &&
|
||||
!test_bit(NF_FLOW_PENDING, &flow->flags) &&
|
||||
!test_bit(NF_FLOW_HW_ESTABLISHED, &flow->flags);
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user