1 // SPDX-License-Identifier: GPL-2.0-only 2 #if IS_ENABLED(CONFIG_NFT_CT) 3 #include <linux/netfilter/nf_tables.h> 4 #include <net/netfilter/nf_tables_core.h> 5 #include <net/netfilter/nf_conntrack.h> 6 nft_ct_get_fast_eval(const struct nft_expr * expr,struct nft_regs * regs,const struct nft_pktinfo * pkt)7void nft_ct_get_fast_eval(const struct nft_expr *expr, 8 struct nft_regs *regs, 9 const struct nft_pktinfo *pkt) 10 { 11 const struct nft_ct *priv = nft_expr_priv(expr); 12 u32 *dest = ®s->data[priv->dreg]; 13 enum ip_conntrack_info ctinfo; 14 const struct nf_conn *ct; 15 unsigned int state; 16 17 ct = nf_ct_get(pkt->skb, &ctinfo); 18 19 switch (priv->key) { 20 case NFT_CT_STATE: 21 if (ct) 22 state = NF_CT_STATE_BIT(ctinfo); 23 else if (ctinfo == IP_CT_UNTRACKED) 24 state = NF_CT_STATE_UNTRACKED_BIT; 25 else 26 state = NF_CT_STATE_INVALID_BIT; 27 *dest = state; 28 return; 29 default: 30 break; 31 } 32 33 if (!ct) { 34 regs->verdict.code = NFT_BREAK; 35 return; 36 } 37 38 switch (priv->key) { 39 case NFT_CT_DIRECTION: 40 nft_reg_store8(dest, CTINFO2DIR(ctinfo)); 41 return; 42 case NFT_CT_STATUS: 43 *dest = ct->status; 44 return; 45 #ifdef CONFIG_NF_CONNTRACK_MARK 46 case NFT_CT_MARK: 47 *dest = ct->mark; 48 return; 49 #endif 50 #ifdef CONFIG_NF_CONNTRACK_SECMARK 51 case NFT_CT_SECMARK: 52 *dest = ct->secmark; 53 return; 54 #endif 55 default: 56 WARN_ON_ONCE(1); 57 regs->verdict.code = NFT_BREAK; 58 break; 59 } 60 } 61 EXPORT_SYMBOL_GPL(nft_ct_get_fast_eval); 62 #endif 63