5531d569aa5e39eef5e8fb7f937b6417d515ac0d
[pandora-kernel.git] / net / netfilter / ipvs / ip_vs_core.c
1 /*
2  * IPVS         An implementation of the IP virtual server support for the
3  *              LINUX operating system.  IPVS is now implemented as a module
4  *              over the Netfilter framework. IPVS can be used to build a
5  *              high-performance and highly available server based on a
6  *              cluster of servers.
7  *
8  * Authors:     Wensong Zhang <wensong@linuxvirtualserver.org>
9  *              Peter Kese <peter.kese@ijs.si>
10  *              Julian Anastasov <ja@ssi.bg>
11  *
12  *              This program is free software; you can redistribute it and/or
13  *              modify it under the terms of the GNU General Public License
14  *              as published by the Free Software Foundation; either version
15  *              2 of the License, or (at your option) any later version.
16  *
17  * The IPVS code for kernel 2.2 was done by Wensong Zhang and Peter Kese,
18  * with changes/fixes from Julian Anastasov, Lars Marowsky-Bree, Horms
19  * and others.
20  *
21  * Changes:
22  *      Paul `Rusty' Russell            properly handle non-linear skbs
23  *      Harald Welte                    don't use nfcache
24  *
25  */
26
27 #define KMSG_COMPONENT "IPVS"
28 #define pr_fmt(fmt) KMSG_COMPONENT ": " fmt
29
30 #include <linux/module.h>
31 #include <linux/kernel.h>
32 #include <linux/ip.h>
33 #include <linux/tcp.h>
34 #include <linux/sctp.h>
35 #include <linux/icmp.h>
36 #include <linux/slab.h>
37
38 #include <net/ip.h>
39 #include <net/tcp.h>
40 #include <net/udp.h>
41 #include <net/icmp.h>                   /* for icmp_send */
42 #include <net/route.h>
43 #include <net/ip6_checksum.h>
44 #include <net/netns/generic.h>          /* net_generic() */
45
46 #include <linux/netfilter.h>
47 #include <linux/netfilter_ipv4.h>
48
49 #ifdef CONFIG_IP_VS_IPV6
50 #include <net/ipv6.h>
51 #include <linux/netfilter_ipv6.h>
52 #include <net/ip6_route.h>
53 #endif
54
55 #include <net/ip_vs.h>
56
57
58 EXPORT_SYMBOL(register_ip_vs_scheduler);
59 EXPORT_SYMBOL(unregister_ip_vs_scheduler);
60 EXPORT_SYMBOL(ip_vs_proto_name);
61 EXPORT_SYMBOL(ip_vs_conn_new);
62 EXPORT_SYMBOL(ip_vs_conn_in_get);
63 EXPORT_SYMBOL(ip_vs_conn_out_get);
64 #ifdef CONFIG_IP_VS_PROTO_TCP
65 EXPORT_SYMBOL(ip_vs_tcp_conn_listen);
66 #endif
67 EXPORT_SYMBOL(ip_vs_conn_put);
68 #ifdef CONFIG_IP_VS_DEBUG
69 EXPORT_SYMBOL(ip_vs_get_debug_level);
70 #endif
71
72 int ip_vs_net_id __read_mostly;
73 #ifdef IP_VS_GENERIC_NETNS
74 EXPORT_SYMBOL(ip_vs_net_id);
75 #endif
76 /* netns cnt used for uniqueness */
77 static atomic_t ipvs_netns_cnt = ATOMIC_INIT(0);
78
79 /* ID used in ICMP lookups */
80 #define icmp_id(icmph)          (((icmph)->un).echo.id)
81 #define icmpv6_id(icmph)        (icmph->icmp6_dataun.u_echo.identifier)
82
83 const char *ip_vs_proto_name(unsigned proto)
84 {
85         static char buf[20];
86
87         switch (proto) {
88         case IPPROTO_IP:
89                 return "IP";
90         case IPPROTO_UDP:
91                 return "UDP";
92         case IPPROTO_TCP:
93                 return "TCP";
94         case IPPROTO_SCTP:
95                 return "SCTP";
96         case IPPROTO_ICMP:
97                 return "ICMP";
98 #ifdef CONFIG_IP_VS_IPV6
99         case IPPROTO_ICMPV6:
100                 return "ICMPv6";
101 #endif
102         default:
103                 sprintf(buf, "IP_%d", proto);
104                 return buf;
105         }
106 }
107
108 void ip_vs_init_hash_table(struct list_head *table, int rows)
109 {
110         while (--rows >= 0)
111                 INIT_LIST_HEAD(&table[rows]);
112 }
113
114 static inline void
115 ip_vs_in_stats(struct ip_vs_conn *cp, struct sk_buff *skb)
116 {
117         struct ip_vs_dest *dest = cp->dest;
118         if (dest && (dest->flags & IP_VS_DEST_F_AVAILABLE)) {
119                 spin_lock(&dest->stats.lock);
120                 dest->stats.ustats.inpkts++;
121                 dest->stats.ustats.inbytes += skb->len;
122                 spin_unlock(&dest->stats.lock);
123
124                 spin_lock(&dest->svc->stats.lock);
125                 dest->svc->stats.ustats.inpkts++;
126                 dest->svc->stats.ustats.inbytes += skb->len;
127                 spin_unlock(&dest->svc->stats.lock);
128
129                 spin_lock(&ip_vs_stats.lock);
130                 ip_vs_stats.ustats.inpkts++;
131                 ip_vs_stats.ustats.inbytes += skb->len;
132                 spin_unlock(&ip_vs_stats.lock);
133         }
134 }
135
136
137 static inline void
138 ip_vs_out_stats(struct ip_vs_conn *cp, struct sk_buff *skb)
139 {
140         struct ip_vs_dest *dest = cp->dest;
141         if (dest && (dest->flags & IP_VS_DEST_F_AVAILABLE)) {
142                 spin_lock(&dest->stats.lock);
143                 dest->stats.ustats.outpkts++;
144                 dest->stats.ustats.outbytes += skb->len;
145                 spin_unlock(&dest->stats.lock);
146
147                 spin_lock(&dest->svc->stats.lock);
148                 dest->svc->stats.ustats.outpkts++;
149                 dest->svc->stats.ustats.outbytes += skb->len;
150                 spin_unlock(&dest->svc->stats.lock);
151
152                 spin_lock(&ip_vs_stats.lock);
153                 ip_vs_stats.ustats.outpkts++;
154                 ip_vs_stats.ustats.outbytes += skb->len;
155                 spin_unlock(&ip_vs_stats.lock);
156         }
157 }
158
159
160 static inline void
161 ip_vs_conn_stats(struct ip_vs_conn *cp, struct ip_vs_service *svc)
162 {
163         spin_lock(&cp->dest->stats.lock);
164         cp->dest->stats.ustats.conns++;
165         spin_unlock(&cp->dest->stats.lock);
166
167         spin_lock(&svc->stats.lock);
168         svc->stats.ustats.conns++;
169         spin_unlock(&svc->stats.lock);
170
171         spin_lock(&ip_vs_stats.lock);
172         ip_vs_stats.ustats.conns++;
173         spin_unlock(&ip_vs_stats.lock);
174 }
175
176
177 static inline int
178 ip_vs_set_state(struct ip_vs_conn *cp, int direction,
179                 const struct sk_buff *skb,
180                 struct ip_vs_proto_data *pd)
181 {
182         if (unlikely(!pd->pp->state_transition))
183                 return 0;
184         return pd->pp->state_transition(cp, direction, skb, pd);
185 }
186
187 static inline int
188 ip_vs_conn_fill_param_persist(const struct ip_vs_service *svc,
189                               struct sk_buff *skb, int protocol,
190                               const union nf_inet_addr *caddr, __be16 cport,
191                               const union nf_inet_addr *vaddr, __be16 vport,
192                               struct ip_vs_conn_param *p)
193 {
194         ip_vs_conn_fill_param(svc->af, protocol, caddr, cport, vaddr, vport, p);
195         p->pe = svc->pe;
196         if (p->pe && p->pe->fill_param)
197                 return p->pe->fill_param(p, skb);
198
199         return 0;
200 }
201
202 /*
203  *  IPVS persistent scheduling function
204  *  It creates a connection entry according to its template if exists,
205  *  or selects a server and creates a connection entry plus a template.
206  *  Locking: we are svc user (svc->refcnt), so we hold all dests too
207  *  Protocols supported: TCP, UDP
208  */
209 static struct ip_vs_conn *
210 ip_vs_sched_persist(struct ip_vs_service *svc,
211                     struct sk_buff *skb,
212                     __be16 src_port, __be16 dst_port, int *ignored)
213 {
214         struct ip_vs_conn *cp = NULL;
215         struct ip_vs_iphdr iph;
216         struct ip_vs_dest *dest;
217         struct ip_vs_conn *ct;
218         __be16 dport = 0;               /* destination port to forward */
219         unsigned int flags;
220         struct ip_vs_conn_param param;
221         union nf_inet_addr snet;        /* source network of the client,
222                                            after masking */
223
224         ip_vs_fill_iphdr(svc->af, skb_network_header(skb), &iph);
225
226         /* Mask saddr with the netmask to adjust template granularity */
227 #ifdef CONFIG_IP_VS_IPV6
228         if (svc->af == AF_INET6)
229                 ipv6_addr_prefix(&snet.in6, &iph.saddr.in6, svc->netmask);
230         else
231 #endif
232                 snet.ip = iph.saddr.ip & svc->netmask;
233
234         IP_VS_DBG_BUF(6, "p-schedule: src %s:%u dest %s:%u "
235                       "mnet %s\n",
236                       IP_VS_DBG_ADDR(svc->af, &iph.saddr), ntohs(src_port),
237                       IP_VS_DBG_ADDR(svc->af, &iph.daddr), ntohs(dst_port),
238                       IP_VS_DBG_ADDR(svc->af, &snet));
239
240         /*
241          * As far as we know, FTP is a very complicated network protocol, and
242          * it uses control connection and data connections. For active FTP,
243          * FTP server initialize data connection to the client, its source port
244          * is often 20. For passive FTP, FTP server tells the clients the port
245          * that it passively listens to,  and the client issues the data
246          * connection. In the tunneling or direct routing mode, the load
247          * balancer is on the client-to-server half of connection, the port
248          * number is unknown to the load balancer. So, a conn template like
249          * <caddr, 0, vaddr, 0, daddr, 0> is created for persistent FTP
250          * service, and a template like <caddr, 0, vaddr, vport, daddr, dport>
251          * is created for other persistent services.
252          */
253         {
254                 int protocol = iph.protocol;
255                 const union nf_inet_addr *vaddr = &iph.daddr;
256                 const union nf_inet_addr fwmark = { .ip = htonl(svc->fwmark) };
257                 __be16 vport = 0;
258
259                 if (dst_port == svc->port) {
260                         /* non-FTP template:
261                          * <protocol, caddr, 0, vaddr, vport, daddr, dport>
262                          * FTP template:
263                          * <protocol, caddr, 0, vaddr, 0, daddr, 0>
264                          */
265                         if (svc->port != FTPPORT)
266                                 vport = dst_port;
267                 } else {
268                         /* Note: persistent fwmark-based services and
269                          * persistent port zero service are handled here.
270                          * fwmark template:
271                          * <IPPROTO_IP,caddr,0,fwmark,0,daddr,0>
272                          * port zero template:
273                          * <protocol,caddr,0,vaddr,0,daddr,0>
274                          */
275                         if (svc->fwmark) {
276                                 protocol = IPPROTO_IP;
277                                 vaddr = &fwmark;
278                         }
279                 }
280                 /* return *ignored = -1 so NF_DROP can be used */
281                 if (ip_vs_conn_fill_param_persist(svc, skb, protocol, &snet, 0,
282                                                   vaddr, vport, &param) < 0) {
283                         *ignored = -1;
284                         return NULL;
285                 }
286         }
287
288         /* Check if a template already exists */
289         ct = ip_vs_ct_in_get(&param);
290         if (!ct || !ip_vs_check_template(ct)) {
291                 /*
292                  * No template found or the dest of the connection
293                  * template is not available.
294                  * return *ignored=0 i.e. ICMP and NF_DROP
295                  */
296                 dest = svc->scheduler->schedule(svc, skb);
297                 if (!dest) {
298                         IP_VS_DBG(1, "p-schedule: no dest found.\n");
299                         kfree(param.pe_data);
300                         *ignored = 0;
301                         return NULL;
302                 }
303
304                 if (dst_port == svc->port && svc->port != FTPPORT)
305                         dport = dest->port;
306
307                 /* Create a template
308                  * This adds param.pe_data to the template,
309                  * and thus param.pe_data will be destroyed
310                  * when the template expires */
311                 ct = ip_vs_conn_new(&param, &dest->addr, dport,
312                                     IP_VS_CONN_F_TEMPLATE, dest, skb->mark);
313                 if (ct == NULL) {
314                         kfree(param.pe_data);
315                         *ignored = -1;
316                         return NULL;
317                 }
318
319                 ct->timeout = svc->timeout;
320         } else {
321                 /* set destination with the found template */
322                 dest = ct->dest;
323                 kfree(param.pe_data);
324         }
325
326         dport = dst_port;
327         if (dport == svc->port && dest->port)
328                 dport = dest->port;
329
330         flags = (svc->flags & IP_VS_SVC_F_ONEPACKET
331                  && iph.protocol == IPPROTO_UDP)?
332                 IP_VS_CONN_F_ONE_PACKET : 0;
333
334         /*
335          *    Create a new connection according to the template
336          */
337         ip_vs_conn_fill_param(svc->af, iph.protocol, &iph.saddr, src_port,
338                               &iph.daddr, dst_port, &param);
339
340         cp = ip_vs_conn_new(&param, &dest->addr, dport, flags, dest, skb->mark);
341         if (cp == NULL) {
342                 ip_vs_conn_put(ct);
343                 *ignored = -1;
344                 return NULL;
345         }
346
347         /*
348          *    Add its control
349          */
350         ip_vs_control_add(cp, ct);
351         ip_vs_conn_put(ct);
352
353         ip_vs_conn_stats(cp, svc);
354         return cp;
355 }
356
357
358 /*
359  *  IPVS main scheduling function
360  *  It selects a server according to the virtual service, and
361  *  creates a connection entry.
362  *  Protocols supported: TCP, UDP
363  *
364  *  Usage of *ignored
365  *
366  * 1 :   protocol tried to schedule (eg. on SYN), found svc but the
367  *       svc/scheduler decides that this packet should be accepted with
368  *       NF_ACCEPT because it must not be scheduled.
369  *
370  * 0 :   scheduler can not find destination, so try bypass or
371  *       return ICMP and then NF_DROP (ip_vs_leave).
372  *
373  * -1 :  scheduler tried to schedule but fatal error occurred, eg.
374  *       ip_vs_conn_new failure (ENOMEM) or ip_vs_sip_fill_param
375  *       failure such as missing Call-ID, ENOMEM on skb_linearize
376  *       or pe_data. In this case we should return NF_DROP without
377  *       any attempts to send ICMP with ip_vs_leave.
378  */
379 struct ip_vs_conn *
380 ip_vs_schedule(struct ip_vs_service *svc, struct sk_buff *skb,
381                struct ip_vs_proto_data *pd, int *ignored)
382 {
383         struct ip_vs_protocol *pp = pd->pp;
384         struct ip_vs_conn *cp = NULL;
385         struct ip_vs_iphdr iph;
386         struct ip_vs_dest *dest;
387         __be16 _ports[2], *pptr;
388         unsigned int flags;
389
390         *ignored = 1;
391         ip_vs_fill_iphdr(svc->af, skb_network_header(skb), &iph);
392         pptr = skb_header_pointer(skb, iph.len, sizeof(_ports), _ports);
393         if (pptr == NULL)
394                 return NULL;
395
396         /*
397          * FTPDATA needs this check when using local real server.
398          * Never schedule Active FTPDATA connections from real server.
399          * For LVS-NAT they must be already created. For other methods
400          * with persistence the connection is created on SYN+ACK.
401          */
402         if (pptr[0] == FTPDATA) {
403                 IP_VS_DBG_PKT(12, svc->af, pp, skb, 0,
404                               "Not scheduling FTPDATA");
405                 return NULL;
406         }
407
408         /*
409          *    Do not schedule replies from local real server.
410          */
411         if ((!skb->dev || skb->dev->flags & IFF_LOOPBACK) &&
412             (cp = pp->conn_in_get(svc->af, skb, &iph, iph.len, 1))) {
413                 IP_VS_DBG_PKT(12, svc->af, pp, skb, 0,
414                               "Not scheduling reply for existing connection");
415                 __ip_vs_conn_put(cp);
416                 return NULL;
417         }
418
419         /*
420          *    Persistent service
421          */
422         if (svc->flags & IP_VS_SVC_F_PERSISTENT)
423                 return ip_vs_sched_persist(svc, skb, pptr[0], pptr[1], ignored);
424
425         *ignored = 0;
426
427         /*
428          *    Non-persistent service
429          */
430         if (!svc->fwmark && pptr[1] != svc->port) {
431                 if (!svc->port)
432                         pr_err("Schedule: port zero only supported "
433                                "in persistent services, "
434                                "check your ipvs configuration\n");
435                 return NULL;
436         }
437
438         dest = svc->scheduler->schedule(svc, skb);
439         if (dest == NULL) {
440                 IP_VS_DBG(1, "Schedule: no dest found.\n");
441                 return NULL;
442         }
443
444         flags = (svc->flags & IP_VS_SVC_F_ONEPACKET
445                  && iph.protocol == IPPROTO_UDP)?
446                 IP_VS_CONN_F_ONE_PACKET : 0;
447
448         /*
449          *    Create a connection entry.
450          */
451         {
452                 struct ip_vs_conn_param p;
453                 ip_vs_conn_fill_param(svc->af, iph.protocol, &iph.saddr,
454                                       pptr[0], &iph.daddr, pptr[1], &p);
455                 cp = ip_vs_conn_new(&p, &dest->addr,
456                                     dest->port ? dest->port : pptr[1],
457                                     flags, dest, skb->mark);
458                 if (!cp) {
459                         *ignored = -1;
460                         return NULL;
461                 }
462         }
463
464         IP_VS_DBG_BUF(6, "Schedule fwd:%c c:%s:%u v:%s:%u "
465                       "d:%s:%u conn->flags:%X conn->refcnt:%d\n",
466                       ip_vs_fwd_tag(cp),
467                       IP_VS_DBG_ADDR(svc->af, &cp->caddr), ntohs(cp->cport),
468                       IP_VS_DBG_ADDR(svc->af, &cp->vaddr), ntohs(cp->vport),
469                       IP_VS_DBG_ADDR(svc->af, &cp->daddr), ntohs(cp->dport),
470                       cp->flags, atomic_read(&cp->refcnt));
471
472         ip_vs_conn_stats(cp, svc);
473         return cp;
474 }
475
476
477 /*
478  *  Pass or drop the packet.
479  *  Called by ip_vs_in, when the virtual service is available but
480  *  no destination is available for a new connection.
481  */
482 int ip_vs_leave(struct ip_vs_service *svc, struct sk_buff *skb,
483                 struct ip_vs_proto_data *pd)
484 {
485         __be16 _ports[2], *pptr;
486         struct ip_vs_iphdr iph;
487         int unicast;
488
489         ip_vs_fill_iphdr(svc->af, skb_network_header(skb), &iph);
490
491         pptr = skb_header_pointer(skb, iph.len, sizeof(_ports), _ports);
492         if (pptr == NULL) {
493                 ip_vs_service_put(svc);
494                 return NF_DROP;
495         }
496
497 #ifdef CONFIG_IP_VS_IPV6
498         if (svc->af == AF_INET6)
499                 unicast = ipv6_addr_type(&iph.daddr.in6) & IPV6_ADDR_UNICAST;
500         else
501 #endif
502                 unicast = (inet_addr_type(&init_net, iph.daddr.ip) == RTN_UNICAST);
503
504         /* if it is fwmark-based service, the cache_bypass sysctl is up
505            and the destination is a non-local unicast, then create
506            a cache_bypass connection entry */
507         if (sysctl_ip_vs_cache_bypass && svc->fwmark && unicast) {
508                 int ret, cs;
509                 struct ip_vs_conn *cp;
510                 unsigned int flags = (svc->flags & IP_VS_SVC_F_ONEPACKET &&
511                                       iph.protocol == IPPROTO_UDP)?
512                                       IP_VS_CONN_F_ONE_PACKET : 0;
513                 union nf_inet_addr daddr =  { .all = { 0, 0, 0, 0 } };
514
515                 ip_vs_service_put(svc);
516
517                 /* create a new connection entry */
518                 IP_VS_DBG(6, "%s(): create a cache_bypass entry\n", __func__);
519                 {
520                         struct ip_vs_conn_param p;
521                         ip_vs_conn_fill_param(svc->af, iph.protocol,
522                                               &iph.saddr, pptr[0],
523                                               &iph.daddr, pptr[1], &p);
524                         cp = ip_vs_conn_new(&p, &daddr, 0,
525                                             IP_VS_CONN_F_BYPASS | flags,
526                                             NULL, skb->mark);
527                         if (!cp)
528                                 return NF_DROP;
529                 }
530
531                 /* statistics */
532                 ip_vs_in_stats(cp, skb);
533
534                 /* set state */
535                 cs = ip_vs_set_state(cp, IP_VS_DIR_INPUT, skb, pd);
536
537                 /* transmit the first SYN packet */
538                 ret = cp->packet_xmit(skb, cp, pd->pp);
539                 /* do not touch skb anymore */
540
541                 atomic_inc(&cp->in_pkts);
542                 ip_vs_conn_put(cp);
543                 return ret;
544         }
545
546         /*
547          * When the virtual ftp service is presented, packets destined
548          * for other services on the VIP may get here (except services
549          * listed in the ipvs table), pass the packets, because it is
550          * not ipvs job to decide to drop the packets.
551          */
552         if ((svc->port == FTPPORT) && (pptr[1] != FTPPORT)) {
553                 ip_vs_service_put(svc);
554                 return NF_ACCEPT;
555         }
556
557         ip_vs_service_put(svc);
558
559         /*
560          * Notify the client that the destination is unreachable, and
561          * release the socket buffer.
562          * Since it is in IP layer, the TCP socket is not actually
563          * created, the TCP RST packet cannot be sent, instead that
564          * ICMP_PORT_UNREACH is sent here no matter it is TCP/UDP. --WZ
565          */
566 #ifdef CONFIG_IP_VS_IPV6
567         if (svc->af == AF_INET6) {
568                 if (!skb->dev) {
569                         struct net *net = dev_net(skb_dst(skb)->dev);
570
571                         skb->dev = net->loopback_dev;
572                 }
573                 icmpv6_send(skb, ICMPV6_DEST_UNREACH, ICMPV6_PORT_UNREACH, 0);
574         } else
575 #endif
576                 icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
577
578         return NF_DROP;
579 }
580
581 __sum16 ip_vs_checksum_complete(struct sk_buff *skb, int offset)
582 {
583         return csum_fold(skb_checksum(skb, offset, skb->len - offset, 0));
584 }
585
586 static inline enum ip_defrag_users ip_vs_defrag_user(unsigned int hooknum)
587 {
588         if (NF_INET_LOCAL_IN == hooknum)
589                 return IP_DEFRAG_VS_IN;
590         if (NF_INET_FORWARD == hooknum)
591                 return IP_DEFRAG_VS_FWD;
592         return IP_DEFRAG_VS_OUT;
593 }
594
595 static inline int ip_vs_gather_frags(struct sk_buff *skb, u_int32_t user)
596 {
597         int err = ip_defrag(skb, user);
598
599         if (!err)
600                 ip_send_check(ip_hdr(skb));
601
602         return err;
603 }
604
605 #ifdef CONFIG_IP_VS_IPV6
606 static inline int ip_vs_gather_frags_v6(struct sk_buff *skb, u_int32_t user)
607 {
608         /* TODO IPv6: Find out what to do here for IPv6 */
609         return 0;
610 }
611 #endif
612
613 /*
614  * Packet has been made sufficiently writable in caller
615  * - inout: 1=in->out, 0=out->in
616  */
617 void ip_vs_nat_icmp(struct sk_buff *skb, struct ip_vs_protocol *pp,
618                     struct ip_vs_conn *cp, int inout)
619 {
620         struct iphdr *iph        = ip_hdr(skb);
621         unsigned int icmp_offset = iph->ihl*4;
622         struct icmphdr *icmph    = (struct icmphdr *)(skb_network_header(skb) +
623                                                       icmp_offset);
624         struct iphdr *ciph       = (struct iphdr *)(icmph + 1);
625
626         if (inout) {
627                 iph->saddr = cp->vaddr.ip;
628                 ip_send_check(iph);
629                 ciph->daddr = cp->vaddr.ip;
630                 ip_send_check(ciph);
631         } else {
632                 iph->daddr = cp->daddr.ip;
633                 ip_send_check(iph);
634                 ciph->saddr = cp->daddr.ip;
635                 ip_send_check(ciph);
636         }
637
638         /* the TCP/UDP/SCTP port */
639         if (IPPROTO_TCP == ciph->protocol || IPPROTO_UDP == ciph->protocol ||
640             IPPROTO_SCTP == ciph->protocol) {
641                 __be16 *ports = (void *)ciph + ciph->ihl*4;
642
643                 if (inout)
644                         ports[1] = cp->vport;
645                 else
646                         ports[0] = cp->dport;
647         }
648
649         /* And finally the ICMP checksum */
650         icmph->checksum = 0;
651         icmph->checksum = ip_vs_checksum_complete(skb, icmp_offset);
652         skb->ip_summed = CHECKSUM_UNNECESSARY;
653
654         if (inout)
655                 IP_VS_DBG_PKT(11, AF_INET, pp, skb, (void *)ciph - (void *)iph,
656                         "Forwarding altered outgoing ICMP");
657         else
658                 IP_VS_DBG_PKT(11, AF_INET, pp, skb, (void *)ciph - (void *)iph,
659                         "Forwarding altered incoming ICMP");
660 }
661
662 #ifdef CONFIG_IP_VS_IPV6
663 void ip_vs_nat_icmp_v6(struct sk_buff *skb, struct ip_vs_protocol *pp,
664                     struct ip_vs_conn *cp, int inout)
665 {
666         struct ipv6hdr *iph      = ipv6_hdr(skb);
667         unsigned int icmp_offset = sizeof(struct ipv6hdr);
668         struct icmp6hdr *icmph   = (struct icmp6hdr *)(skb_network_header(skb) +
669                                                       icmp_offset);
670         struct ipv6hdr *ciph     = (struct ipv6hdr *)(icmph + 1);
671
672         if (inout) {
673                 iph->saddr = cp->vaddr.in6;
674                 ciph->daddr = cp->vaddr.in6;
675         } else {
676                 iph->daddr = cp->daddr.in6;
677                 ciph->saddr = cp->daddr.in6;
678         }
679
680         /* the TCP/UDP/SCTP port */
681         if (IPPROTO_TCP == ciph->nexthdr || IPPROTO_UDP == ciph->nexthdr ||
682             IPPROTO_SCTP == ciph->nexthdr) {
683                 __be16 *ports = (void *)ciph + sizeof(struct ipv6hdr);
684
685                 if (inout)
686                         ports[1] = cp->vport;
687                 else
688                         ports[0] = cp->dport;
689         }
690
691         /* And finally the ICMP checksum */
692         icmph->icmp6_cksum = ~csum_ipv6_magic(&iph->saddr, &iph->daddr,
693                                               skb->len - icmp_offset,
694                                               IPPROTO_ICMPV6, 0);
695         skb->csum_start = skb_network_header(skb) - skb->head + icmp_offset;
696         skb->csum_offset = offsetof(struct icmp6hdr, icmp6_cksum);
697         skb->ip_summed = CHECKSUM_PARTIAL;
698
699         if (inout)
700                 IP_VS_DBG_PKT(11, AF_INET6, pp, skb,
701                               (void *)ciph - (void *)iph,
702                               "Forwarding altered outgoing ICMPv6");
703         else
704                 IP_VS_DBG_PKT(11, AF_INET6, pp, skb,
705                               (void *)ciph - (void *)iph,
706                               "Forwarding altered incoming ICMPv6");
707 }
708 #endif
709
710 /* Handle relevant response ICMP messages - forward to the right
711  * destination host. Used for NAT and local client.
712  */
713 static int handle_response_icmp(int af, struct sk_buff *skb,
714                                 union nf_inet_addr *snet,
715                                 __u8 protocol, struct ip_vs_conn *cp,
716                                 struct ip_vs_protocol *pp,
717                                 unsigned int offset, unsigned int ihl)
718 {
719         unsigned int verdict = NF_DROP;
720
721         if (IP_VS_FWD_METHOD(cp) != 0) {
722                 pr_err("shouldn't reach here, because the box is on the "
723                        "half connection in the tun/dr module.\n");
724         }
725
726         /* Ensure the checksum is correct */
727         if (!skb_csum_unnecessary(skb) && ip_vs_checksum_complete(skb, ihl)) {
728                 /* Failed checksum! */
729                 IP_VS_DBG_BUF(1, "Forward ICMP: failed checksum from %s!\n",
730                               IP_VS_DBG_ADDR(af, snet));
731                 goto out;
732         }
733
734         if (IPPROTO_TCP == protocol || IPPROTO_UDP == protocol ||
735             IPPROTO_SCTP == protocol)
736                 offset += 2 * sizeof(__u16);
737         if (!skb_make_writable(skb, offset))
738                 goto out;
739
740 #ifdef CONFIG_IP_VS_IPV6
741         if (af == AF_INET6)
742                 ip_vs_nat_icmp_v6(skb, pp, cp, 1);
743         else
744 #endif
745                 ip_vs_nat_icmp(skb, pp, cp, 1);
746
747 #ifdef CONFIG_IP_VS_IPV6
748         if (af == AF_INET6) {
749                 if (sysctl_ip_vs_snat_reroute && ip6_route_me_harder(skb) != 0)
750                         goto out;
751         } else
752 #endif
753                 if ((sysctl_ip_vs_snat_reroute ||
754                      skb_rtable(skb)->rt_flags & RTCF_LOCAL) &&
755                     ip_route_me_harder(skb, RTN_LOCAL) != 0)
756                         goto out;
757
758         /* do the statistics and put it back */
759         ip_vs_out_stats(cp, skb);
760
761         skb->ipvs_property = 1;
762         if (!(cp->flags & IP_VS_CONN_F_NFCT))
763                 ip_vs_notrack(skb);
764         else
765                 ip_vs_update_conntrack(skb, cp, 0);
766         verdict = NF_ACCEPT;
767
768 out:
769         __ip_vs_conn_put(cp);
770
771         return verdict;
772 }
773
774 /*
775  *      Handle ICMP messages in the inside-to-outside direction (outgoing).
776  *      Find any that might be relevant, check against existing connections.
777  *      Currently handles error types - unreachable, quench, ttl exceeded.
778  */
779 static int ip_vs_out_icmp(struct sk_buff *skb, int *related,
780                           unsigned int hooknum)
781 {
782         struct iphdr *iph;
783         struct icmphdr  _icmph, *ic;
784         struct iphdr    _ciph, *cih;    /* The ip header contained within the ICMP */
785         struct ip_vs_iphdr ciph;
786         struct ip_vs_conn *cp;
787         struct ip_vs_protocol *pp;
788         unsigned int offset, ihl;
789         union nf_inet_addr snet;
790
791         *related = 1;
792
793         /* reassemble IP fragments */
794         if (ip_hdr(skb)->frag_off & htons(IP_MF | IP_OFFSET)) {
795                 if (ip_vs_gather_frags(skb, ip_vs_defrag_user(hooknum)))
796                         return NF_STOLEN;
797         }
798
799         iph = ip_hdr(skb);
800         offset = ihl = iph->ihl * 4;
801         ic = skb_header_pointer(skb, offset, sizeof(_icmph), &_icmph);
802         if (ic == NULL)
803                 return NF_DROP;
804
805         IP_VS_DBG(12, "Outgoing ICMP (%d,%d) %pI4->%pI4\n",
806                   ic->type, ntohs(icmp_id(ic)),
807                   &iph->saddr, &iph->daddr);
808
809         /*
810          * Work through seeing if this is for us.
811          * These checks are supposed to be in an order that means easy
812          * things are checked first to speed up processing.... however
813          * this means that some packets will manage to get a long way
814          * down this stack and then be rejected, but that's life.
815          */
816         if ((ic->type != ICMP_DEST_UNREACH) &&
817             (ic->type != ICMP_SOURCE_QUENCH) &&
818             (ic->type != ICMP_TIME_EXCEEDED)) {
819                 *related = 0;
820                 return NF_ACCEPT;
821         }
822
823         /* Now find the contained IP header */
824         offset += sizeof(_icmph);
825         cih = skb_header_pointer(skb, offset, sizeof(_ciph), &_ciph);
826         if (cih == NULL)
827                 return NF_ACCEPT; /* The packet looks wrong, ignore */
828
829         pp = ip_vs_proto_get(cih->protocol);
830         if (!pp)
831                 return NF_ACCEPT;
832
833         /* Is the embedded protocol header present? */
834         if (unlikely(cih->frag_off & htons(IP_OFFSET) &&
835                      pp->dont_defrag))
836                 return NF_ACCEPT;
837
838         IP_VS_DBG_PKT(11, AF_INET, pp, skb, offset,
839                       "Checking outgoing ICMP for");
840
841         offset += cih->ihl * 4;
842
843         ip_vs_fill_iphdr(AF_INET, cih, &ciph);
844         /* The embedded headers contain source and dest in reverse order */
845         cp = pp->conn_out_get(AF_INET, skb, &ciph, offset, 1);
846         if (!cp)
847                 return NF_ACCEPT;
848
849         snet.ip = iph->saddr;
850         return handle_response_icmp(AF_INET, skb, &snet, cih->protocol, cp,
851                                     pp, offset, ihl);
852 }
853
854 #ifdef CONFIG_IP_VS_IPV6
855 static int ip_vs_out_icmp_v6(struct sk_buff *skb, int *related,
856                              unsigned int hooknum)
857 {
858         struct ipv6hdr *iph;
859         struct icmp6hdr _icmph, *ic;
860         struct ipv6hdr  _ciph, *cih;    /* The ip header contained
861                                            within the ICMP */
862         struct ip_vs_iphdr ciph;
863         struct ip_vs_conn *cp;
864         struct ip_vs_protocol *pp;
865         unsigned int offset;
866         union nf_inet_addr snet;
867
868         *related = 1;
869
870         /* reassemble IP fragments */
871         if (ipv6_hdr(skb)->nexthdr == IPPROTO_FRAGMENT) {
872                 if (ip_vs_gather_frags_v6(skb, ip_vs_defrag_user(hooknum)))
873                         return NF_STOLEN;
874         }
875
876         iph = ipv6_hdr(skb);
877         offset = sizeof(struct ipv6hdr);
878         ic = skb_header_pointer(skb, offset, sizeof(_icmph), &_icmph);
879         if (ic == NULL)
880                 return NF_DROP;
881
882         IP_VS_DBG(12, "Outgoing ICMPv6 (%d,%d) %pI6->%pI6\n",
883                   ic->icmp6_type, ntohs(icmpv6_id(ic)),
884                   &iph->saddr, &iph->daddr);
885
886         /*
887          * Work through seeing if this is for us.
888          * These checks are supposed to be in an order that means easy
889          * things are checked first to speed up processing.... however
890          * this means that some packets will manage to get a long way
891          * down this stack and then be rejected, but that's life.
892          */
893         if ((ic->icmp6_type != ICMPV6_DEST_UNREACH) &&
894             (ic->icmp6_type != ICMPV6_PKT_TOOBIG) &&
895             (ic->icmp6_type != ICMPV6_TIME_EXCEED)) {
896                 *related = 0;
897                 return NF_ACCEPT;
898         }
899
900         /* Now find the contained IP header */
901         offset += sizeof(_icmph);
902         cih = skb_header_pointer(skb, offset, sizeof(_ciph), &_ciph);
903         if (cih == NULL)
904                 return NF_ACCEPT; /* The packet looks wrong, ignore */
905
906         pp = ip_vs_proto_get(cih->nexthdr);
907         if (!pp)
908                 return NF_ACCEPT;
909
910         /* Is the embedded protocol header present? */
911         /* TODO: we don't support fragmentation at the moment anyways */
912         if (unlikely(cih->nexthdr == IPPROTO_FRAGMENT && pp->dont_defrag))
913                 return NF_ACCEPT;
914
915         IP_VS_DBG_PKT(11, AF_INET6, pp, skb, offset,
916                       "Checking outgoing ICMPv6 for");
917
918         offset += sizeof(struct ipv6hdr);
919
920         ip_vs_fill_iphdr(AF_INET6, cih, &ciph);
921         /* The embedded headers contain source and dest in reverse order */
922         cp = pp->conn_out_get(AF_INET6, skb, &ciph, offset, 1);
923         if (!cp)
924                 return NF_ACCEPT;
925
926         ipv6_addr_copy(&snet.in6, &iph->saddr);
927         return handle_response_icmp(AF_INET6, skb, &snet, cih->nexthdr, cp,
928                                     pp, offset, sizeof(struct ipv6hdr));
929 }
930 #endif
931
932 /*
933  * Check if sctp chunc is ABORT chunk
934  */
935 static inline int is_sctp_abort(const struct sk_buff *skb, int nh_len)
936 {
937         sctp_chunkhdr_t *sch, schunk;
938         sch = skb_header_pointer(skb, nh_len + sizeof(sctp_sctphdr_t),
939                         sizeof(schunk), &schunk);
940         if (sch == NULL)
941                 return 0;
942         if (sch->type == SCTP_CID_ABORT)
943                 return 1;
944         return 0;
945 }
946
947 static inline int is_tcp_reset(const struct sk_buff *skb, int nh_len)
948 {
949         struct tcphdr _tcph, *th;
950
951         th = skb_header_pointer(skb, nh_len, sizeof(_tcph), &_tcph);
952         if (th == NULL)
953                 return 0;
954         return th->rst;
955 }
956
957 /* Handle response packets: rewrite addresses and send away...
958  * Used for NAT and local client.
959  */
960 static unsigned int
961 handle_response(int af, struct sk_buff *skb, struct ip_vs_proto_data *pd,
962                 struct ip_vs_conn *cp, int ihl)
963 {
964         struct ip_vs_protocol *pp = pd->pp;
965
966         IP_VS_DBG_PKT(11, af, pp, skb, 0, "Outgoing packet");
967
968         if (!skb_make_writable(skb, ihl))
969                 goto drop;
970
971         /* mangle the packet */
972         if (pp->snat_handler && !pp->snat_handler(skb, pp, cp))
973                 goto drop;
974
975 #ifdef CONFIG_IP_VS_IPV6
976         if (af == AF_INET6)
977                 ipv6_hdr(skb)->saddr = cp->vaddr.in6;
978         else
979 #endif
980         {
981                 ip_hdr(skb)->saddr = cp->vaddr.ip;
982                 ip_send_check(ip_hdr(skb));
983         }
984
985         /*
986          * nf_iterate does not expect change in the skb->dst->dev.
987          * It looks like it is not fatal to enable this code for hooks
988          * where our handlers are at the end of the chain list and
989          * when all next handlers use skb->dst->dev and not outdev.
990          * It will definitely route properly the inout NAT traffic
991          * when multiple paths are used.
992          */
993
994         /* For policy routing, packets originating from this
995          * machine itself may be routed differently to packets
996          * passing through.  We want this packet to be routed as
997          * if it came from this machine itself.  So re-compute
998          * the routing information.
999          */
1000 #ifdef CONFIG_IP_VS_IPV6
1001         if (af == AF_INET6) {
1002                 if (sysctl_ip_vs_snat_reroute && ip6_route_me_harder(skb) != 0)
1003                         goto drop;
1004         } else
1005 #endif
1006                 if ((sysctl_ip_vs_snat_reroute ||
1007                      skb_rtable(skb)->rt_flags & RTCF_LOCAL) &&
1008                     ip_route_me_harder(skb, RTN_LOCAL) != 0)
1009                         goto drop;
1010
1011         IP_VS_DBG_PKT(10, af, pp, skb, 0, "After SNAT");
1012
1013         ip_vs_out_stats(cp, skb);
1014         ip_vs_set_state(cp, IP_VS_DIR_OUTPUT, skb, pd);
1015         skb->ipvs_property = 1;
1016         if (!(cp->flags & IP_VS_CONN_F_NFCT))
1017                 ip_vs_notrack(skb);
1018         else
1019                 ip_vs_update_conntrack(skb, cp, 0);
1020         ip_vs_conn_put(cp);
1021
1022         LeaveFunction(11);
1023         return NF_ACCEPT;
1024
1025 drop:
1026         ip_vs_conn_put(cp);
1027         kfree_skb(skb);
1028         LeaveFunction(11);
1029         return NF_STOLEN;
1030 }
1031
1032 /*
1033  *      Check if outgoing packet belongs to the established ip_vs_conn.
1034  */
1035 static unsigned int
1036 ip_vs_out(unsigned int hooknum, struct sk_buff *skb, int af)
1037 {
1038         struct net *net = NULL;
1039         struct ip_vs_iphdr iph;
1040         struct ip_vs_protocol *pp;
1041         struct ip_vs_proto_data *pd;
1042         struct ip_vs_conn *cp;
1043
1044         EnterFunction(11);
1045
1046         /* Already marked as IPVS request or reply? */
1047         if (skb->ipvs_property)
1048                 return NF_ACCEPT;
1049
1050         /* Bad... Do not break raw sockets */
1051         if (unlikely(skb->sk != NULL && hooknum == NF_INET_LOCAL_OUT &&
1052                      af == AF_INET)) {
1053                 struct sock *sk = skb->sk;
1054                 struct inet_sock *inet = inet_sk(skb->sk);
1055
1056                 if (inet && sk->sk_family == PF_INET && inet->nodefrag)
1057                         return NF_ACCEPT;
1058         }
1059
1060         if (unlikely(!skb_dst(skb)))
1061                 return NF_ACCEPT;
1062
1063         net = skb_net(skb);
1064         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1065 #ifdef CONFIG_IP_VS_IPV6
1066         if (af == AF_INET6) {
1067                 if (unlikely(iph.protocol == IPPROTO_ICMPV6)) {
1068                         int related;
1069                         int verdict = ip_vs_out_icmp_v6(skb, &related,
1070                                                         hooknum);
1071
1072                         if (related)
1073                                 return verdict;
1074                         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1075                 }
1076         } else
1077 #endif
1078                 if (unlikely(iph.protocol == IPPROTO_ICMP)) {
1079                         int related;
1080                         int verdict = ip_vs_out_icmp(skb, &related, hooknum);
1081
1082                         if (related)
1083                                 return verdict;
1084                         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1085                 }
1086
1087         pd = ip_vs_proto_data_get(net, iph.protocol);
1088         if (unlikely(!pd))
1089                 return NF_ACCEPT;
1090         pp = pd->pp;
1091
1092         /* reassemble IP fragments */
1093 #ifdef CONFIG_IP_VS_IPV6
1094         if (af == AF_INET6) {
1095                 if (ipv6_hdr(skb)->nexthdr == IPPROTO_FRAGMENT) {
1096                         if (ip_vs_gather_frags_v6(skb,
1097                                                   ip_vs_defrag_user(hooknum)))
1098                                 return NF_STOLEN;
1099                 }
1100
1101                 ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1102         } else
1103 #endif
1104                 if (unlikely(ip_hdr(skb)->frag_off & htons(IP_MF|IP_OFFSET) &&
1105                              !pp->dont_defrag)) {
1106                         if (ip_vs_gather_frags(skb,
1107                                                ip_vs_defrag_user(hooknum)))
1108                                 return NF_STOLEN;
1109
1110                         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1111                 }
1112
1113         /*
1114          * Check if the packet belongs to an existing entry
1115          */
1116         cp = pp->conn_out_get(af, skb, &iph, iph.len, 0);
1117
1118         if (likely(cp))
1119                 return handle_response(af, skb, pd, cp, iph.len);
1120         if (sysctl_ip_vs_nat_icmp_send &&
1121             (pp->protocol == IPPROTO_TCP ||
1122              pp->protocol == IPPROTO_UDP ||
1123              pp->protocol == IPPROTO_SCTP)) {
1124                 __be16 _ports[2], *pptr;
1125
1126                 pptr = skb_header_pointer(skb, iph.len,
1127                                           sizeof(_ports), _ports);
1128                 if (pptr == NULL)
1129                         return NF_ACCEPT;       /* Not for me */
1130                 if (ip_vs_lookup_real_service(net, af, iph.protocol,
1131                                               &iph.saddr,
1132                                               pptr[0])) {
1133                         /*
1134                          * Notify the real server: there is no
1135                          * existing entry if it is not RST
1136                          * packet or not TCP packet.
1137                          */
1138                         if ((iph.protocol != IPPROTO_TCP &&
1139                              iph.protocol != IPPROTO_SCTP)
1140                              || ((iph.protocol == IPPROTO_TCP
1141                                   && !is_tcp_reset(skb, iph.len))
1142                                  || (iph.protocol == IPPROTO_SCTP
1143                                         && !is_sctp_abort(skb,
1144                                                 iph.len)))) {
1145 #ifdef CONFIG_IP_VS_IPV6
1146                                 if (af == AF_INET6) {
1147                                         struct net *net =
1148                                                 dev_net(skb_dst(skb)->dev);
1149
1150                                         if (!skb->dev)
1151                                                 skb->dev = net->loopback_dev;
1152                                         icmpv6_send(skb,
1153                                                     ICMPV6_DEST_UNREACH,
1154                                                     ICMPV6_PORT_UNREACH,
1155                                                     0);
1156                                 } else
1157 #endif
1158                                         icmp_send(skb,
1159                                                   ICMP_DEST_UNREACH,
1160                                                   ICMP_PORT_UNREACH, 0);
1161                                 return NF_DROP;
1162                         }
1163                 }
1164         }
1165         IP_VS_DBG_PKT(12, af, pp, skb, 0,
1166                       "ip_vs_out: packet continues traversal as normal");
1167         return NF_ACCEPT;
1168 }
1169
1170 /*
1171  *      It is hooked at the NF_INET_FORWARD and NF_INET_LOCAL_IN chain,
1172  *      used only for VS/NAT.
1173  *      Check if packet is reply for established ip_vs_conn.
1174  */
1175 static unsigned int
1176 ip_vs_reply4(unsigned int hooknum, struct sk_buff *skb,
1177              const struct net_device *in, const struct net_device *out,
1178              int (*okfn)(struct sk_buff *))
1179 {
1180         return ip_vs_out(hooknum, skb, AF_INET);
1181 }
1182
1183 /*
1184  *      It is hooked at the NF_INET_LOCAL_OUT chain, used only for VS/NAT.
1185  *      Check if packet is reply for established ip_vs_conn.
1186  */
1187 static unsigned int
1188 ip_vs_local_reply4(unsigned int hooknum, struct sk_buff *skb,
1189                    const struct net_device *in, const struct net_device *out,
1190                    int (*okfn)(struct sk_buff *))
1191 {
1192         unsigned int verdict;
1193
1194         /* Disable BH in LOCAL_OUT until all places are fixed */
1195         local_bh_disable();
1196         verdict = ip_vs_out(hooknum, skb, AF_INET);
1197         local_bh_enable();
1198         return verdict;
1199 }
1200
1201 #ifdef CONFIG_IP_VS_IPV6
1202
1203 /*
1204  *      It is hooked at the NF_INET_FORWARD and NF_INET_LOCAL_IN chain,
1205  *      used only for VS/NAT.
1206  *      Check if packet is reply for established ip_vs_conn.
1207  */
1208 static unsigned int
1209 ip_vs_reply6(unsigned int hooknum, struct sk_buff *skb,
1210              const struct net_device *in, const struct net_device *out,
1211              int (*okfn)(struct sk_buff *))
1212 {
1213         return ip_vs_out(hooknum, skb, AF_INET6);
1214 }
1215
1216 /*
1217  *      It is hooked at the NF_INET_LOCAL_OUT chain, used only for VS/NAT.
1218  *      Check if packet is reply for established ip_vs_conn.
1219  */
1220 static unsigned int
1221 ip_vs_local_reply6(unsigned int hooknum, struct sk_buff *skb,
1222                    const struct net_device *in, const struct net_device *out,
1223                    int (*okfn)(struct sk_buff *))
1224 {
1225         unsigned int verdict;
1226
1227         /* Disable BH in LOCAL_OUT until all places are fixed */
1228         local_bh_disable();
1229         verdict = ip_vs_out(hooknum, skb, AF_INET6);
1230         local_bh_enable();
1231         return verdict;
1232 }
1233
1234 #endif
1235
1236 /*
1237  *      Handle ICMP messages in the outside-to-inside direction (incoming).
1238  *      Find any that might be relevant, check against existing connections,
1239  *      forward to the right destination host if relevant.
1240  *      Currently handles error types - unreachable, quench, ttl exceeded.
1241  */
1242 static int
1243 ip_vs_in_icmp(struct sk_buff *skb, int *related, unsigned int hooknum)
1244 {
1245         struct net *net = NULL;
1246         struct iphdr *iph;
1247         struct icmphdr  _icmph, *ic;
1248         struct iphdr    _ciph, *cih;    /* The ip header contained within the ICMP */
1249         struct ip_vs_iphdr ciph;
1250         struct ip_vs_conn *cp;
1251         struct ip_vs_protocol *pp;
1252         struct ip_vs_proto_data *pd;
1253         unsigned int offset, ihl, verdict;
1254         union nf_inet_addr snet;
1255
1256         *related = 1;
1257
1258         /* reassemble IP fragments */
1259         if (ip_hdr(skb)->frag_off & htons(IP_MF | IP_OFFSET)) {
1260                 if (ip_vs_gather_frags(skb, ip_vs_defrag_user(hooknum)))
1261                         return NF_STOLEN;
1262         }
1263
1264         iph = ip_hdr(skb);
1265         offset = ihl = iph->ihl * 4;
1266         ic = skb_header_pointer(skb, offset, sizeof(_icmph), &_icmph);
1267         if (ic == NULL)
1268                 return NF_DROP;
1269
1270         IP_VS_DBG(12, "Incoming ICMP (%d,%d) %pI4->%pI4\n",
1271                   ic->type, ntohs(icmp_id(ic)),
1272                   &iph->saddr, &iph->daddr);
1273
1274         /*
1275          * Work through seeing if this is for us.
1276          * These checks are supposed to be in an order that means easy
1277          * things are checked first to speed up processing.... however
1278          * this means that some packets will manage to get a long way
1279          * down this stack and then be rejected, but that's life.
1280          */
1281         if ((ic->type != ICMP_DEST_UNREACH) &&
1282             (ic->type != ICMP_SOURCE_QUENCH) &&
1283             (ic->type != ICMP_TIME_EXCEEDED)) {
1284                 *related = 0;
1285                 return NF_ACCEPT;
1286         }
1287
1288         /* Now find the contained IP header */
1289         offset += sizeof(_icmph);
1290         cih = skb_header_pointer(skb, offset, sizeof(_ciph), &_ciph);
1291         if (cih == NULL)
1292                 return NF_ACCEPT; /* The packet looks wrong, ignore */
1293
1294         net = skb_net(skb);
1295         pd = ip_vs_proto_data_get(net, cih->protocol);
1296         if (!pd)
1297                 return NF_ACCEPT;
1298         pp = pd->pp;
1299
1300         /* Is the embedded protocol header present? */
1301         if (unlikely(cih->frag_off & htons(IP_OFFSET) &&
1302                      pp->dont_defrag))
1303                 return NF_ACCEPT;
1304
1305         IP_VS_DBG_PKT(11, AF_INET, pp, skb, offset,
1306                       "Checking incoming ICMP for");
1307
1308         offset += cih->ihl * 4;
1309
1310         ip_vs_fill_iphdr(AF_INET, cih, &ciph);
1311         /* The embedded headers contain source and dest in reverse order */
1312         cp = pp->conn_in_get(AF_INET, skb, &ciph, offset, 1);
1313         if (!cp) {
1314                 /* The packet could also belong to a local client */
1315                 cp = pp->conn_out_get(AF_INET, skb, &ciph, offset, 1);
1316                 if (cp) {
1317                         snet.ip = iph->saddr;
1318                         return handle_response_icmp(AF_INET, skb, &snet,
1319                                                     cih->protocol, cp, pp,
1320                                                     offset, ihl);
1321                 }
1322                 return NF_ACCEPT;
1323         }
1324
1325         verdict = NF_DROP;
1326
1327         /* Ensure the checksum is correct */
1328         if (!skb_csum_unnecessary(skb) && ip_vs_checksum_complete(skb, ihl)) {
1329                 /* Failed checksum! */
1330                 IP_VS_DBG(1, "Incoming ICMP: failed checksum from %pI4!\n",
1331                           &iph->saddr);
1332                 goto out;
1333         }
1334
1335         /* do the statistics and put it back */
1336         ip_vs_in_stats(cp, skb);
1337         if (IPPROTO_TCP == cih->protocol || IPPROTO_UDP == cih->protocol)
1338                 offset += 2 * sizeof(__u16);
1339         verdict = ip_vs_icmp_xmit(skb, cp, pp, offset);
1340         /* LOCALNODE from FORWARD hook is not supported */
1341         if (verdict == NF_ACCEPT && hooknum == NF_INET_FORWARD &&
1342             skb_rtable(skb)->rt_flags & RTCF_LOCAL) {
1343                 IP_VS_DBG(1, "%s(): "
1344                           "local delivery to %pI4 but in FORWARD\n",
1345                           __func__, &skb_rtable(skb)->rt_dst);
1346                 verdict = NF_DROP;
1347         }
1348
1349   out:
1350         __ip_vs_conn_put(cp);
1351
1352         return verdict;
1353 }
1354
1355 #ifdef CONFIG_IP_VS_IPV6
1356 static int
1357 ip_vs_in_icmp_v6(struct sk_buff *skb, int *related, unsigned int hooknum)
1358 {
1359         struct net *net = NULL;
1360         struct ipv6hdr *iph;
1361         struct icmp6hdr _icmph, *ic;
1362         struct ipv6hdr  _ciph, *cih;    /* The ip header contained
1363                                            within the ICMP */
1364         struct ip_vs_iphdr ciph;
1365         struct ip_vs_conn *cp;
1366         struct ip_vs_protocol *pp;
1367         struct ip_vs_proto_data *pd;
1368         unsigned int offset, verdict;
1369         union nf_inet_addr snet;
1370         struct rt6_info *rt;
1371
1372         *related = 1;
1373
1374         /* reassemble IP fragments */
1375         if (ipv6_hdr(skb)->nexthdr == IPPROTO_FRAGMENT) {
1376                 if (ip_vs_gather_frags_v6(skb, ip_vs_defrag_user(hooknum)))
1377                         return NF_STOLEN;
1378         }
1379
1380         iph = ipv6_hdr(skb);
1381         offset = sizeof(struct ipv6hdr);
1382         ic = skb_header_pointer(skb, offset, sizeof(_icmph), &_icmph);
1383         if (ic == NULL)
1384                 return NF_DROP;
1385
1386         IP_VS_DBG(12, "Incoming ICMPv6 (%d,%d) %pI6->%pI6\n",
1387                   ic->icmp6_type, ntohs(icmpv6_id(ic)),
1388                   &iph->saddr, &iph->daddr);
1389
1390         /*
1391          * Work through seeing if this is for us.
1392          * These checks are supposed to be in an order that means easy
1393          * things are checked first to speed up processing.... however
1394          * this means that some packets will manage to get a long way
1395          * down this stack and then be rejected, but that's life.
1396          */
1397         if ((ic->icmp6_type != ICMPV6_DEST_UNREACH) &&
1398             (ic->icmp6_type != ICMPV6_PKT_TOOBIG) &&
1399             (ic->icmp6_type != ICMPV6_TIME_EXCEED)) {
1400                 *related = 0;
1401                 return NF_ACCEPT;
1402         }
1403
1404         /* Now find the contained IP header */
1405         offset += sizeof(_icmph);
1406         cih = skb_header_pointer(skb, offset, sizeof(_ciph), &_ciph);
1407         if (cih == NULL)
1408                 return NF_ACCEPT; /* The packet looks wrong, ignore */
1409
1410         net = skb_net(skb);
1411         pd = ip_vs_proto_data_get(net, cih->nexthdr);
1412         if (!pd)
1413                 return NF_ACCEPT;
1414         pp = pd->pp;
1415
1416         /* Is the embedded protocol header present? */
1417         /* TODO: we don't support fragmentation at the moment anyways */
1418         if (unlikely(cih->nexthdr == IPPROTO_FRAGMENT && pp->dont_defrag))
1419                 return NF_ACCEPT;
1420
1421         IP_VS_DBG_PKT(11, AF_INET6, pp, skb, offset,
1422                       "Checking incoming ICMPv6 for");
1423
1424         offset += sizeof(struct ipv6hdr);
1425
1426         ip_vs_fill_iphdr(AF_INET6, cih, &ciph);
1427         /* The embedded headers contain source and dest in reverse order */
1428         cp = pp->conn_in_get(AF_INET6, skb, &ciph, offset, 1);
1429         if (!cp) {
1430                 /* The packet could also belong to a local client */
1431                 cp = pp->conn_out_get(AF_INET6, skb, &ciph, offset, 1);
1432                 if (cp) {
1433                         ipv6_addr_copy(&snet.in6, &iph->saddr);
1434                         return handle_response_icmp(AF_INET6, skb, &snet,
1435                                                     cih->nexthdr,
1436                                                     cp, pp, offset,
1437                                                     sizeof(struct ipv6hdr));
1438                 }
1439                 return NF_ACCEPT;
1440         }
1441
1442         verdict = NF_DROP;
1443
1444         /* do the statistics and put it back */
1445         ip_vs_in_stats(cp, skb);
1446         if (IPPROTO_TCP == cih->nexthdr || IPPROTO_UDP == cih->nexthdr ||
1447             IPPROTO_SCTP == cih->nexthdr)
1448                 offset += 2 * sizeof(__u16);
1449         verdict = ip_vs_icmp_xmit_v6(skb, cp, pp, offset);
1450         /* LOCALNODE from FORWARD hook is not supported */
1451         if (verdict == NF_ACCEPT && hooknum == NF_INET_FORWARD &&
1452             (rt = (struct rt6_info *) skb_dst(skb)) &&
1453             rt->rt6i_dev && rt->rt6i_dev->flags & IFF_LOOPBACK) {
1454                 IP_VS_DBG(1, "%s(): "
1455                           "local delivery to %pI6 but in FORWARD\n",
1456                           __func__, &rt->rt6i_dst);
1457                 verdict = NF_DROP;
1458         }
1459
1460         __ip_vs_conn_put(cp);
1461
1462         return verdict;
1463 }
1464 #endif
1465
1466
1467 /*
1468  *      Check if it's for virtual services, look it up,
1469  *      and send it on its way...
1470  */
1471 static unsigned int
1472 ip_vs_in(unsigned int hooknum, struct sk_buff *skb, int af)
1473 {
1474         struct net *net;
1475         struct ip_vs_iphdr iph;
1476         struct ip_vs_protocol *pp;
1477         struct ip_vs_proto_data *pd;
1478         struct ip_vs_conn *cp;
1479         int ret, restart, pkts;
1480         struct netns_ipvs *ipvs;
1481
1482         /* Already marked as IPVS request or reply? */
1483         if (skb->ipvs_property)
1484                 return NF_ACCEPT;
1485
1486         /*
1487          *      Big tappo:
1488          *      - remote client: only PACKET_HOST
1489          *      - route: used for struct net when skb->dev is unset
1490          */
1491         if (unlikely((skb->pkt_type != PACKET_HOST &&
1492                       hooknum != NF_INET_LOCAL_OUT) ||
1493                      !skb_dst(skb))) {
1494                 ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1495                 IP_VS_DBG_BUF(12, "packet type=%d proto=%d daddr=%s"
1496                               " ignored in hook %u\n",
1497                               skb->pkt_type, iph.protocol,
1498                               IP_VS_DBG_ADDR(af, &iph.daddr), hooknum);
1499                 return NF_ACCEPT;
1500         }
1501         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1502
1503         /* Bad... Do not break raw sockets */
1504         if (unlikely(skb->sk != NULL && hooknum == NF_INET_LOCAL_OUT &&
1505                      af == AF_INET)) {
1506                 struct sock *sk = skb->sk;
1507                 struct inet_sock *inet = inet_sk(skb->sk);
1508
1509                 if (inet && sk->sk_family == PF_INET && inet->nodefrag)
1510                         return NF_ACCEPT;
1511         }
1512
1513 #ifdef CONFIG_IP_VS_IPV6
1514         if (af == AF_INET6) {
1515                 if (unlikely(iph.protocol == IPPROTO_ICMPV6)) {
1516                         int related;
1517                         int verdict = ip_vs_in_icmp_v6(skb, &related, hooknum);
1518
1519                         if (related)
1520                                 return verdict;
1521                         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1522                 }
1523         } else
1524 #endif
1525                 if (unlikely(iph.protocol == IPPROTO_ICMP)) {
1526                         int related;
1527                         int verdict = ip_vs_in_icmp(skb, &related, hooknum);
1528
1529                         if (related)
1530                                 return verdict;
1531                         ip_vs_fill_iphdr(af, skb_network_header(skb), &iph);
1532                 }
1533
1534         net = skb_net(skb);
1535         /* Protocol supported? */
1536         pd = ip_vs_proto_data_get(net, iph.protocol);
1537         if (unlikely(!pd))
1538                 return NF_ACCEPT;
1539         pp = pd->pp;
1540         /*
1541          * Check if the packet belongs to an existing connection entry
1542          */
1543         cp = pp->conn_in_get(af, skb, &iph, iph.len, 0);
1544
1545         if (unlikely(!cp)) {
1546                 int v;
1547
1548                 if (!pp->conn_schedule(af, skb, pd, &v, &cp))
1549                         return v;
1550         }
1551
1552         if (unlikely(!cp)) {
1553                 /* sorry, all this trouble for a no-hit :) */
1554                 IP_VS_DBG_PKT(12, af, pp, skb, 0,
1555                               "ip_vs_in: packet continues traversal as normal");
1556                 return NF_ACCEPT;
1557         }
1558
1559         IP_VS_DBG_PKT(11, af, pp, skb, 0, "Incoming packet");
1560         net = skb_net(skb);
1561         ipvs = net_ipvs(net);
1562         /* Check the server status */
1563         if (cp->dest && !(cp->dest->flags & IP_VS_DEST_F_AVAILABLE)) {
1564                 /* the destination server is not available */
1565
1566                 if (sysctl_ip_vs_expire_nodest_conn) {
1567                         /* try to expire the connection immediately */
1568                         ip_vs_conn_expire_now(cp);
1569                 }
1570                 /* don't restart its timer, and silently
1571                    drop the packet. */
1572                 __ip_vs_conn_put(cp);
1573                 return NF_DROP;
1574         }
1575
1576         ip_vs_in_stats(cp, skb);
1577         restart = ip_vs_set_state(cp, IP_VS_DIR_INPUT, skb, pd);
1578         if (cp->packet_xmit)
1579                 ret = cp->packet_xmit(skb, cp, pp);
1580                 /* do not touch skb anymore */
1581         else {
1582                 IP_VS_DBG_RL("warning: packet_xmit is null");
1583                 ret = NF_ACCEPT;
1584         }
1585
1586         /* Increase its packet counter and check if it is needed
1587          * to be synchronized
1588          *
1589          * Sync connection if it is about to close to
1590          * encorage the standby servers to update the connections timeout
1591          *
1592          * For ONE_PKT let ip_vs_sync_conn() do the filter work.
1593          */
1594
1595         if (cp->flags & IP_VS_CONN_F_ONE_PACKET)
1596                 pkts = sysctl_ip_vs_sync_threshold[0];
1597         else
1598                 pkts = atomic_add_return(1, &cp->in_pkts);
1599
1600         if ((ipvs->sync_state & IP_VS_STATE_MASTER) &&
1601             cp->protocol == IPPROTO_SCTP) {
1602                 if ((cp->state == IP_VS_SCTP_S_ESTABLISHED &&
1603                         (pkts % sysctl_ip_vs_sync_threshold[1]
1604                          == sysctl_ip_vs_sync_threshold[0])) ||
1605                                 (cp->old_state != cp->state &&
1606                                  ((cp->state == IP_VS_SCTP_S_CLOSED) ||
1607                                   (cp->state == IP_VS_SCTP_S_SHUT_ACK_CLI) ||
1608                                   (cp->state == IP_VS_SCTP_S_SHUT_ACK_SER)))) {
1609                         ip_vs_sync_conn(net, cp);
1610                         goto out;
1611                 }
1612         }
1613
1614         /* Keep this block last: TCP and others with pp->num_states <= 1 */
1615         else if ((ipvs->sync_state & IP_VS_STATE_MASTER) &&
1616             (((cp->protocol != IPPROTO_TCP ||
1617                cp->state == IP_VS_TCP_S_ESTABLISHED) &&
1618               (pkts % sysctl_ip_vs_sync_threshold[1]
1619                == sysctl_ip_vs_sync_threshold[0])) ||
1620              ((cp->protocol == IPPROTO_TCP) && (cp->old_state != cp->state) &&
1621               ((cp->state == IP_VS_TCP_S_FIN_WAIT) ||
1622                (cp->state == IP_VS_TCP_S_CLOSE) ||
1623                (cp->state == IP_VS_TCP_S_CLOSE_WAIT) ||
1624                (cp->state == IP_VS_TCP_S_TIME_WAIT)))))
1625                 ip_vs_sync_conn(net, cp);
1626 out:
1627         cp->old_state = cp->state;
1628
1629         ip_vs_conn_put(cp);
1630         return ret;
1631 }
1632
1633 /*
1634  *      AF_INET handler in NF_INET_LOCAL_IN chain
1635  *      Schedule and forward packets from remote clients
1636  */
1637 static unsigned int
1638 ip_vs_remote_request4(unsigned int hooknum, struct sk_buff *skb,
1639                       const struct net_device *in,
1640                       const struct net_device *out,
1641                       int (*okfn)(struct sk_buff *))
1642 {
1643         return ip_vs_in(hooknum, skb, AF_INET);
1644 }
1645
1646 /*
1647  *      AF_INET handler in NF_INET_LOCAL_OUT chain
1648  *      Schedule and forward packets from local clients
1649  */
1650 static unsigned int
1651 ip_vs_local_request4(unsigned int hooknum, struct sk_buff *skb,
1652                      const struct net_device *in, const struct net_device *out,
1653                      int (*okfn)(struct sk_buff *))
1654 {
1655         unsigned int verdict;
1656
1657         /* Disable BH in LOCAL_OUT until all places are fixed */
1658         local_bh_disable();
1659         verdict = ip_vs_in(hooknum, skb, AF_INET);
1660         local_bh_enable();
1661         return verdict;
1662 }
1663
1664 #ifdef CONFIG_IP_VS_IPV6
1665
1666 /*
1667  *      AF_INET6 handler in NF_INET_LOCAL_IN chain
1668  *      Schedule and forward packets from remote clients
1669  */
1670 static unsigned int
1671 ip_vs_remote_request6(unsigned int hooknum, struct sk_buff *skb,
1672                       const struct net_device *in,
1673                       const struct net_device *out,
1674                       int (*okfn)(struct sk_buff *))
1675 {
1676         return ip_vs_in(hooknum, skb, AF_INET6);
1677 }
1678
1679 /*
1680  *      AF_INET6 handler in NF_INET_LOCAL_OUT chain
1681  *      Schedule and forward packets from local clients
1682  */
1683 static unsigned int
1684 ip_vs_local_request6(unsigned int hooknum, struct sk_buff *skb,
1685                      const struct net_device *in, const struct net_device *out,
1686                      int (*okfn)(struct sk_buff *))
1687 {
1688         unsigned int verdict;
1689
1690         /* Disable BH in LOCAL_OUT until all places are fixed */
1691         local_bh_disable();
1692         verdict = ip_vs_in(hooknum, skb, AF_INET6);
1693         local_bh_enable();
1694         return verdict;
1695 }
1696
1697 #endif
1698
1699
1700 /*
1701  *      It is hooked at the NF_INET_FORWARD chain, in order to catch ICMP
1702  *      related packets destined for 0.0.0.0/0.
1703  *      When fwmark-based virtual service is used, such as transparent
1704  *      cache cluster, TCP packets can be marked and routed to ip_vs_in,
1705  *      but ICMP destined for 0.0.0.0/0 cannot not be easily marked and
1706  *      sent to ip_vs_in_icmp. So, catch them at the NF_INET_FORWARD chain
1707  *      and send them to ip_vs_in_icmp.
1708  */
1709 static unsigned int
1710 ip_vs_forward_icmp(unsigned int hooknum, struct sk_buff *skb,
1711                    const struct net_device *in, const struct net_device *out,
1712                    int (*okfn)(struct sk_buff *))
1713 {
1714         int r;
1715
1716         if (ip_hdr(skb)->protocol != IPPROTO_ICMP)
1717                 return NF_ACCEPT;
1718
1719         return ip_vs_in_icmp(skb, &r, hooknum);
1720 }
1721
1722 #ifdef CONFIG_IP_VS_IPV6
1723 static unsigned int
1724 ip_vs_forward_icmp_v6(unsigned int hooknum, struct sk_buff *skb,
1725                       const struct net_device *in, const struct net_device *out,
1726                       int (*okfn)(struct sk_buff *))
1727 {
1728         int r;
1729
1730         if (ipv6_hdr(skb)->nexthdr != IPPROTO_ICMPV6)
1731                 return NF_ACCEPT;
1732
1733         return ip_vs_in_icmp_v6(skb, &r, hooknum);
1734 }
1735 #endif
1736
1737
1738 static struct nf_hook_ops ip_vs_ops[] __read_mostly = {
1739         /* After packet filtering, change source only for VS/NAT */
1740         {
1741                 .hook           = ip_vs_reply4,
1742                 .owner          = THIS_MODULE,
1743                 .pf             = PF_INET,
1744                 .hooknum        = NF_INET_LOCAL_IN,
1745                 .priority       = 99,
1746         },
1747         /* After packet filtering, forward packet through VS/DR, VS/TUN,
1748          * or VS/NAT(change destination), so that filtering rules can be
1749          * applied to IPVS. */
1750         {
1751                 .hook           = ip_vs_remote_request4,
1752                 .owner          = THIS_MODULE,
1753                 .pf             = PF_INET,
1754                 .hooknum        = NF_INET_LOCAL_IN,
1755                 .priority       = 101,
1756         },
1757         /* Before ip_vs_in, change source only for VS/NAT */
1758         {
1759                 .hook           = ip_vs_local_reply4,
1760                 .owner          = THIS_MODULE,
1761                 .pf             = PF_INET,
1762                 .hooknum        = NF_INET_LOCAL_OUT,
1763                 .priority       = -99,
1764         },
1765         /* After mangle, schedule and forward local requests */
1766         {
1767                 .hook           = ip_vs_local_request4,
1768                 .owner          = THIS_MODULE,
1769                 .pf             = PF_INET,
1770                 .hooknum        = NF_INET_LOCAL_OUT,
1771                 .priority       = -98,
1772         },
1773         /* After packet filtering (but before ip_vs_out_icmp), catch icmp
1774          * destined for 0.0.0.0/0, which is for incoming IPVS connections */
1775         {
1776                 .hook           = ip_vs_forward_icmp,
1777                 .owner          = THIS_MODULE,
1778                 .pf             = PF_INET,
1779                 .hooknum        = NF_INET_FORWARD,
1780                 .priority       = 99,
1781         },
1782         /* After packet filtering, change source only for VS/NAT */
1783         {
1784                 .hook           = ip_vs_reply4,
1785                 .owner          = THIS_MODULE,
1786                 .pf             = PF_INET,
1787                 .hooknum        = NF_INET_FORWARD,
1788                 .priority       = 100,
1789         },
1790 #ifdef CONFIG_IP_VS_IPV6
1791         /* After packet filtering, change source only for VS/NAT */
1792         {
1793                 .hook           = ip_vs_reply6,
1794                 .owner          = THIS_MODULE,
1795                 .pf             = PF_INET6,
1796                 .hooknum        = NF_INET_LOCAL_IN,
1797                 .priority       = 99,
1798         },
1799         /* After packet filtering, forward packet through VS/DR, VS/TUN,
1800          * or VS/NAT(change destination), so that filtering rules can be
1801          * applied to IPVS. */
1802         {
1803                 .hook           = ip_vs_remote_request6,
1804                 .owner          = THIS_MODULE,
1805                 .pf             = PF_INET6,
1806                 .hooknum        = NF_INET_LOCAL_IN,
1807                 .priority       = 101,
1808         },
1809         /* Before ip_vs_in, change source only for VS/NAT */
1810         {
1811                 .hook           = ip_vs_local_reply6,
1812                 .owner          = THIS_MODULE,
1813                 .pf             = PF_INET,
1814                 .hooknum        = NF_INET_LOCAL_OUT,
1815                 .priority       = -99,
1816         },
1817         /* After mangle, schedule and forward local requests */
1818         {
1819                 .hook           = ip_vs_local_request6,
1820                 .owner          = THIS_MODULE,
1821                 .pf             = PF_INET6,
1822                 .hooknum        = NF_INET_LOCAL_OUT,
1823                 .priority       = -98,
1824         },
1825         /* After packet filtering (but before ip_vs_out_icmp), catch icmp
1826          * destined for 0.0.0.0/0, which is for incoming IPVS connections */
1827         {
1828                 .hook           = ip_vs_forward_icmp_v6,
1829                 .owner          = THIS_MODULE,
1830                 .pf             = PF_INET6,
1831                 .hooknum        = NF_INET_FORWARD,
1832                 .priority       = 99,
1833         },
1834         /* After packet filtering, change source only for VS/NAT */
1835         {
1836                 .hook           = ip_vs_reply6,
1837                 .owner          = THIS_MODULE,
1838                 .pf             = PF_INET6,
1839                 .hooknum        = NF_INET_FORWARD,
1840                 .priority       = 100,
1841         },
1842 #endif
1843 };
1844
1845 /*
1846  *      Initialize IP Virtual Server netns mem.
1847  */
1848 static int __net_init __ip_vs_init(struct net *net)
1849 {
1850         struct netns_ipvs *ipvs;
1851
1852         if (!net_eq(net, &init_net)) {
1853                 pr_err("The final patch for enabling netns is missing\n");
1854                 return -EPERM;
1855         }
1856         ipvs = net_generic(net, ip_vs_net_id);
1857         if (ipvs == NULL) {
1858                 pr_err("%s(): no memory.\n", __func__);
1859                 return -ENOMEM;
1860         }
1861         /* Counters used for creating unique names */
1862         ipvs->gen = atomic_read(&ipvs_netns_cnt);
1863         atomic_inc(&ipvs_netns_cnt);
1864         net->ipvs = ipvs;
1865         printk(KERN_INFO "IPVS: Creating netns size=%lu id=%d\n",
1866                          sizeof(struct netns_ipvs), ipvs->gen);
1867         return 0;
1868 }
1869
1870 static void __net_exit __ip_vs_cleanup(struct net *net)
1871 {
1872         struct netns_ipvs *ipvs = net_ipvs(net);
1873
1874         IP_VS_DBG(10, "ipvs netns %d released\n", ipvs->gen);
1875 }
1876
1877 static struct pernet_operations ipvs_core_ops = {
1878         .init = __ip_vs_init,
1879         .exit = __ip_vs_cleanup,
1880         .id   = &ip_vs_net_id,
1881         .size = sizeof(struct netns_ipvs),
1882 };
1883
1884 /*
1885  *      Initialize IP Virtual Server
1886  */
1887 static int __init ip_vs_init(void)
1888 {
1889         int ret;
1890
1891         ret = register_pernet_subsys(&ipvs_core_ops);   /* Alloc ip_vs struct */
1892         if (ret < 0)
1893                 return ret;
1894
1895         ip_vs_estimator_init();
1896         ret = ip_vs_control_init();
1897         if (ret < 0) {
1898                 pr_err("can't setup control.\n");
1899                 goto cleanup_estimator;
1900         }
1901
1902         ip_vs_protocol_init();
1903
1904         ret = ip_vs_app_init();
1905         if (ret < 0) {
1906                 pr_err("can't setup application helper.\n");
1907                 goto cleanup_protocol;
1908         }
1909
1910         ret = ip_vs_conn_init();
1911         if (ret < 0) {
1912                 pr_err("can't setup connection table.\n");
1913                 goto cleanup_app;
1914         }
1915
1916         ret = ip_vs_sync_init();
1917         if (ret < 0) {
1918                 pr_err("can't setup sync data.\n");
1919                 goto cleanup_conn;
1920         }
1921
1922         ret = nf_register_hooks(ip_vs_ops, ARRAY_SIZE(ip_vs_ops));
1923         if (ret < 0) {
1924                 pr_err("can't register hooks.\n");
1925                 goto cleanup_sync;
1926         }
1927
1928         pr_info("ipvs loaded.\n");
1929         return ret;
1930
1931 cleanup_sync:
1932         ip_vs_sync_cleanup();
1933   cleanup_conn:
1934         ip_vs_conn_cleanup();
1935   cleanup_app:
1936         ip_vs_app_cleanup();
1937   cleanup_protocol:
1938         ip_vs_protocol_cleanup();
1939         ip_vs_control_cleanup();
1940   cleanup_estimator:
1941         ip_vs_estimator_cleanup();
1942         unregister_pernet_subsys(&ipvs_core_ops);       /* free ip_vs struct */
1943         return ret;
1944 }
1945
1946 static void __exit ip_vs_cleanup(void)
1947 {
1948         nf_unregister_hooks(ip_vs_ops, ARRAY_SIZE(ip_vs_ops));
1949         ip_vs_sync_cleanup();
1950         ip_vs_conn_cleanup();
1951         ip_vs_app_cleanup();
1952         ip_vs_protocol_cleanup();
1953         ip_vs_control_cleanup();
1954         ip_vs_estimator_cleanup();
1955         unregister_pernet_subsys(&ipvs_core_ops);       /* free ip_vs struct */
1956         pr_info("ipvs unloaded.\n");
1957 }
1958
1959 module_init(ip_vs_init);
1960 module_exit(ip_vs_cleanup);
1961 MODULE_LICENSE("GPL");