Skip to content

Commit f2a6d76

Browse files
committed
netfilter: nf_tables: add generation mask to tables
This patch addresses two problems: 1) The netlink dump is inconsistent when interfering with an ongoing transaction update for several reasons: 1.a) We don't honor the internal NFT_TABLE_INACTIVE flag, and we should be skipping these inactive objects in the dump. 1.b) We perform speculative deletion during the preparation phase, that may result in skipping active objects. 1.c) The listing order changes, which generates noise when tracking incremental ruleset update via tools like git or our own testsuite. 2) We don't allow to add and to update the object in the same batch, eg. add table x; add table x { flags dormant\; }. In order to resolve these problems: 1) If the user requests a deletion, the object becomes inactive in the next generation. Then, ignore objects that scheduled to be deleted from the lookup path, as they will be effectively removed in the next generation. 2) From the get/dump path, if the object is not currently active, we skip it. 3) Support 'add X -> update X' sequence from a transaction. After this update, we obtain a consistent list as long as we stay in the same generation. The userspace side can detect interferences through the generation counter so it can restart the dumping. Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
1 parent 889f7ee commit f2a6d76

File tree

2 files changed

+62
-45
lines changed

2 files changed

+62
-45
lines changed

include/net/netfilter/nf_tables.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -838,6 +838,7 @@ unsigned int nft_do_chain(struct nft_pktinfo *pkt, void *priv);
838838
* @hgenerator: handle generator state
839839
* @use: number of chain references to this table
840840
* @flags: table flag (see enum nft_table_flags)
841+
* @genmask: generation mask
841842
* @name: name of the table
842843
*/
843844
struct nft_table {
@@ -846,7 +847,8 @@ struct nft_table {
846847
struct list_head sets;
847848
u64 hgenerator;
848849
u32 use;
849-
u16 flags;
850+
u16 flags:14,
851+
genmask:2;
850852
char name[NFT_TABLE_MAXNAMELEN];
851853
};
852854

@@ -992,6 +994,8 @@ static inline u8 nft_genmask_cur(const struct net *net)
992994
/* After committing the ruleset, clear the stale generation bit. */
993995
#define nft_clear(__net, __obj) \
994996
(__obj)->genmask &= ~nft_genmask_next(__net)
997+
#define nft_active_genmask(__obj, __genmask) \
998+
!((__obj)->genmask & __genmask)
995999

9961000
/*
9971001
* Set element transaction helpers

0 commit comments

Comments
 (0)