netfilter: nf_tables: add NFTA_CHAIN_ID attribute
This netlink attribute allows you to refer to chains inside a transaction as an alternative to the name and the handle. The chain binding support requires this new chain ID approach. Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
This commit is contained in:
parent
f0a5e4d7a5
commit
74cccc3d38
@ -1433,6 +1433,7 @@ struct nft_trans_chain {
|
|||||||
char *name;
|
char *name;
|
||||||
struct nft_stats __percpu *stats;
|
struct nft_stats __percpu *stats;
|
||||||
u8 policy;
|
u8 policy;
|
||||||
|
u32 chain_id;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define nft_trans_chain_update(trans) \
|
#define nft_trans_chain_update(trans) \
|
||||||
@ -1443,6 +1444,8 @@ struct nft_trans_chain {
|
|||||||
(((struct nft_trans_chain *)trans->data)->stats)
|
(((struct nft_trans_chain *)trans->data)->stats)
|
||||||
#define nft_trans_chain_policy(trans) \
|
#define nft_trans_chain_policy(trans) \
|
||||||
(((struct nft_trans_chain *)trans->data)->policy)
|
(((struct nft_trans_chain *)trans->data)->policy)
|
||||||
|
#define nft_trans_chain_id(trans) \
|
||||||
|
(((struct nft_trans_chain *)trans->data)->chain_id)
|
||||||
|
|
||||||
struct nft_trans_table {
|
struct nft_trans_table {
|
||||||
bool update;
|
bool update;
|
||||||
|
@ -196,6 +196,7 @@ enum nft_table_attributes {
|
|||||||
* @NFTA_CHAIN_TYPE: type name of the string (NLA_NUL_STRING)
|
* @NFTA_CHAIN_TYPE: type name of the string (NLA_NUL_STRING)
|
||||||
* @NFTA_CHAIN_COUNTERS: counter specification of the chain (NLA_NESTED: nft_counter_attributes)
|
* @NFTA_CHAIN_COUNTERS: counter specification of the chain (NLA_NESTED: nft_counter_attributes)
|
||||||
* @NFTA_CHAIN_FLAGS: chain flags
|
* @NFTA_CHAIN_FLAGS: chain flags
|
||||||
|
* @NFTA_CHAIN_ID: uniquely identifies a chain in a transaction (NLA_U32)
|
||||||
*/
|
*/
|
||||||
enum nft_chain_attributes {
|
enum nft_chain_attributes {
|
||||||
NFTA_CHAIN_UNSPEC,
|
NFTA_CHAIN_UNSPEC,
|
||||||
@ -209,6 +210,7 @@ enum nft_chain_attributes {
|
|||||||
NFTA_CHAIN_COUNTERS,
|
NFTA_CHAIN_COUNTERS,
|
||||||
NFTA_CHAIN_PAD,
|
NFTA_CHAIN_PAD,
|
||||||
NFTA_CHAIN_FLAGS,
|
NFTA_CHAIN_FLAGS,
|
||||||
|
NFTA_CHAIN_ID,
|
||||||
__NFTA_CHAIN_MAX
|
__NFTA_CHAIN_MAX
|
||||||
};
|
};
|
||||||
#define NFTA_CHAIN_MAX (__NFTA_CHAIN_MAX - 1)
|
#define NFTA_CHAIN_MAX (__NFTA_CHAIN_MAX - 1)
|
||||||
|
@ -280,9 +280,15 @@ static struct nft_trans *nft_trans_chain_add(struct nft_ctx *ctx, int msg_type)
|
|||||||
if (trans == NULL)
|
if (trans == NULL)
|
||||||
return ERR_PTR(-ENOMEM);
|
return ERR_PTR(-ENOMEM);
|
||||||
|
|
||||||
if (msg_type == NFT_MSG_NEWCHAIN)
|
if (msg_type == NFT_MSG_NEWCHAIN) {
|
||||||
nft_activate_next(ctx->net, ctx->chain);
|
nft_activate_next(ctx->net, ctx->chain);
|
||||||
|
|
||||||
|
if (ctx->nla[NFTA_CHAIN_ID]) {
|
||||||
|
nft_trans_chain_id(trans) =
|
||||||
|
ntohl(nla_get_be32(ctx->nla[NFTA_CHAIN_ID]));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
list_add_tail(&trans->list, &ctx->net->nft.commit_list);
|
list_add_tail(&trans->list, &ctx->net->nft.commit_list);
|
||||||
return trans;
|
return trans;
|
||||||
}
|
}
|
||||||
@ -1274,6 +1280,7 @@ static const struct nla_policy nft_chain_policy[NFTA_CHAIN_MAX + 1] = {
|
|||||||
.len = NFT_MODULE_AUTOLOAD_LIMIT },
|
.len = NFT_MODULE_AUTOLOAD_LIMIT },
|
||||||
[NFTA_CHAIN_COUNTERS] = { .type = NLA_NESTED },
|
[NFTA_CHAIN_COUNTERS] = { .type = NLA_NESTED },
|
||||||
[NFTA_CHAIN_FLAGS] = { .type = NLA_U32 },
|
[NFTA_CHAIN_FLAGS] = { .type = NLA_U32 },
|
||||||
|
[NFTA_CHAIN_ID] = { .type = NLA_U32 },
|
||||||
};
|
};
|
||||||
|
|
||||||
static const struct nla_policy nft_hook_policy[NFTA_HOOK_MAX + 1] = {
|
static const struct nla_policy nft_hook_policy[NFTA_HOOK_MAX + 1] = {
|
||||||
@ -2154,9 +2161,9 @@ static int nf_tables_newchain(struct net *net, struct sock *nlsk,
|
|||||||
const struct nfgenmsg *nfmsg = nlmsg_data(nlh);
|
const struct nfgenmsg *nfmsg = nlmsg_data(nlh);
|
||||||
u8 genmask = nft_genmask_next(net);
|
u8 genmask = nft_genmask_next(net);
|
||||||
int family = nfmsg->nfgen_family;
|
int family = nfmsg->nfgen_family;
|
||||||
|
struct nft_chain *chain = NULL;
|
||||||
const struct nlattr *attr;
|
const struct nlattr *attr;
|
||||||
struct nft_table *table;
|
struct nft_table *table;
|
||||||
struct nft_chain *chain;
|
|
||||||
u8 policy = NF_ACCEPT;
|
u8 policy = NF_ACCEPT;
|
||||||
struct nft_ctx ctx;
|
struct nft_ctx ctx;
|
||||||
u64 handle = 0;
|
u64 handle = 0;
|
||||||
@ -2181,7 +2188,7 @@ static int nf_tables_newchain(struct net *net, struct sock *nlsk,
|
|||||||
return PTR_ERR(chain);
|
return PTR_ERR(chain);
|
||||||
}
|
}
|
||||||
attr = nla[NFTA_CHAIN_HANDLE];
|
attr = nla[NFTA_CHAIN_HANDLE];
|
||||||
} else {
|
} else if (nla[NFTA_CHAIN_NAME]) {
|
||||||
chain = nft_chain_lookup(net, table, attr, genmask);
|
chain = nft_chain_lookup(net, table, attr, genmask);
|
||||||
if (IS_ERR(chain)) {
|
if (IS_ERR(chain)) {
|
||||||
if (PTR_ERR(chain) != -ENOENT) {
|
if (PTR_ERR(chain) != -ENOENT) {
|
||||||
@ -2190,6 +2197,8 @@ static int nf_tables_newchain(struct net *net, struct sock *nlsk,
|
|||||||
}
|
}
|
||||||
chain = NULL;
|
chain = NULL;
|
||||||
}
|
}
|
||||||
|
} else if (!nla[NFTA_CHAIN_ID]) {
|
||||||
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (nla[NFTA_CHAIN_POLICY]) {
|
if (nla[NFTA_CHAIN_POLICY]) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user