diff options
author | Jan Engelhardt <jengelh@computergmbh.de> | 2008-01-31 06:58:24 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-01-31 22:27:31 -0500 |
commit | b41649989c9640e54e47001994b7ecb927ea1822 (patch) | |
tree | 4c733dd12a1d8f95ac05c431fb64a1eb7cd7e59e /net | |
parent | 41d0cdedd5d0a067069a1559315aa9bfdf00794a (diff) |
[NETFILTER]: xt_conntrack: add port and direction matching
Extend the xt_conntrack match revision 1 by port matching (all four
{orig,repl}{src,dst}) and by packet direction matching.
Signed-off-by: Jan Engelhardt <jengelh@computergmbh.de>
Signed-off-by: Patrick McHardy <kaber@trash.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net')
-rw-r--r-- | net/netfilter/xt_conntrack.c | 50 |
1 files changed, 45 insertions, 5 deletions
diff --git a/net/netfilter/xt_conntrack.c b/net/netfilter/xt_conntrack.c index e92190eafcc5..85330856a29c 100644 --- a/net/netfilter/xt_conntrack.c +++ b/net/netfilter/xt_conntrack.c | |||
@@ -4,7 +4,6 @@ | |||
4 | * | 4 | * |
5 | * (C) 2001 Marc Boucher (marc@mbsi.ca). | 5 | * (C) 2001 Marc Boucher (marc@mbsi.ca). |
6 | * Copyright © CC Computer Consultants GmbH, 2007 - 2008 | 6 | * Copyright © CC Computer Consultants GmbH, 2007 - 2008 |
7 | * Jan Engelhardt <jengelh@computergmbh.de> | ||
8 | * | 7 | * |
9 | * This program is free software; you can redistribute it and/or modify | 8 | * This program is free software; you can redistribute it and/or modify |
10 | * it under the terms of the GNU General Public License version 2 as | 9 | * it under the terms of the GNU General Public License version 2 as |
@@ -20,6 +19,7 @@ | |||
20 | 19 | ||
21 | MODULE_LICENSE("GPL"); | 20 | MODULE_LICENSE("GPL"); |
22 | MODULE_AUTHOR("Marc Boucher <marc@mbsi.ca>"); | 21 | MODULE_AUTHOR("Marc Boucher <marc@mbsi.ca>"); |
22 | MODULE_AUTHOR("Jan Engelhardt <jengelh@computergmbh.de>"); | ||
23 | MODULE_DESCRIPTION("Xtables: connection tracking state match"); | 23 | MODULE_DESCRIPTION("Xtables: connection tracking state match"); |
24 | MODULE_ALIAS("ipt_conntrack"); | 24 | MODULE_ALIAS("ipt_conntrack"); |
25 | MODULE_ALIAS("ip6t_conntrack"); | 25 | MODULE_ALIAS("ip6t_conntrack"); |
@@ -166,6 +166,44 @@ conntrack_mt_repldst(const struct nf_conn *ct, | |||
166 | &info->repldst_addr, &info->repldst_mask, family); | 166 | &info->repldst_addr, &info->repldst_mask, family); |
167 | } | 167 | } |
168 | 168 | ||
169 | static inline bool | ||
170 | ct_proto_port_check(const struct xt_conntrack_mtinfo1 *info, | ||
171 | const struct nf_conn *ct) | ||
172 | { | ||
173 | const struct nf_conntrack_tuple *tuple; | ||
174 | |||
175 | tuple = &ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple; | ||
176 | if ((info->match_flags & XT_CONNTRACK_PROTO) && | ||
177 | (tuple->dst.protonum == info->l4proto) ^ | ||
178 | !(info->invert_flags & XT_CONNTRACK_PROTO)) | ||
179 | return false; | ||
180 | |||
181 | /* Shortcut to match all recognized protocols by using ->src.all. */ | ||
182 | if ((info->match_flags & XT_CONNTRACK_ORIGSRC_PORT) && | ||
183 | (tuple->src.u.all == info->origsrc_port) ^ | ||
184 | !(info->invert_flags & XT_CONNTRACK_ORIGSRC_PORT)) | ||
185 | return false; | ||
186 | |||
187 | if ((info->match_flags & XT_CONNTRACK_ORIGDST_PORT) && | ||
188 | (tuple->dst.u.all == info->origdst_port) ^ | ||
189 | !(info->invert_flags & XT_CONNTRACK_ORIGDST_PORT)) | ||
190 | return false; | ||
191 | |||
192 | tuple = &ct->tuplehash[IP_CT_DIR_REPLY].tuple; | ||
193 | |||
194 | if ((info->match_flags & XT_CONNTRACK_REPLSRC_PORT) && | ||
195 | (tuple->src.u.all == info->replsrc_port) ^ | ||
196 | !(info->invert_flags & XT_CONNTRACK_REPLSRC_PORT)) | ||
197 | return false; | ||
198 | |||
199 | if ((info->match_flags & XT_CONNTRACK_REPLDST_PORT) && | ||
200 | (tuple->dst.u.all == info->repldst_port) ^ | ||
201 | !(info->invert_flags & XT_CONNTRACK_REPLDST_PORT)) | ||
202 | return false; | ||
203 | |||
204 | return true; | ||
205 | } | ||
206 | |||
169 | static bool | 207 | static bool |
170 | conntrack_mt(const struct sk_buff *skb, const struct net_device *in, | 208 | conntrack_mt(const struct sk_buff *skb, const struct net_device *in, |
171 | const struct net_device *out, const struct xt_match *match, | 209 | const struct net_device *out, const struct xt_match *match, |
@@ -200,10 +238,9 @@ conntrack_mt(const struct sk_buff *skb, const struct net_device *in, | |||
200 | 238 | ||
201 | if (ct == NULL) | 239 | if (ct == NULL) |
202 | return info->match_flags & XT_CONNTRACK_STATE; | 240 | return info->match_flags & XT_CONNTRACK_STATE; |
203 | 241 | if ((info->match_flags & XT_CONNTRACK_DIRECTION) && | |
204 | if ((info->match_flags & XT_CONNTRACK_PROTO) && | 242 | (CTINFO2DIR(ctinfo) == IP_CT_DIR_ORIGINAL) ^ |
205 | ((ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple.dst.protonum == | 243 | !!(info->invert_flags & XT_CONNTRACK_DIRECTION)) |
206 | info->l4proto) ^ !(info->invert_flags & XT_CONNTRACK_PROTO))) | ||
207 | return false; | 244 | return false; |
208 | 245 | ||
209 | if (info->match_flags & XT_CONNTRACK_ORIGSRC) | 246 | if (info->match_flags & XT_CONNTRACK_ORIGSRC) |
@@ -226,6 +263,9 @@ conntrack_mt(const struct sk_buff *skb, const struct net_device *in, | |||
226 | !(info->invert_flags & XT_CONNTRACK_REPLDST)) | 263 | !(info->invert_flags & XT_CONNTRACK_REPLDST)) |
227 | return false; | 264 | return false; |
228 | 265 | ||
266 | if (!ct_proto_port_check(info, ct)) | ||
267 | return false; | ||
268 | |||
229 | if ((info->match_flags & XT_CONNTRACK_STATUS) && | 269 | if ((info->match_flags & XT_CONNTRACK_STATUS) && |
230 | (!!(info->status_mask & ct->status) ^ | 270 | (!!(info->status_mask & ct->status) ^ |
231 | !(info->invert_flags & XT_CONNTRACK_STATUS))) | 271 | !(info->invert_flags & XT_CONNTRACK_STATUS))) |