aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLiping Zhang <liping.zhang@spreadtrum.com>2016-03-28 10:27:27 -0400
committerPablo Neira Ayuso <pablo@netfilter.org>2016-03-29 07:31:17 -0400
commit8fef24ca90fb79de8454e26e9f3eae6cc610de1a (patch)
tree8c77b8c042b62947691d6c07f1c2790e78613f2f
parent8d45ff22f1b43249f0cf1baafe0262ca10d1666e (diff)
netfilter: ip6t_SYNPROXY: remove magic number for hop_limit
Replace '64' with the per-net ipv6_devconf_all's hop_limit when building the ipv6 header. Signed-off-by: Liping Zhang <liping.zhang@spreadtrum.com> Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
-rw-r--r--net/ipv6/netfilter/ip6t_SYNPROXY.c56
1 files changed, 30 insertions, 26 deletions
diff --git a/net/ipv6/netfilter/ip6t_SYNPROXY.c b/net/ipv6/netfilter/ip6t_SYNPROXY.c
index 3deed5860a42..5d778dd11f66 100644
--- a/net/ipv6/netfilter/ip6t_SYNPROXY.c
+++ b/net/ipv6/netfilter/ip6t_SYNPROXY.c
@@ -20,15 +20,16 @@
20#include <net/netfilter/nf_conntrack_synproxy.h> 20#include <net/netfilter/nf_conntrack_synproxy.h>
21 21
22static struct ipv6hdr * 22static struct ipv6hdr *
23synproxy_build_ip(struct sk_buff *skb, const struct in6_addr *saddr, 23synproxy_build_ip(struct net *net, struct sk_buff *skb,
24 const struct in6_addr *daddr) 24 const struct in6_addr *saddr,
25 const struct in6_addr *daddr)
25{ 26{
26 struct ipv6hdr *iph; 27 struct ipv6hdr *iph;
27 28
28 skb_reset_network_header(skb); 29 skb_reset_network_header(skb);
29 iph = (struct ipv6hdr *)skb_put(skb, sizeof(*iph)); 30 iph = (struct ipv6hdr *)skb_put(skb, sizeof(*iph));
30 ip6_flow_hdr(iph, 0, 0); 31 ip6_flow_hdr(iph, 0, 0);
31 iph->hop_limit = 64; //XXX 32 iph->hop_limit = net->ipv6.devconf_all->hop_limit;
32 iph->nexthdr = IPPROTO_TCP; 33 iph->nexthdr = IPPROTO_TCP;
33 iph->saddr = *saddr; 34 iph->saddr = *saddr;
34 iph->daddr = *daddr; 35 iph->daddr = *daddr;
@@ -37,13 +38,12 @@ synproxy_build_ip(struct sk_buff *skb, const struct in6_addr *saddr,
37} 38}
38 39
39static void 40static void
40synproxy_send_tcp(const struct synproxy_net *snet, 41synproxy_send_tcp(struct net *net,
41 const struct sk_buff *skb, struct sk_buff *nskb, 42 const struct sk_buff *skb, struct sk_buff *nskb,
42 struct nf_conntrack *nfct, enum ip_conntrack_info ctinfo, 43 struct nf_conntrack *nfct, enum ip_conntrack_info ctinfo,
43 struct ipv6hdr *niph, struct tcphdr *nth, 44 struct ipv6hdr *niph, struct tcphdr *nth,
44 unsigned int tcp_hdr_size) 45 unsigned int tcp_hdr_size)
45{ 46{
46 struct net *net = nf_ct_net(snet->tmpl);
47 struct dst_entry *dst; 47 struct dst_entry *dst;
48 struct flowi6 fl6; 48 struct flowi6 fl6;
49 49
@@ -84,7 +84,7 @@ free_nskb:
84} 84}
85 85
86static void 86static void
87synproxy_send_client_synack(const struct synproxy_net *snet, 87synproxy_send_client_synack(struct net *net,
88 const struct sk_buff *skb, const struct tcphdr *th, 88 const struct sk_buff *skb, const struct tcphdr *th,
89 const struct synproxy_options *opts) 89 const struct synproxy_options *opts)
90{ 90{
@@ -103,7 +103,7 @@ synproxy_send_client_synack(const struct synproxy_net *snet,
103 return; 103 return;
104 skb_reserve(nskb, MAX_TCP_HEADER); 104 skb_reserve(nskb, MAX_TCP_HEADER);
105 105
106 niph = synproxy_build_ip(nskb, &iph->daddr, &iph->saddr); 106 niph = synproxy_build_ip(net, nskb, &iph->daddr, &iph->saddr);
107 107
108 skb_reset_transport_header(nskb); 108 skb_reset_transport_header(nskb);
109 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size); 109 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size);
@@ -121,15 +121,16 @@ synproxy_send_client_synack(const struct synproxy_net *snet,
121 121
122 synproxy_build_options(nth, opts); 122 synproxy_build_options(nth, opts);
123 123
124 synproxy_send_tcp(snet, skb, nskb, skb->nfct, IP_CT_ESTABLISHED_REPLY, 124 synproxy_send_tcp(net, skb, nskb, skb->nfct, IP_CT_ESTABLISHED_REPLY,
125 niph, nth, tcp_hdr_size); 125 niph, nth, tcp_hdr_size);
126} 126}
127 127
128static void 128static void
129synproxy_send_server_syn(const struct synproxy_net *snet, 129synproxy_send_server_syn(struct net *net,
130 const struct sk_buff *skb, const struct tcphdr *th, 130 const struct sk_buff *skb, const struct tcphdr *th,
131 const struct synproxy_options *opts, u32 recv_seq) 131 const struct synproxy_options *opts, u32 recv_seq)
132{ 132{
133 struct synproxy_net *snet = synproxy_pernet(net);
133 struct sk_buff *nskb; 134 struct sk_buff *nskb;
134 struct ipv6hdr *iph, *niph; 135 struct ipv6hdr *iph, *niph;
135 struct tcphdr *nth; 136 struct tcphdr *nth;
@@ -144,7 +145,7 @@ synproxy_send_server_syn(const struct synproxy_net *snet,
144 return; 145 return;
145 skb_reserve(nskb, MAX_TCP_HEADER); 146 skb_reserve(nskb, MAX_TCP_HEADER);
146 147
147 niph = synproxy_build_ip(nskb, &iph->saddr, &iph->daddr); 148 niph = synproxy_build_ip(net, nskb, &iph->saddr, &iph->daddr);
148 149
149 skb_reset_transport_header(nskb); 150 skb_reset_transport_header(nskb);
150 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size); 151 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size);
@@ -165,12 +166,12 @@ synproxy_send_server_syn(const struct synproxy_net *snet,
165 166
166 synproxy_build_options(nth, opts); 167 synproxy_build_options(nth, opts);
167 168
168 synproxy_send_tcp(snet, skb, nskb, &snet->tmpl->ct_general, IP_CT_NEW, 169 synproxy_send_tcp(net, skb, nskb, &snet->tmpl->ct_general, IP_CT_NEW,
169 niph, nth, tcp_hdr_size); 170 niph, nth, tcp_hdr_size);
170} 171}
171 172
172static void 173static void
173synproxy_send_server_ack(const struct synproxy_net *snet, 174synproxy_send_server_ack(struct net *net,
174 const struct ip_ct_tcp *state, 175 const struct ip_ct_tcp *state,
175 const struct sk_buff *skb, const struct tcphdr *th, 176 const struct sk_buff *skb, const struct tcphdr *th,
176 const struct synproxy_options *opts) 177 const struct synproxy_options *opts)
@@ -189,7 +190,7 @@ synproxy_send_server_ack(const struct synproxy_net *snet,
189 return; 190 return;
190 skb_reserve(nskb, MAX_TCP_HEADER); 191 skb_reserve(nskb, MAX_TCP_HEADER);
191 192
192 niph = synproxy_build_ip(nskb, &iph->daddr, &iph->saddr); 193 niph = synproxy_build_ip(net, nskb, &iph->daddr, &iph->saddr);
193 194
194 skb_reset_transport_header(nskb); 195 skb_reset_transport_header(nskb);
195 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size); 196 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size);
@@ -205,11 +206,11 @@ synproxy_send_server_ack(const struct synproxy_net *snet,
205 206
206 synproxy_build_options(nth, opts); 207 synproxy_build_options(nth, opts);
207 208
208 synproxy_send_tcp(snet, skb, nskb, NULL, 0, niph, nth, tcp_hdr_size); 209 synproxy_send_tcp(net, skb, nskb, NULL, 0, niph, nth, tcp_hdr_size);
209} 210}
210 211
211static void 212static void
212synproxy_send_client_ack(const struct synproxy_net *snet, 213synproxy_send_client_ack(struct net *net,
213 const struct sk_buff *skb, const struct tcphdr *th, 214 const struct sk_buff *skb, const struct tcphdr *th,
214 const struct synproxy_options *opts) 215 const struct synproxy_options *opts)
215{ 216{
@@ -227,7 +228,7 @@ synproxy_send_client_ack(const struct synproxy_net *snet,
227 return; 228 return;
228 skb_reserve(nskb, MAX_TCP_HEADER); 229 skb_reserve(nskb, MAX_TCP_HEADER);
229 230
230 niph = synproxy_build_ip(nskb, &iph->saddr, &iph->daddr); 231 niph = synproxy_build_ip(net, nskb, &iph->saddr, &iph->daddr);
231 232
232 skb_reset_transport_header(nskb); 233 skb_reset_transport_header(nskb);
233 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size); 234 nth = (struct tcphdr *)skb_put(nskb, tcp_hdr_size);
@@ -243,15 +244,16 @@ synproxy_send_client_ack(const struct synproxy_net *snet,
243 244
244 synproxy_build_options(nth, opts); 245 synproxy_build_options(nth, opts);
245 246
246 synproxy_send_tcp(snet, skb, nskb, skb->nfct, IP_CT_ESTABLISHED_REPLY, 247 synproxy_send_tcp(net, skb, nskb, skb->nfct, IP_CT_ESTABLISHED_REPLY,
247 niph, nth, tcp_hdr_size); 248 niph, nth, tcp_hdr_size);
248} 249}
249 250
250static bool 251static bool
251synproxy_recv_client_ack(const struct synproxy_net *snet, 252synproxy_recv_client_ack(struct net *net,
252 const struct sk_buff *skb, const struct tcphdr *th, 253 const struct sk_buff *skb, const struct tcphdr *th,
253 struct synproxy_options *opts, u32 recv_seq) 254 struct synproxy_options *opts, u32 recv_seq)
254{ 255{
256 struct synproxy_net *snet = synproxy_pernet(net);
255 int mss; 257 int mss;
256 258
257 mss = __cookie_v6_check(ipv6_hdr(skb), th, ntohl(th->ack_seq) - 1); 259 mss = __cookie_v6_check(ipv6_hdr(skb), th, ntohl(th->ack_seq) - 1);
@@ -267,7 +269,7 @@ synproxy_recv_client_ack(const struct synproxy_net *snet,
267 if (opts->options & XT_SYNPROXY_OPT_TIMESTAMP) 269 if (opts->options & XT_SYNPROXY_OPT_TIMESTAMP)
268 synproxy_check_timestamp_cookie(opts); 270 synproxy_check_timestamp_cookie(opts);
269 271
270 synproxy_send_server_syn(snet, skb, th, opts, recv_seq); 272 synproxy_send_server_syn(net, skb, th, opts, recv_seq);
271 return true; 273 return true;
272} 274}
273 275
@@ -275,7 +277,8 @@ static unsigned int
275synproxy_tg6(struct sk_buff *skb, const struct xt_action_param *par) 277synproxy_tg6(struct sk_buff *skb, const struct xt_action_param *par)
276{ 278{
277 const struct xt_synproxy_info *info = par->targinfo; 279 const struct xt_synproxy_info *info = par->targinfo;
278 struct synproxy_net *snet = synproxy_pernet(par->net); 280 struct net *net = par->net;
281 struct synproxy_net *snet = synproxy_pernet(net);
279 struct synproxy_options opts = {}; 282 struct synproxy_options opts = {};
280 struct tcphdr *th, _th; 283 struct tcphdr *th, _th;
281 284
@@ -304,12 +307,12 @@ synproxy_tg6(struct sk_buff *skb, const struct xt_action_param *par)
304 XT_SYNPROXY_OPT_SACK_PERM | 307 XT_SYNPROXY_OPT_SACK_PERM |
305 XT_SYNPROXY_OPT_ECN); 308 XT_SYNPROXY_OPT_ECN);
306 309
307 synproxy_send_client_synack(snet, skb, th, &opts); 310 synproxy_send_client_synack(net, skb, th, &opts);
308 return NF_DROP; 311 return NF_DROP;
309 312
310 } else if (th->ack && !(th->fin || th->rst || th->syn)) { 313 } else if (th->ack && !(th->fin || th->rst || th->syn)) {
311 /* ACK from client */ 314 /* ACK from client */
312 synproxy_recv_client_ack(snet, skb, th, &opts, ntohl(th->seq)); 315 synproxy_recv_client_ack(net, skb, th, &opts, ntohl(th->seq));
313 return NF_DROP; 316 return NF_DROP;
314 } 317 }
315 318
@@ -320,7 +323,8 @@ static unsigned int ipv6_synproxy_hook(void *priv,
320 struct sk_buff *skb, 323 struct sk_buff *skb,
321 const struct nf_hook_state *nhs) 324 const struct nf_hook_state *nhs)
322{ 325{
323 struct synproxy_net *snet = synproxy_pernet(nhs->net); 326 struct net *net = nhs->net;
327 struct synproxy_net *snet = synproxy_pernet(net);
324 enum ip_conntrack_info ctinfo; 328 enum ip_conntrack_info ctinfo;
325 struct nf_conn *ct; 329 struct nf_conn *ct;
326 struct nf_conn_synproxy *synproxy; 330 struct nf_conn_synproxy *synproxy;
@@ -384,7 +388,7 @@ static unsigned int ipv6_synproxy_hook(void *priv,
384 * therefore we need to add 1 to make the SYN sequence 388 * therefore we need to add 1 to make the SYN sequence
385 * number match the one of first SYN. 389 * number match the one of first SYN.
386 */ 390 */
387 if (synproxy_recv_client_ack(snet, skb, th, &opts, 391 if (synproxy_recv_client_ack(net, skb, th, &opts,
388 ntohl(th->seq) + 1)) 392 ntohl(th->seq) + 1))
389 this_cpu_inc(snet->stats->cookie_retrans); 393 this_cpu_inc(snet->stats->cookie_retrans);
390 394
@@ -410,12 +414,12 @@ static unsigned int ipv6_synproxy_hook(void *priv,
410 XT_SYNPROXY_OPT_SACK_PERM); 414 XT_SYNPROXY_OPT_SACK_PERM);
411 415
412 swap(opts.tsval, opts.tsecr); 416 swap(opts.tsval, opts.tsecr);
413 synproxy_send_server_ack(snet, state, skb, th, &opts); 417 synproxy_send_server_ack(net, state, skb, th, &opts);
414 418
415 nf_ct_seqadj_init(ct, ctinfo, synproxy->isn - ntohl(th->seq)); 419 nf_ct_seqadj_init(ct, ctinfo, synproxy->isn - ntohl(th->seq));
416 420
417 swap(opts.tsval, opts.tsecr); 421 swap(opts.tsval, opts.tsecr);
418 synproxy_send_client_ack(snet, skb, th, &opts); 422 synproxy_send_client_ack(net, skb, th, &opts);
419 423
420 consume_skb(skb); 424 consume_skb(skb);
421 return NF_STOLEN; 425 return NF_STOLEN;