4 #include <net/netfilter/nf_tables.h>
5 #include <linux/netfilter/nfnetlink_osf.h>
8 enum nft_registers dreg
:8;
12 static const struct nla_policy nft_osf_policy
[NFTA_OSF_MAX
+ 1] = {
13 [NFTA_OSF_DREG
] = { .type
= NLA_U32
},
14 [NFTA_OSF_TTL
] = { .type
= NLA_U8
},
17 static void nft_osf_eval(const struct nft_expr
*expr
, struct nft_regs
*regs
,
18 const struct nft_pktinfo
*pkt
)
20 struct nft_osf
*priv
= nft_expr_priv(expr
);
21 u32
*dest
= ®s
->data
[priv
->dreg
];
22 struct sk_buff
*skb
= pkt
->skb
;
23 const struct tcphdr
*tcp
;
27 tcp
= skb_header_pointer(skb
, ip_hdrlen(skb
),
28 sizeof(struct tcphdr
), &_tcph
);
30 regs
->verdict
.code
= NFT_BREAK
;
34 regs
->verdict
.code
= NFT_BREAK
;
38 os_name
= nf_osf_find(skb
, nf_osf_fingers
, priv
->ttl
);
40 strncpy((char *)dest
, "unknown", NFT_OSF_MAXGENRELEN
);
42 strncpy((char *)dest
, os_name
, NFT_OSF_MAXGENRELEN
);
45 static int nft_osf_init(const struct nft_ctx
*ctx
,
46 const struct nft_expr
*expr
,
47 const struct nlattr
* const tb
[])
49 struct nft_osf
*priv
= nft_expr_priv(expr
);
53 if (tb
[NFTA_OSF_TTL
]) {
54 ttl
= nla_get_u8(tb
[NFTA_OSF_TTL
]);
60 priv
->dreg
= nft_parse_register(tb
[NFTA_OSF_DREG
]);
61 err
= nft_validate_register_store(ctx
, priv
->dreg
, NULL
,
62 NFT_DATA_VALUE
, NFT_OSF_MAXGENRELEN
);
69 static int nft_osf_dump(struct sk_buff
*skb
, const struct nft_expr
*expr
)
71 const struct nft_osf
*priv
= nft_expr_priv(expr
);
73 if (nla_put_u8(skb
, NFTA_OSF_TTL
, priv
->ttl
))
76 if (nft_dump_register(skb
, NFTA_OSF_DREG
, priv
->dreg
))
85 static int nft_osf_validate(const struct nft_ctx
*ctx
,
86 const struct nft_expr
*expr
,
87 const struct nft_data
**data
)
89 return nft_chain_validate_hooks(ctx
->chain
, (1 << NF_INET_LOCAL_IN
) |
90 (1 << NF_INET_PRE_ROUTING
) |
91 (1 << NF_INET_FORWARD
));
94 static struct nft_expr_type nft_osf_type
;
95 static const struct nft_expr_ops nft_osf_op
= {
97 .size
= NFT_EXPR_SIZE(sizeof(struct nft_osf
)),
100 .type
= &nft_osf_type
,
101 .validate
= nft_osf_validate
,
104 static struct nft_expr_type nft_osf_type __read_mostly
= {
107 .owner
= THIS_MODULE
,
108 .policy
= nft_osf_policy
,
109 .maxattr
= NFTA_OSF_MAX
,
112 static int __init
nft_osf_module_init(void)
114 return nft_register_expr(&nft_osf_type
);
117 static void __exit
nft_osf_module_exit(void)
119 return nft_unregister_expr(&nft_osf_type
);
122 module_init(nft_osf_module_init
);
123 module_exit(nft_osf_module_exit
);
125 MODULE_LICENSE("GPL");
126 MODULE_AUTHOR("Fernando Fernandez <ffmancera@riseup.net>");
127 MODULE_ALIAS_NFT_EXPR("osf");