mirror of
https://github.com/torvalds/linux.git
synced 2024-11-26 22:21:42 +00:00
netfilter pull request 23-12-06
-----BEGIN PGP SIGNATURE----- iQIzBAABCgAdFiEEN9lkrMBJgcdVAPub1V2XiooUIOQFAmVwtKsACgkQ1V2XiooU IOQSmBAAo+L16FYFpdaZIUoFoE9D+WdZCiKVuY2pn9NNOzg8k9OEu2XYqjvOPjcu 68GvgWIbDp0O6lIj70Oz2VxAG7z74hAJJIWsq/ufsSnzggAl+L/eNm0naOysd8rv wzzO8W22xB6aGSPVUxFul3L9FD0Cf0NkwCVHzTnndthcfxX6GEeV33puTnUnC2Ww b3l01tw/mbX7But0j4XwvFhSdXUGjUQPy6h8T90kp/wgZ8Fkyqsm2VFPRn2Yrayr XQ/RS+zdTy4Y07P4KA50k80l0lGbpcoZMEFbvzPmsKCWKgqqpb8fE2EgZ4sPSeY/ 0nDhkWzKDriJrmZS2kW/GEXyV61DbIL/Pmq/Y+GQwBHoxNMP/tonJ2EFXsmQPVwO jHsYerqQ6X8zsuCwtsUldp/afz+SjBL8HzQjfm5TVxNmArXythKsSpJmfUoDOsp1 opSxoXztFfFid7K3T1/g+yhoVE6Xxe+KdnWYdpfC3t2VrX/HZts2Wxeuvpe7UbOB ktK9jceknMb22AHNixX4UeyY/xYcZMpuQtwsXp6twaxOBbB++g1X/rTuK6TeXoFb 2fPFjPaBuiyqFRC78leLYiHWtbKIQg7i5yIcuadUUifXW6q6C9gUUM9dsDt6SOlr Uao9GayMsjhLDgmUMesSsIJ6LILkhTytPNpE8OiOmIdZv7fhmqo= =dEOA -----END PGP SIGNATURE----- Merge tag 'nf-23-12-06' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf Pablo Neira Ayuso says: ==================== Netfilter fixes for net The following patchset contains Netfilter fixes for net: 1) Incorrect nf_defrag registration for bpf link infra, from D. Wythe. 2) Skip inactive elements in pipapo set backend walk to avoid double deactivation, from Florian Westphal. 3) Fix NFT_*_F_PRESENT check with big endian arch, also from Florian. 4) Bail out if number of expressions in NFTA_DYNSET_EXPRESSIONS mismatch stateful expressions in set declaration. 5) Honor family in table lookup by handle. Broken since 4.16. 6) Use sk_callback_lock to protect access to sk->sk_socket in xt_owner. sock_orphan() might zap this pointer, from Phil Sutter. All of these fixes address broken stuff for several releases. * tag 'nf-23-12-06' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf: netfilter: xt_owner: Fix for unsafe access of sk->sk_socket netfilter: nf_tables: validate family when identifying table via handle netfilter: nf_tables: bail out on mismatching dynset and set expressions netfilter: nf_tables: fix 'exist' matching on bigendian arches netfilter: nft_set_pipapo: skip inactive elements during set walk netfilter: bpf: fix bad registration on nf_defrag ==================== Link: https://lore.kernel.org/r/20231206180357.959930-1-pablo@netfilter.org Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
commit
4de75d3e6b
@ -31,7 +31,7 @@ struct bpf_nf_link {
|
||||
#if IS_ENABLED(CONFIG_NF_DEFRAG_IPV4) || IS_ENABLED(CONFIG_NF_DEFRAG_IPV6)
|
||||
static const struct nf_defrag_hook *
|
||||
get_proto_defrag_hook(struct bpf_nf_link *link,
|
||||
const struct nf_defrag_hook __rcu *global_hook,
|
||||
const struct nf_defrag_hook __rcu **ptr_global_hook,
|
||||
const char *mod)
|
||||
{
|
||||
const struct nf_defrag_hook *hook;
|
||||
@ -39,7 +39,7 @@ get_proto_defrag_hook(struct bpf_nf_link *link,
|
||||
|
||||
/* RCU protects us from races against module unloading */
|
||||
rcu_read_lock();
|
||||
hook = rcu_dereference(global_hook);
|
||||
hook = rcu_dereference(*ptr_global_hook);
|
||||
if (!hook) {
|
||||
rcu_read_unlock();
|
||||
err = request_module(mod);
|
||||
@ -47,7 +47,7 @@ get_proto_defrag_hook(struct bpf_nf_link *link,
|
||||
return ERR_PTR(err < 0 ? err : -EINVAL);
|
||||
|
||||
rcu_read_lock();
|
||||
hook = rcu_dereference(global_hook);
|
||||
hook = rcu_dereference(*ptr_global_hook);
|
||||
}
|
||||
|
||||
if (hook && try_module_get(hook->owner)) {
|
||||
@ -78,7 +78,7 @@ static int bpf_nf_enable_defrag(struct bpf_nf_link *link)
|
||||
switch (link->hook_ops.pf) {
|
||||
#if IS_ENABLED(CONFIG_NF_DEFRAG_IPV4)
|
||||
case NFPROTO_IPV4:
|
||||
hook = get_proto_defrag_hook(link, nf_defrag_v4_hook, "nf_defrag_ipv4");
|
||||
hook = get_proto_defrag_hook(link, &nf_defrag_v4_hook, "nf_defrag_ipv4");
|
||||
if (IS_ERR(hook))
|
||||
return PTR_ERR(hook);
|
||||
|
||||
@ -87,7 +87,7 @@ static int bpf_nf_enable_defrag(struct bpf_nf_link *link)
|
||||
#endif
|
||||
#if IS_ENABLED(CONFIG_NF_DEFRAG_IPV6)
|
||||
case NFPROTO_IPV6:
|
||||
hook = get_proto_defrag_hook(link, nf_defrag_v6_hook, "nf_defrag_ipv6");
|
||||
hook = get_proto_defrag_hook(link, &nf_defrag_v6_hook, "nf_defrag_ipv6");
|
||||
if (IS_ERR(hook))
|
||||
return PTR_ERR(hook);
|
||||
|
||||
|
@ -803,7 +803,7 @@ static struct nft_table *nft_table_lookup(const struct net *net,
|
||||
|
||||
static struct nft_table *nft_table_lookup_byhandle(const struct net *net,
|
||||
const struct nlattr *nla,
|
||||
u8 genmask, u32 nlpid)
|
||||
int family, u8 genmask, u32 nlpid)
|
||||
{
|
||||
struct nftables_pernet *nft_net;
|
||||
struct nft_table *table;
|
||||
@ -811,6 +811,7 @@ static struct nft_table *nft_table_lookup_byhandle(const struct net *net,
|
||||
nft_net = nft_pernet(net);
|
||||
list_for_each_entry(table, &nft_net->tables, list) {
|
||||
if (be64_to_cpu(nla_get_be64(nla)) == table->handle &&
|
||||
table->family == family &&
|
||||
nft_active_genmask(table, genmask)) {
|
||||
if (nft_table_has_owner(table) &&
|
||||
nlpid && table->nlpid != nlpid)
|
||||
@ -1544,7 +1545,7 @@ static int nf_tables_deltable(struct sk_buff *skb, const struct nfnl_info *info,
|
||||
|
||||
if (nla[NFTA_TABLE_HANDLE]) {
|
||||
attr = nla[NFTA_TABLE_HANDLE];
|
||||
table = nft_table_lookup_byhandle(net, attr, genmask,
|
||||
table = nft_table_lookup_byhandle(net, attr, family, genmask,
|
||||
NETLINK_CB(skb).portid);
|
||||
} else {
|
||||
attr = nla[NFTA_TABLE_NAME];
|
||||
|
@ -280,10 +280,15 @@ static int nft_dynset_init(const struct nft_ctx *ctx,
|
||||
priv->expr_array[i] = dynset_expr;
|
||||
priv->num_exprs++;
|
||||
|
||||
if (set->num_exprs &&
|
||||
dynset_expr->ops != set->exprs[i]->ops) {
|
||||
err = -EOPNOTSUPP;
|
||||
goto err_expr_free;
|
||||
if (set->num_exprs) {
|
||||
if (i >= set->num_exprs) {
|
||||
err = -EINVAL;
|
||||
goto err_expr_free;
|
||||
}
|
||||
if (dynset_expr->ops != set->exprs[i]->ops) {
|
||||
err = -EOPNOTSUPP;
|
||||
goto err_expr_free;
|
||||
}
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
@ -214,7 +214,7 @@ static void nft_exthdr_tcp_eval(const struct nft_expr *expr,
|
||||
|
||||
offset = i + priv->offset;
|
||||
if (priv->flags & NFT_EXTHDR_F_PRESENT) {
|
||||
*dest = 1;
|
||||
nft_reg_store8(dest, 1);
|
||||
} else {
|
||||
if (priv->len % NFT_REG32_SIZE)
|
||||
dest[priv->len / NFT_REG32_SIZE] = 0;
|
||||
@ -461,7 +461,7 @@ static void nft_exthdr_dccp_eval(const struct nft_expr *expr,
|
||||
type = bufp[0];
|
||||
|
||||
if (type == priv->type) {
|
||||
*dest = 1;
|
||||
nft_reg_store8(dest, 1);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -145,11 +145,15 @@ void nft_fib_store_result(void *reg, const struct nft_fib *priv,
|
||||
switch (priv->result) {
|
||||
case NFT_FIB_RESULT_OIF:
|
||||
index = dev ? dev->ifindex : 0;
|
||||
*dreg = (priv->flags & NFTA_FIB_F_PRESENT) ? !!index : index;
|
||||
if (priv->flags & NFTA_FIB_F_PRESENT)
|
||||
nft_reg_store8(dreg, !!index);
|
||||
else
|
||||
*dreg = index;
|
||||
|
||||
break;
|
||||
case NFT_FIB_RESULT_OIFNAME:
|
||||
if (priv->flags & NFTA_FIB_F_PRESENT)
|
||||
*dreg = !!dev;
|
||||
nft_reg_store8(dreg, !!dev);
|
||||
else
|
||||
strscpy_pad(reg, dev ? dev->name : "", IFNAMSIZ);
|
||||
break;
|
||||
|
@ -2043,6 +2043,9 @@ static void nft_pipapo_walk(const struct nft_ctx *ctx, struct nft_set *set,
|
||||
|
||||
e = f->mt[r].e;
|
||||
|
||||
if (!nft_set_elem_active(&e->ext, iter->genmask))
|
||||
goto cont;
|
||||
|
||||
iter->err = iter->fn(ctx, set, iter, &e->priv);
|
||||
if (iter->err < 0)
|
||||
goto out;
|
||||
|
@ -76,18 +76,23 @@ owner_mt(const struct sk_buff *skb, struct xt_action_param *par)
|
||||
*/
|
||||
return false;
|
||||
|
||||
filp = sk->sk_socket->file;
|
||||
if (filp == NULL)
|
||||
read_lock_bh(&sk->sk_callback_lock);
|
||||
filp = sk->sk_socket ? sk->sk_socket->file : NULL;
|
||||
if (filp == NULL) {
|
||||
read_unlock_bh(&sk->sk_callback_lock);
|
||||
return ((info->match ^ info->invert) &
|
||||
(XT_OWNER_UID | XT_OWNER_GID)) == 0;
|
||||
}
|
||||
|
||||
if (info->match & XT_OWNER_UID) {
|
||||
kuid_t uid_min = make_kuid(net->user_ns, info->uid_min);
|
||||
kuid_t uid_max = make_kuid(net->user_ns, info->uid_max);
|
||||
if ((uid_gte(filp->f_cred->fsuid, uid_min) &&
|
||||
uid_lte(filp->f_cred->fsuid, uid_max)) ^
|
||||
!(info->invert & XT_OWNER_UID))
|
||||
!(info->invert & XT_OWNER_UID)) {
|
||||
read_unlock_bh(&sk->sk_callback_lock);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if (info->match & XT_OWNER_GID) {
|
||||
@ -112,10 +117,13 @@ owner_mt(const struct sk_buff *skb, struct xt_action_param *par)
|
||||
}
|
||||
}
|
||||
|
||||
if (match ^ !(info->invert & XT_OWNER_GID))
|
||||
if (match ^ !(info->invert & XT_OWNER_GID)) {
|
||||
read_unlock_bh(&sk->sk_callback_lock);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
read_unlock_bh(&sk->sk_callback_lock);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user