This source file includes following definitions.
- port_match
- ip_fw_chk
- masq_expire
- alloc_masq_entry
- revamp
- recalc_check
- ip_fw_masquerade
- ip_fw_demasquerade
- zero_fw_chain
- free_fw_chain
- add_to_chain
- del_from_chain
- check_ipfw_struct
- ip_acct_cnt
- ip_acct_ctl
- ip_fw_ctl
- ip_chain_procinfo
- ip_acct_procinfo
- ip_fw_blk_procinfo
- ip_fw_fwd_procinfo
- ip_msqhst_procinfo
- ipfw_input_check
- ipfw_forward_check
- ip_fw_init
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67 #include <linux/config.h>
68 #include <asm/segment.h>
69 #include <asm/system.h>
70 #include <linux/types.h>
71 #include <linux/kernel.h>
72 #include <linux/sched.h>
73 #include <linux/string.h>
74 #include <linux/errno.h>
75 #include <linux/config.h>
76
77 #include <linux/socket.h>
78 #include <linux/sockios.h>
79 #include <linux/in.h>
80 #include <linux/inet.h>
81 #include <linux/netdevice.h>
82 #include <linux/icmp.h>
83 #include <linux/udp.h>
84 #include <net/ip.h>
85 #include <net/protocol.h>
86 #include <net/route.h>
87 #include <net/tcp.h>
88 #include <net/udp.h>
89 #include <linux/skbuff.h>
90 #include <net/sock.h>
91 #include <net/icmp.h>
92 #include <linux/firewall.h>
93 #include <linux/ip_fw.h>
94 #include <net/checksum.h>
95 #include <linux/proc_fs.h>
96 #include <linux/stat.h>
97
98
99
100
101
102 #ifdef CONFIG_IPFIREWALL_DEBUG
103 #define dprintf1(a) printk(a)
104 #define dprintf2(a1,a2) printk(a1,a2)
105 #define dprintf3(a1,a2,a3) printk(a1,a2,a3)
106 #define dprintf4(a1,a2,a3,a4) printk(a1,a2,a3,a4)
107 #else
108 #define dprintf1(a)
109 #define dprintf2(a1,a2)
110 #define dprintf3(a1,a2,a3)
111 #define dprintf4(a1,a2,a3,a4)
112 #endif
113
114 #define print_ip(a) printk("%ld.%ld.%ld.%ld",(ntohl(a)>>24)&0xFF,\
115 (ntohl(a)>>16)&0xFF,\
116 (ntohl(a)>>8)&0xFF,\
117 (ntohl(a))&0xFF);
118
119 #ifdef IPFIREWALL_DEBUG
120 #define dprint_ip(a) print_ip(a)
121 #else
122 #define dprint_ip(a)
123 #endif
124
125 #ifdef CONFIG_IP_FIREWALL
126 struct ip_fw *ip_fw_fwd_chain;
127 struct ip_fw *ip_fw_blk_chain;
128 int ip_fw_blk_policy=IP_FW_F_ACCEPT;
129 int ip_fw_fwd_policy=IP_FW_F_ACCEPT;
130 #endif
131 #ifdef CONFIG_IP_ACCT
132 struct ip_fw *ip_acct_chain;
133 #endif
134
135 #define IP_INFO_BLK 0
136 #define IP_INFO_FWD 1
137 #define IP_INFO_ACCT 2
138
139 #ifdef CONFIG_IP_MASQUERADE
140
141
142
143
144 static unsigned short masq_port = PORT_MASQ_BEGIN;
145 static const char *strProt[] = {"UDP","TCP"};
146 struct ip_masq *ip_msq_hosts;
147
148 #endif
149
150
151
152
153
154 extern inline int port_match(unsigned short *portptr,int nports,unsigned short port,int range_flag)
155 {
156 if (!nports)
157 return 1;
158 if ( range_flag )
159 {
160 if ( portptr[0] <= port && port <= portptr[1] )
161 {
162 return( 1 );
163 }
164 nports -= 2;
165 portptr += 2;
166 }
167 while ( nports-- > 0 )
168 {
169 if ( *portptr++ == port )
170 {
171 return( 1 );
172 }
173 }
174 return(0);
175 }
176
177 #if defined(CONFIG_IP_ACCT) || defined(CONFIG_IP_FIREWALL)
178
179
180
181
182
183
184
185
186
187
188
189
190
191 int ip_fw_chk(struct iphdr *ip, struct device *rif, struct ip_fw *chain, int policy, int opt)
192 {
193 struct ip_fw *f;
194 struct tcphdr *tcp=(struct tcphdr *)((unsigned long *)ip+ip->ihl);
195 struct udphdr *udp=(struct udphdr *)((unsigned long *)ip+ip->ihl);
196 struct icmphdr *icmp=(struct icmphdr *)((unsigned long *)ip+ip->ihl);
197 __u32 src, dst;
198 __u16 src_port=0, dst_port=0, icmp_type=0;
199 unsigned short f_prt=0, prt;
200 char notcpsyn=1, notcpack=1, match;
201 unsigned short offset;
202 int answer, priority;
203
204
205
206
207
208
209
210 src = ip->saddr;
211 dst = ip->daddr;
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227 offset = ntohs(ip->frag_off) & IP_OFFSET;
228
229
230
231
232
233
234
235
236 if (offset == 1 && ip->protocol == IPPROTO_TCP)
237 return FW_BLOCK;
238
239 if (offset!=0 && (opt != 1) && (ip->protocol == IPPROTO_TCP ||
240 ip->protocol == IPPROTO_UDP))
241 return FW_ACCEPT;
242
243
244
245
246
247 if(ip->protocol==IPPROTO_TCP && (ip->ihl<<2)+16 > ntohs(ip->tot_len))
248 return FW_BLOCK;
249
250
251
252
253
254 else if(ntohs(ip->tot_len)<8+(ip->ihl<<2))
255 return FW_BLOCK;
256
257 src = ip->saddr;
258 dst = ip->daddr;
259
260
261
262
263
264
265
266
267
268 dprintf1("Packet ");
269 switch(ip->protocol)
270 {
271 case IPPROTO_TCP:
272 dprintf1("TCP ");
273
274 if (!offset) {
275 src_port=ntohs(tcp->source);
276 dst_port=ntohs(tcp->dest);
277 if(tcp->ack)
278
279 notcpack=0;
280 if(tcp->syn && notcpack)
281
282 notcpsyn=0;
283 }
284 prt=IP_FW_F_TCP;
285 break;
286 case IPPROTO_UDP:
287 dprintf1("UDP ");
288
289 if (!offset) {
290 src_port=ntohs(udp->source);
291 dst_port=ntohs(udp->dest);
292 }
293 prt=IP_FW_F_UDP;
294 break;
295 case IPPROTO_ICMP:
296 icmp_type=(__u16)(icmp->type);
297 dprintf2("ICMP:%d ",icmp_type);
298 prt=IP_FW_F_ICMP;
299 break;
300 default:
301 dprintf2("p=%d ",ip->protocol);
302 prt=IP_FW_F_ALL;
303 break;
304 }
305 #ifdef CONFIG_IP_FIREWALL_DEBUG
306 dprint_ip(ip->saddr);
307
308 if (ip->protocol==IPPROTO_TCP || ip->protocol==IPPROTO_UDP)
309
310 dprintf2(":%d ", src_port);
311 dprint_ip(ip->daddr);
312 if (ip->protocol==IPPROTO_TCP || ip->protocol==IPPROTO_UDP)
313
314 dprintf2(":%d ",dst_port);
315 dprintf1("\n");
316 #endif
317
318 for (f=chain;f;f=f->fw_next)
319 {
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337 match = 0x00;
338
339 if ((src&f->fw_smsk.s_addr)==f->fw_src.s_addr
340 && (dst&f->fw_dmsk.s_addr)==f->fw_dst.s_addr)
341
342 match |= 0x01;
343
344 if ((f->fw_flg & IP_FW_F_BIDIR) &&
345 (dst&f->fw_smsk.s_addr)==f->fw_src.s_addr
346 && (src&f->fw_dmsk.s_addr)==f->fw_dst.s_addr)
347
348 match |= 0x02;
349
350 if (match)
351 {
352
353
354
355 if(f->fw_via.s_addr && rif)
356 {
357 if(rif->pa_addr!=f->fw_via.s_addr)
358 continue;
359 }
360
361
362
363 }
364 else
365 continue;
366
367
368
369
370
371 f_prt=f->fw_flg&IP_FW_F_KIND;
372 if (f_prt!=IP_FW_F_ALL)
373 {
374
375
376
377
378
379
380
381 if((f->fw_flg&IP_FW_F_TCPSYN) && notcpsyn)
382 continue;
383
384
385
386
387
388
389
390
391 if((f->fw_flg&IP_FW_F_TCPACK) && notcpack)
392 if(f->fw_flg&IP_FW_F_BIDIR) {
393 if(match & 0x02)
394 continue;
395 } else
396 continue;
397
398
399
400
401
402
403 if(prt!=f_prt)
404 continue;
405
406 if((prt==IP_FW_F_ICMP &&
407 ! port_match(&f->fw_pts[0], f->fw_nsp,
408 icmp_type,f->fw_flg&IP_FW_F_SRNG)) ||
409 !(prt==IP_FW_F_ICMP || ((match & 0x01) &&
410 port_match(&f->fw_pts[0], f->fw_nsp, src_port,
411 f->fw_flg&IP_FW_F_SRNG) &&
412 port_match(&f->fw_pts[f->fw_nsp], f->fw_ndp, dst_port,
413 f->fw_flg&IP_FW_F_DRNG)) || ((match & 0x02) &&
414 port_match(&f->fw_pts[0], f->fw_nsp, dst_port,
415 f->fw_flg&IP_FW_F_SRNG) &&
416 port_match(&f->fw_pts[f->fw_nsp], f->fw_ndp, src_port,
417 f->fw_flg&IP_FW_F_DRNG))))
418 {
419 continue;
420 }
421 }
422 #ifdef CONFIG_IP_FIREWALL_VERBOSE
423
424
425
426
427
428 if (f->fw_flg & IP_FW_F_PRN)
429 {
430 if(opt != 1) {
431 if(f->fw_flg&IP_FW_F_ACCEPT)
432 printk("Accept ");
433 else if(f->fw_flg&IP_FW_F_ICMPRPL)
434 printk("Reject ");
435 else
436 printk("Deny ");
437 }
438 switch(ip->protocol)
439 {
440 case IPPROTO_TCP:
441 printk("TCP ");
442 break;
443 case IPPROTO_UDP:
444 printk("UDP ");
445 case IPPROTO_ICMP:
446 printk("ICMP:%d ",icmp_type);
447 break;
448 default:
449 printk("p=%d ",ip->protocol);
450 break;
451 }
452 print_ip(ip->saddr);
453 if(ip->protocol == IPPROTO_TCP || ip->protocol == IPPROTO_UDP)
454 printk(":%d", src_port);
455 printk(" ");
456 print_ip(ip->daddr);
457 if(ip->protocol == IPPROTO_TCP || ip->protocol == IPPROTO_UDP)
458 printk(":%d",dst_port);
459 printk("\n");
460 }
461 #endif
462 if (opt != 2) {
463 f->fw_bcnt+=ntohs(ip->tot_len);
464 f->fw_pcnt++;
465 }
466 if (opt != 1)
467 break;
468 }
469
470 answer = FW_BLOCK;
471
472
473
474
475
476
477
478 if(f!=NULL)
479 {
480 policy=f->fw_flg;
481 priority=f->fw_priority;
482 }
483 else
484 priority=0xFF00;
485
486 if(opt != 1)
487 {
488 if(policy&IP_FW_F_ACCEPT)
489 answer=(policy&IP_FW_F_MASQ)?FW_MASQUERADE:FW_ACCEPT;
490 else
491 if(policy&IP_FW_F_ICMPRPL)
492 answer = FW_REJECT;
493 }
494
495 if (answer == 0) {
496 __u8 old_tos = ip->tos;
497 ip->tos = (old_tos & (priority>>8)) ^ priority;
498 if (ip->tos != old_tos)
499 ip_send_check(ip);
500 }
501
502 return answer;
503 }
504
505 #ifdef CONFIG_IP_MASQUERADE
506
507 static void masq_expire(unsigned long data)
508 {
509 struct ip_masq *ms = (struct ip_masq *)data;
510 struct ip_masq *old,*cur;
511 unsigned long flags;
512
513 #ifdef DEBUG_MASQ
514 printk("Masqueraded %s %lX:%X expired\n",
515 strProt[ms->protocol==IPPROTO_TCP],
516 ntohl(ms->src),ntohs(ms->sport));
517 #endif
518
519 save_flags(flags);
520 cli();
521
522
523 old = NULL;
524 cur = ip_msq_hosts;
525 while (cur!=NULL) {
526 if (cur==ms) {
527 if (old==NULL) ip_msq_hosts = ms->next;
528 else old->next = ms->next;
529 kfree_s(ms,sizeof(*ms));
530 break;
531 }
532 old = cur;
533 cur=cur->next;
534 }
535 restore_flags(flags);
536 }
537
538
539
540
541
542
543
544
545 static struct ip_masq *alloc_masq_entry(void)
546 {
547 struct ip_masq *ms, *mst;
548 unsigned long flags;
549
550 ms = (struct ip_masq *) kmalloc(sizeof(struct ip_masq), GFP_ATOMIC);
551 if (ms==NULL)
552 return NULL;
553
554 memset(ms,0,sizeof(*ms));
555 init_timer(&ms->timer);
556 ms->timer.data = (unsigned long)ms;
557 ms->timer.function = masq_expire;
558
559 save_flags(flags);
560 cli();
561 do
562 {
563
564 ms->mport = htons(masq_port++);
565 if (masq_port==PORT_MASQ_END)
566 masq_port = PORT_MASQ_BEGIN;
567
568
569
570 mst = ip_msq_hosts;
571 while (mst && mst->mport!=ms->mport)
572 mst = mst->next;
573 }
574 while (mst!=NULL);
575
576
577 ms->next = ip_msq_hosts;
578 ip_msq_hosts = ms;
579 restore_flags(flags);
580
581 return ms;
582 }
583
584
585
586
587
588
589
590
591
592
593
594
595
596 static struct sk_buff *revamp(struct sk_buff *skb, struct device *dev, struct ip_masq *ftp)
597 {
598 struct iphdr *iph = skb->h.iph;
599 struct tcphdr *th = (struct tcphdr *)&(((char *)iph)[iph->ihl*4]);
600 struct sk_buff *skb2;
601 char *p, *data = (char *)&th[1];
602 unsigned char p1,p2,p3,p4,p5,p6;
603 unsigned long from;
604 unsigned short port;
605 struct ip_masq *ms;
606 char buf[24];
607 int diff;
608 __u32 seq;
609
610
611
612
613
614
615
616
617
618 seq=ntohl(th->seq);
619 if (ftp->delta || ftp->previous_delta)
620 {
621 if(after(seq,ftp->init_seq) )
622 {
623 th->seq = htonl(seq + ftp->delta);
624 #ifdef DEBUG_MASQ
625 printk("masq_revamp : added delta (%d) to seq\n",ftp->delta);
626 #endif
627 }
628 else
629 {
630 th->seq = htonl(seq + ftp->previous_delta);
631 #ifdef DEBUG_MASQ
632 printk("masq_revamp : added previous_delta (%d) to seq\n",ftp->previous_delta);
633 #endif
634 }
635 }
636
637 while (skb->len - ((unsigned char *)data - skb->h.raw) > 18)
638 {
639 if (memcmp(data,"PORT ",5) && memcmp(data,"port ",5))
640 {
641 data ++;
642 continue;
643 }
644 p = data+5;
645 p1 = simple_strtoul(data+5,&data,10);
646 if (*data!=',')
647 continue;
648 p2 = simple_strtoul(data+1,&data,10);
649 if (*data!=',')
650 continue;
651 p3 = simple_strtoul(data+1,&data,10);
652 if (*data!=',')
653 continue;
654 p4 = simple_strtoul(data+1,&data,10);
655 if (*data!=',')
656 continue;
657 p5 = simple_strtoul(data+1,&data,10);
658 if (*data!=',')
659 continue;
660 p6 = simple_strtoul(data+1,&data,10);
661 if (*data!='\r' && *data!='\n')
662 continue;
663
664 from = (p1<<24) | (p2<<16) | (p3<<8) | p4;
665 port = (p5<<8) | p6;
666 #ifdef MASQ_DEBUG
667 printk("PORT %lX:%X detected\n",from,port);
668 #endif
669
670
671
672 ms = alloc_masq_entry();
673 if (ms==NULL)
674 return skb;
675 ms->protocol = IPPROTO_TCP;
676 ms->src = htonl(from);
677 ms->sport = htons(port);
678 ms->dst = iph->daddr;
679
680
681
682
683
684 ms->dport = htons(FTP_DPORT_TBD);
685 ms->timer.expires = jiffies+MASQUERADE_EXPIRE_TCP_FIN;
686 add_timer(&ms->timer);
687
688
689
690
691 from = ntohl(dev->pa_addr);
692 port = ntohs(ms->mport);
693 sprintf(buf,"%ld,%ld,%ld,%ld,%d,%d",
694 from>>24&255,from>>16&255,from>>8&255,from&255,
695 port>>8&255,port&255);
696
697
698
699
700
701 diff = strlen(buf) - (data-p);
702
703
704
705
706
707 if (diff==0)
708 {
709
710
711
712 memcpy(p,buf,strlen(buf));
713 return skb;
714 }
715
716
717
718
719
720
721
722
723
724
725
726 if(!ftp->init_seq || after(seq,ftp->init_seq) )
727 {
728 ftp->previous_delta=ftp->delta;
729 ftp->delta+=diff;
730 ftp->init_seq = seq;
731 }
732
733
734
735
736 #ifdef DEBUG_MASQ
737 printk("MASQUERADE: resizing needed for %d bytes (%ld)\n",diff, skb->len);
738 #endif
739 skb2 = alloc_skb(MAX_HEADER + skb->len+diff, GFP_ATOMIC);
740 if (skb2 == NULL) {
741 printk("MASQUERADE: No memory available\n");
742 return skb;
743 }
744 skb2->free = skb->free;
745 skb_reserve(skb2,MAX_HEADER);
746 skb_put(skb2,skb->len + diff);
747 skb2->h.raw = skb2->data + (skb->h.raw - skb->data);
748 iph=skb2->h.iph;
749
750
751
752 iph->tot_len = htons(diff+ntohs(iph->tot_len));
753 iph->check = 0;
754 iph->check = ip_fast_csum((unsigned char *)iph, iph->ihl);
755
756
757
758
759
760 memcpy(skb2->data, skb->data, (p - (char *)skb->data));
761 memcpy(&skb2->data[(p - (char *)skb->data)], buf, strlen(buf));
762 memcpy(&skb2->data[(p - (char *)skb->data) + strlen(buf)], data,
763 skb->len - (data-(char *)skb->data));
764
765
766
767
768
769 iph->tot_len = htons(skb->len + diff);
770
771
772
773
774
775
776 kfree_skb(skb, FREE_WRITE);
777 return skb2;
778 }
779 return skb;
780 }
781
782 static void recalc_check(struct udphdr *uh, unsigned long saddr,
783 unsigned long daddr, int len)
784 {
785 uh->check=0;
786 uh->check=csum_tcpudp_magic(saddr,daddr,len,
787 IPPROTO_UDP, csum_partial((char *)uh,len,0));
788 if(uh->check==0)
789 uh->check=0xFFFF;
790 }
791
792 void ip_fw_masquerade(struct sk_buff **skb_ptr, struct device *dev)
793 {
794 struct sk_buff *skb=*skb_ptr;
795 struct iphdr *iph = skb->h.iph;
796 unsigned short *portptr;
797 struct ip_masq *ms;
798 int size;
799
800
801
802
803
804 if (iph->protocol!=IPPROTO_UDP && iph->protocol!=IPPROTO_TCP)
805 return;
806
807
808
809
810
811 portptr = (unsigned short *)&(((char *)iph)[iph->ihl*4]);
812 ms = ip_msq_hosts;
813
814 #ifdef DEBUG_MASQ
815 printk("Outgoing %s %lX:%X -> %lX:%X\n",
816 strProt[iph->protocol==IPPROTO_TCP],
817 ntohl(iph->saddr), ntohs(portptr[0]),
818 ntohl(iph->daddr), ntohs(portptr[1]));
819 #endif
820 while (ms!=NULL)
821 {
822 if (iph->protocol == ms->protocol &&
823 iph->saddr == ms->src && iph->daddr == ms->dst &&
824 portptr[0] == ms->sport && portptr[1] == ms->dport)
825 {
826 del_timer(&ms->timer);
827 break;
828 }
829 ms = ms->next;
830 }
831
832
833
834
835
836 if (ms==NULL)
837 {
838 ms = alloc_masq_entry();
839 if (ms==NULL)
840 {
841 printk("MASQUERADE: no memory left !\n");
842 return;
843 }
844 ms->protocol = iph->protocol;
845 ms->src = iph->saddr;
846 ms->dst = iph->daddr;
847 ms->sport = portptr[0];
848 ms->dport = portptr[1];
849 }
850
851
852
853
854
855 size = skb->len - ((unsigned char *)portptr - skb->h.raw);
856 iph->saddr = dev->pa_addr;
857 portptr[0] = ms->mport;
858
859
860
861
862
863 if (iph->protocol==IPPROTO_UDP)
864 {
865 ms->timer.expires = jiffies+MASQUERADE_EXPIRE_UDP;
866 recalc_check((struct udphdr *)portptr,iph->saddr,iph->daddr,size);
867 }
868 else
869 {
870 struct tcphdr *th;
871 if (portptr[1]==htons(21))
872 {
873 skb = revamp(*skb_ptr, dev, ms);
874 *skb_ptr = skb;
875 iph = skb->h.iph;
876 portptr = (unsigned short *)&(((char *)iph)[iph->ihl*4]);
877 size = skb->len - ((unsigned char *)portptr-skb->h.raw);
878 }
879 th = (struct tcphdr *)portptr;
880
881
882
883
884 if (ms->sawfin || th->fin)
885 {
886 ms->timer.expires = jiffies+MASQUERADE_EXPIRE_TCP_FIN;
887 ms->sawfin = 1;
888 }
889 else ms->timer.expires = jiffies+MASQUERADE_EXPIRE_TCP;
890
891 tcp_send_check(th,iph->saddr,iph->daddr,size,skb->sk);
892 }
893 add_timer(&ms->timer);
894 ip_send_check(iph);
895
896 #ifdef DEBUG_MASQ
897 printk("O-routed from %lX:%X over %s\n",ntohl(dev->pa_addr),ntohs(ms->mport),dev->name);
898 #endif
899 }
900
901
902
903
904
905
906
907
908
909
910 int ip_fw_demasquerade(struct sk_buff *skb_ptr)
911 {
912 struct iphdr *iph = skb_ptr->h.iph;
913 unsigned short *portptr;
914 struct ip_masq *ms;
915 struct tcphdr *th = (struct tcphdr *)(skb_ptr->h.raw+(iph->ihl<<2));
916
917 if (iph->protocol!=IPPROTO_UDP && iph->protocol!=IPPROTO_TCP)
918 return 0;
919
920 portptr = (unsigned short *)&(((char *)iph)[iph->ihl*4]);
921 if (ntohs(portptr[1]) < PORT_MASQ_BEGIN ||
922 ntohs(portptr[1]) > PORT_MASQ_END)
923 return 0;
924
925 #ifdef DEBUG_MASQ
926 printk("Incoming %s %lX:%X -> %lX:%X\n",
927 strProt[iph->protocol==IPPROTO_TCP],
928 ntohl(iph->saddr), ntohs(portptr[0]),
929 ntohl(iph->daddr), ntohs(portptr[1]));
930 #endif
931
932
933
934
935
936
937
938
939
940
941 ms = ip_msq_hosts;
942 while (ms!=NULL)
943 {
944 if (iph->protocol==ms->protocol &&
945 (iph->saddr==ms->dst || iph->protocol==IPPROTO_UDP) &&
946 (ms->dport==htons(FTP_DPORT_TBD) || portptr[0]==ms->dport) &&
947 portptr[1]==ms->mport)
948 {
949
950 int size = skb_ptr->len - ((unsigned char *)portptr - skb_ptr->h.raw);
951 iph->daddr = ms->src;
952 portptr[1] = ms->sport;
953
954 if(ms->dport==htons(FTP_DPORT_TBD))
955 {
956 ms->dport=portptr[0];
957 #ifdef DEBUG_MASQ
958 printk("demasq : Filled out dport entry (%d) based on initial connect attempt from FTP deamon\n",ntohs(ms->dport));
959 #endif
960 }
961
962
963
964
965 if (iph->protocol==IPPROTO_UDP)
966 recalc_check((struct udphdr *)portptr,iph->saddr,iph->daddr,size);
967 else
968 {
969 __u32 ack_seq;
970
971
972
973
974
975 #ifdef DEBUG_MASQ
976 printk("demasq : delta=%d ; previous_delta=%d ; init_seq=%lX ; ack_seq=%lX ; after=%d\n",ms->delta,ms->previous_delta,ntohl(ms->init_seq),ntohl(th->ack_seq),after(ntohl(th->ack_seq),ntohl(ms->init_seq)));
977 #endif
978 ack_seq=ntohl(th->ack_seq);
979 if (ms->delta || ms->previous_delta)
980 {
981 if(after(ack_seq,ms->init_seq))
982 {
983 th->ack_seq = htonl(ack_seq-ms->delta);
984 #ifdef DEBUG_MASQ
985 printk("demasq : substracted delta (%d) from ack_seq\n",ms->delta);
986 #endif
987 }
988 else
989 {
990 th->ack_seq = htonl(ack_seq-ms->previous_delta);
991 #ifdef DEBUG_MASQ
992 printk("demasq : substracted previous_delta (%d) from ack_seq\n",ms->previous_delta);
993 #endif
994 }
995 }
996 tcp_send_check((struct tcphdr *)portptr,iph->saddr,iph->daddr,size,skb_ptr->sk);
997 }
998 ip_send_check(iph);
999 #ifdef DEBUG_MASQ
1000 printk("I-routed to %lX:%X\n",ntohl(iph->daddr),ntohs(portptr[1]));
1001 #endif
1002 return 1;
1003 }
1004 ms = ms->next;
1005 }
1006
1007
1008 return 0;
1009 }
1010 #endif
1011
1012
1013
1014 static void zero_fw_chain(struct ip_fw *chainptr)
1015 {
1016 struct ip_fw *ctmp=chainptr;
1017 while(ctmp)
1018 {
1019 ctmp->fw_pcnt=0L;
1020 ctmp->fw_bcnt=0L;
1021 ctmp=ctmp->fw_next;
1022 }
1023 }
1024
1025 static void free_fw_chain(struct ip_fw *volatile* chainptr)
1026 {
1027 unsigned long flags;
1028 save_flags(flags);
1029 cli();
1030 while ( *chainptr != NULL )
1031 {
1032 struct ip_fw *ftmp;
1033 ftmp = *chainptr;
1034 *chainptr = ftmp->fw_next;
1035 kfree_s(ftmp,sizeof(*ftmp));
1036 }
1037 restore_flags(flags);
1038 }
1039
1040
1041
1042 static int add_to_chain(struct ip_fw *volatile* chainptr, struct ip_fw *frwl,int len)
1043 {
1044 struct ip_fw *ftmp;
1045 struct ip_fw *chtmp=NULL;
1046 struct ip_fw *volatile chtmp_prev=NULL;
1047 unsigned long flags;
1048 unsigned long m_src_mask,m_dst_mask;
1049 unsigned long n_sa,n_da,o_sa,o_da,o_sm,o_dm,n_sm,n_dm;
1050 unsigned short n_sr,n_dr,o_sr,o_dr;
1051 unsigned short oldkind,newkind;
1052 int addb4=0;
1053 int n_o,n_n;
1054
1055 save_flags(flags);
1056
1057 ftmp = kmalloc( sizeof(struct ip_fw), GFP_ATOMIC );
1058 if ( ftmp == NULL )
1059 {
1060 #ifdef DEBUG_CONFIG_IP_FIREWALL
1061 printk("ip_fw_ctl: malloc said no\n");
1062 #endif
1063 return( ENOMEM );
1064 }
1065
1066 memcpy(ftmp, frwl, len);
1067 if (len == sizeof (struct ip_fw_old))
1068 ftmp->fw_priority = 0xFF00;
1069
1070 ftmp->fw_priority = (ftmp->fw_priority & 0xFFFC) | 0x0300;
1071 ftmp->fw_pcnt=0L;
1072 ftmp->fw_bcnt=0L;
1073
1074 ftmp->fw_next = NULL;
1075
1076 cli();
1077
1078 if (*chainptr==NULL)
1079 {
1080 *chainptr=ftmp;
1081 }
1082 else
1083 {
1084 chtmp_prev=NULL;
1085 for (chtmp=*chainptr;chtmp!=NULL;chtmp=chtmp->fw_next)
1086 {
1087 if (ftmp->fw_flg & IP_FW_F_APPEND) {
1088 chtmp_prev=chtmp;
1089 continue;
1090 }
1091 addb4=0;
1092 newkind=ftmp->fw_flg & IP_FW_F_KIND;
1093 oldkind=chtmp->fw_flg & IP_FW_F_KIND;
1094
1095 if (newkind!=IP_FW_F_ALL
1096 && oldkind!=IP_FW_F_ALL
1097 && oldkind!=newkind)
1098 {
1099 chtmp_prev=chtmp;
1100 continue;
1101 }
1102
1103
1104
1105
1106
1107
1108 n_sa=ntohl(ftmp->fw_src.s_addr);
1109 n_da=ntohl(ftmp->fw_dst.s_addr);
1110 n_sm=ntohl(ftmp->fw_smsk.s_addr);
1111 n_dm=ntohl(ftmp->fw_dmsk.s_addr);
1112
1113 o_sa=ntohl(chtmp->fw_src.s_addr);
1114 o_da=ntohl(chtmp->fw_dst.s_addr);
1115 o_sm=ntohl(chtmp->fw_smsk.s_addr);
1116 o_dm=ntohl(chtmp->fw_dmsk.s_addr);
1117
1118 m_src_mask = o_sm & n_sm;
1119 m_dst_mask = o_dm & n_dm;
1120
1121 if ((o_sa & m_src_mask) == (n_sa & m_src_mask))
1122 {
1123 if (n_sm > o_sm)
1124 addb4++;
1125 if (n_sm < o_sm)
1126 addb4--;
1127 }
1128
1129 if ((o_da & m_dst_mask) == (n_da & m_dst_mask))
1130 {
1131 if (n_dm > o_dm)
1132 addb4++;
1133 if (n_dm < o_dm)
1134 addb4--;
1135 }
1136
1137 if (((o_da & o_dm) == (n_da & n_dm))
1138 &&((o_sa & o_sm) == (n_sa & n_sm)))
1139 {
1140 if (newkind!=IP_FW_F_ALL &&
1141 oldkind==IP_FW_F_ALL)
1142 addb4++;
1143 if (newkind==oldkind && (oldkind==IP_FW_F_TCP
1144 || oldkind==IP_FW_F_UDP))
1145 {
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158 if (ftmp->fw_flg & IP_FW_F_SRNG)
1159 n_sr=ftmp->fw_pts[1]-ftmp->fw_pts[0];
1160 else
1161 n_sr=(ftmp->fw_nsp)?
1162 ftmp->fw_nsp : 0xFFFF;
1163
1164 if (chtmp->fw_flg & IP_FW_F_SRNG)
1165 o_sr=chtmp->fw_pts[1]-chtmp->fw_pts[0];
1166 else
1167 o_sr=(chtmp->fw_nsp)?chtmp->fw_nsp : 0xFFFF;
1168
1169 if (n_sr<o_sr)
1170 addb4++;
1171 if (n_sr>o_sr)
1172 addb4--;
1173
1174 n_n=ftmp->fw_nsp;
1175 n_o=chtmp->fw_nsp;
1176
1177
1178
1179
1180
1181
1182
1183 if ((n_n>(IP_FW_MAX_PORTS-2)) ||
1184 (n_o>(IP_FW_MAX_PORTS-2)))
1185 goto skip_check;
1186
1187 if (ftmp->fw_flg & IP_FW_F_DRNG)
1188 n_dr=ftmp->fw_pts[n_n+1]-ftmp->fw_pts[n_n];
1189 else
1190 n_dr=(ftmp->fw_ndp)? ftmp->fw_ndp : 0xFFFF;
1191
1192 if (chtmp->fw_flg & IP_FW_F_DRNG)
1193 o_dr=chtmp->fw_pts[n_o+1]-chtmp->fw_pts[n_o];
1194 else
1195 o_dr=(chtmp->fw_ndp)? chtmp->fw_ndp : 0xFFFF;
1196 if (n_dr<o_dr)
1197 addb4++;
1198 if (n_dr>o_dr)
1199 addb4--;
1200 skip_check:
1201 }
1202
1203 if ((addb4 == 0) && ftmp->fw_via.s_addr &&
1204 !(chtmp->fw_via.s_addr))
1205 addb4++;
1206 }
1207 if (addb4>0)
1208 {
1209 if (chtmp_prev)
1210 {
1211 chtmp_prev->fw_next=ftmp;
1212 ftmp->fw_next=chtmp;
1213 }
1214 else
1215 {
1216 *chainptr=ftmp;
1217 ftmp->fw_next=chtmp;
1218 }
1219 restore_flags(flags);
1220 return 0;
1221 }
1222 chtmp_prev=chtmp;
1223 }
1224 }
1225
1226 if (chtmp_prev)
1227 chtmp_prev->fw_next=ftmp;
1228 else
1229 *chainptr=ftmp;
1230 restore_flags(flags);
1231 return(0);
1232 }
1233
1234 static int del_from_chain(struct ip_fw *volatile*chainptr, struct ip_fw *frwl)
1235 {
1236 struct ip_fw *ftmp,*ltmp;
1237 unsigned short tport1,tport2,tmpnum;
1238 char matches,was_found;
1239 unsigned long flags;
1240
1241 save_flags(flags);
1242 cli();
1243
1244 ftmp=*chainptr;
1245
1246 if ( ftmp == NULL )
1247 {
1248 #ifdef DEBUG_CONFIG_IP_FIREWALL
1249 printk("ip_fw_ctl: chain is empty\n");
1250 #endif
1251 restore_flags(flags);
1252 return( EINVAL );
1253 }
1254
1255 ltmp=NULL;
1256 was_found=0;
1257
1258 while( ftmp != NULL )
1259 {
1260 matches=1;
1261 if (ftmp->fw_src.s_addr!=frwl->fw_src.s_addr
1262 || ftmp->fw_dst.s_addr!=frwl->fw_dst.s_addr
1263 || ftmp->fw_smsk.s_addr!=frwl->fw_smsk.s_addr
1264 || ftmp->fw_dmsk.s_addr!=frwl->fw_dmsk.s_addr
1265 || ftmp->fw_via.s_addr!=frwl->fw_via.s_addr
1266 || ftmp->fw_flg!=frwl->fw_flg)
1267 matches=0;
1268
1269 tport1=ftmp->fw_nsp+ftmp->fw_ndp;
1270 tport2=frwl->fw_nsp+frwl->fw_ndp;
1271 if (tport1!=tport2)
1272 matches=0;
1273 else if (tport1!=0)
1274 {
1275 for (tmpnum=0;tmpnum < tport1 && tmpnum < IP_FW_MAX_PORTS;tmpnum++)
1276 if (ftmp->fw_pts[tmpnum]!=frwl->fw_pts[tmpnum])
1277 matches=0;
1278 }
1279 if(matches)
1280 {
1281 was_found=1;
1282 if (ltmp)
1283 {
1284 ltmp->fw_next=ftmp->fw_next;
1285 kfree_s(ftmp,sizeof(*ftmp));
1286 ftmp=ltmp->fw_next;
1287 }
1288 else
1289 {
1290 *chainptr=ftmp->fw_next;
1291 kfree_s(ftmp,sizeof(*ftmp));
1292 ftmp=*chainptr;
1293 }
1294 }
1295 else
1296 {
1297 ltmp = ftmp;
1298 ftmp = ftmp->fw_next;
1299 }
1300 }
1301 restore_flags(flags);
1302 if (was_found)
1303 return 0;
1304 else
1305 return(EINVAL);
1306 }
1307
1308 #endif
1309
1310 struct ip_fw *check_ipfw_struct(struct ip_fw *frwl, int len)
1311 {
1312
1313 if ( len != sizeof(struct ip_fw) && len != sizeof(struct ip_fw_old))
1314 {
1315 #ifdef DEBUG_CONFIG_IP_FIREWALL
1316 printk("ip_fw_ctl: len=%d, want %d\n",len, sizeof(struct ip_fw));
1317 #endif
1318 return(NULL);
1319 }
1320
1321 if ( (frwl->fw_flg & ~IP_FW_F_MASK) != 0 )
1322 {
1323 #ifdef DEBUG_CONFIG_IP_FIREWALL
1324 printk("ip_fw_ctl: undefined flag bits set (flags=%x)\n",
1325 frwl->fw_flg);
1326 #endif
1327 return(NULL);
1328 }
1329
1330 if ( (frwl->fw_flg & IP_FW_F_SRNG) && frwl->fw_nsp < 2 )
1331 {
1332 #ifdef DEBUG_CONFIG_IP_FIREWALL
1333 printk("ip_fw_ctl: src range set but fw_nsp=%d\n",
1334 frwl->fw_nsp);
1335 #endif
1336 return(NULL);
1337 }
1338
1339 if ( (frwl->fw_flg & IP_FW_F_DRNG) && frwl->fw_ndp < 2 )
1340 {
1341 #ifdef DEBUG_CONFIG_IP_FIREWALL
1342 printk("ip_fw_ctl: dst range set but fw_ndp=%d\n",
1343 frwl->fw_ndp);
1344 #endif
1345 return(NULL);
1346 }
1347
1348 if ( frwl->fw_nsp + frwl->fw_ndp > IP_FW_MAX_PORTS )
1349 {
1350 #ifdef DEBUG_CONFIG_IP_FIREWALL
1351 printk("ip_fw_ctl: too many ports (%d+%d)\n",
1352 frwl->fw_nsp,frwl->fw_ndp);
1353 #endif
1354 return(NULL);
1355 }
1356
1357 return frwl;
1358 }
1359
1360
1361
1362
1363 #ifdef CONFIG_IP_ACCT
1364
1365 #if 0
1366 void ip_acct_cnt(struct iphdr *iph, struct device *dev, struct ip_fw *f)
1367 {
1368 (void) ip_fw_chk(iph, dev, f, 0, 1);
1369 return;
1370 }
1371 #endif
1372
1373 int ip_acct_ctl(int stage, void *m, int len)
1374 {
1375 if ( stage == IP_ACCT_FLUSH )
1376 {
1377 free_fw_chain(&ip_acct_chain);
1378 return(0);
1379 }
1380 if ( stage == IP_ACCT_ZERO )
1381 {
1382 zero_fw_chain(ip_acct_chain);
1383 return(0);
1384 }
1385 if ( stage == IP_ACCT_ADD
1386 || stage == IP_ACCT_DEL
1387 )
1388 {
1389 struct ip_fw *frwl;
1390
1391 if (!(frwl=check_ipfw_struct(m,len)))
1392 return (EINVAL);
1393
1394 switch (stage)
1395 {
1396 case IP_ACCT_ADD:
1397 return( add_to_chain(&ip_acct_chain,frwl,len));
1398 case IP_ACCT_DEL:
1399 return( del_from_chain(&ip_acct_chain,frwl));
1400 default:
1401
1402
1403
1404 #ifdef DEBUG_CONFIG_IP_FIREWALL
1405 printk("ip_acct_ctl: unknown request %d\n",stage);
1406 #endif
1407 return(EINVAL);
1408 }
1409 }
1410 #ifdef DEBUG_CONFIG_IP_FIREWALL
1411 printk("ip_acct_ctl: unknown request %d\n",stage);
1412 #endif
1413 return(EINVAL);
1414 }
1415 #endif
1416
1417 #ifdef CONFIG_IP_FIREWALL
1418 int ip_fw_ctl(int stage, void *m, int len)
1419 {
1420 int ret;
1421
1422 if ( stage == IP_FW_FLUSH_BLK )
1423 {
1424 free_fw_chain(&ip_fw_blk_chain);
1425 return(0);
1426 }
1427
1428 if ( stage == IP_FW_FLUSH_FWD )
1429 {
1430 free_fw_chain(&ip_fw_fwd_chain);
1431 return(0);
1432 }
1433
1434 if ( stage == IP_FW_ZERO_BLK )
1435 {
1436 zero_fw_chain(ip_fw_blk_chain);
1437 return(0);
1438 }
1439
1440 if ( stage == IP_FW_ZERO_FWD )
1441 {
1442 zero_fw_chain(ip_fw_fwd_chain);
1443 return(0);
1444 }
1445
1446 if ( stage == IP_FW_POLICY_BLK || stage == IP_FW_POLICY_FWD )
1447 {
1448 int *tmp_policy_ptr;
1449 tmp_policy_ptr=(int *)m;
1450 if ( stage == IP_FW_POLICY_BLK )
1451 ip_fw_blk_policy=*tmp_policy_ptr;
1452 else
1453 ip_fw_fwd_policy=*tmp_policy_ptr;
1454 return 0;
1455 }
1456
1457 if ( stage == IP_FW_CHK_BLK || stage == IP_FW_CHK_FWD )
1458 {
1459 struct device viadev;
1460 struct ip_fwpkt *ipfwp;
1461 struct iphdr *ip;
1462
1463 if ( len < sizeof(struct ip_fwpkt) )
1464 {
1465 #ifdef DEBUG_CONFIG_IP_FIREWALL
1466 printk("ip_fw_ctl: length=%d, expected %d\n",
1467 len, sizeof(struct ip_fwpkt));
1468 #endif
1469 return( EINVAL );
1470 }
1471
1472 ipfwp = (struct ip_fwpkt *)m;
1473 ip = &(ipfwp->fwp_iph);
1474
1475 if ( ip->ihl != sizeof(struct iphdr) / sizeof(int))
1476 {
1477 #ifdef DEBUG_CONFIG_IP_FIREWALL
1478 printk("ip_fw_ctl: ip->ihl=%d, want %d\n",ip->ihl,
1479 sizeof(struct iphdr)/sizeof(int));
1480 #endif
1481 return(EINVAL);
1482 }
1483
1484 viadev.pa_addr = ipfwp->fwp_via.s_addr;
1485
1486 if ((ret = ip_fw_chk(ip, &viadev,
1487 stage == IP_FW_CHK_BLK ?
1488 ip_fw_blk_chain : ip_fw_fwd_chain,
1489 stage == IP_FW_CHK_BLK ?
1490 ip_fw_blk_policy : ip_fw_fwd_policy, 2 )) > 0
1491 )
1492 return(0);
1493 else if (ret == -1)
1494 return(ECONNREFUSED);
1495 else
1496 return(ETIMEDOUT);
1497 }
1498
1499
1500
1501
1502
1503
1504 if ( stage == IP_FW_ADD_BLK || stage == IP_FW_ADD_FWD
1505 || stage == IP_FW_DEL_BLK || stage == IP_FW_DEL_FWD
1506 )
1507 {
1508 struct ip_fw *frwl;
1509 frwl=check_ipfw_struct(m,len);
1510 if (frwl==NULL)
1511 return (EINVAL);
1512
1513 switch (stage)
1514 {
1515 case IP_FW_ADD_BLK:
1516 return(add_to_chain(&ip_fw_blk_chain,frwl,len));
1517 case IP_FW_ADD_FWD:
1518 return(add_to_chain(&ip_fw_fwd_chain,frwl,len));
1519 case IP_FW_DEL_BLK:
1520 return(del_from_chain(&ip_fw_blk_chain,frwl));
1521 case IP_FW_DEL_FWD:
1522 return(del_from_chain(&ip_fw_fwd_chain,frwl));
1523 default:
1524
1525
1526
1527 #ifdef DEBUG_CONFIG_IP_FIREWALL
1528 printk("ip_fw_ctl: unknown request %d\n",stage);
1529 #endif
1530 return(EINVAL);
1531 }
1532 }
1533
1534 #ifdef DEBUG_CONFIG_IP_FIREWALL
1535 printk("ip_fw_ctl: unknown request %d\n",stage);
1536 #endif
1537 return(EINVAL);
1538 }
1539 #endif
1540
1541 #if defined(CONFIG_IP_FIREWALL) || defined(CONFIG_IP_ACCT)
1542
1543 static int ip_chain_procinfo(int stage, char *buffer, char **start,
1544 off_t offset, int length, int reset)
1545 {
1546 off_t pos=0, begin=0;
1547 struct ip_fw *i;
1548 unsigned long flags;
1549 int len, p;
1550
1551
1552 switch(stage)
1553 {
1554 #ifdef CONFIG_IP_FIREWALL
1555 case IP_INFO_BLK:
1556 i = ip_fw_blk_chain;
1557 len=sprintf(buffer, "IP firewall block rules, default %d\n",
1558 ip_fw_blk_policy);
1559 break;
1560 case IP_INFO_FWD:
1561 i = ip_fw_fwd_chain;
1562 len=sprintf(buffer, "IP firewall forward rules, default %d\n",
1563 ip_fw_fwd_policy);
1564 break;
1565 #endif
1566 #ifdef CONFIG_IP_ACCT
1567 case IP_INFO_ACCT:
1568 i = ip_acct_chain;
1569 len=sprintf(buffer,"IP accounting rules\n");
1570 break;
1571 #endif
1572 default:
1573
1574 i = NULL;
1575 len=0;
1576 break;
1577 }
1578
1579 save_flags(flags);
1580 cli();
1581
1582 while(i!=NULL)
1583 {
1584 len+=sprintf(buffer+len,"%08lX/%08lX->%08lX/%08lX %08lX %X ",
1585 ntohl(i->fw_src.s_addr),ntohl(i->fw_smsk.s_addr),
1586 ntohl(i->fw_dst.s_addr),ntohl(i->fw_dmsk.s_addr),
1587 ntohl(i->fw_via.s_addr),i->fw_flg);
1588 len+=sprintf(buffer+len,"%u %u %-9lu %-9lu",
1589 i->fw_nsp,i->fw_ndp, i->fw_pcnt,i->fw_bcnt);
1590 for (p = 0; p < IP_FW_MAX_PORTS; p++)
1591 len+=sprintf(buffer+len, " %u", i->fw_pts[p]);
1592 len+=sprintf(buffer+len, " M%04X", i->fw_priority);
1593 buffer[len++]='\n';
1594 buffer[len]='\0';
1595 pos=begin+len;
1596 if(pos<offset)
1597 {
1598 len=0;
1599 begin=pos;
1600 }
1601 else if(reset)
1602 {
1603
1604 i->fw_pcnt=0L;
1605 i->fw_bcnt=0L;
1606 }
1607 if(pos>offset+length)
1608 break;
1609 i=i->fw_next;
1610 }
1611 restore_flags(flags);
1612 *start=buffer+(offset-begin);
1613 len-=(offset-begin);
1614 if(len>length)
1615 len=length;
1616 return len;
1617 }
1618 #endif
1619
1620 #ifdef CONFIG_IP_ACCT
1621
1622 static int ip_acct_procinfo(char *buffer, char **start, off_t offset,
1623 int length, int reset)
1624 {
1625 return ip_chain_procinfo(IP_INFO_ACCT, buffer,start, offset,length,
1626 reset);
1627 }
1628
1629 #endif
1630
1631 #ifdef CONFIG_IP_FIREWALL
1632
1633 static int ip_fw_blk_procinfo(char *buffer, char **start, off_t offset,
1634 int length, int reset)
1635 {
1636 return ip_chain_procinfo(IP_INFO_BLK, buffer,start,offset,length,
1637 reset);
1638 }
1639
1640 static int ip_fw_fwd_procinfo(char *buffer, char **start, off_t offset,
1641 int length, int reset)
1642 {
1643 return ip_chain_procinfo(IP_INFO_FWD, buffer,start,offset,length,
1644 reset);
1645 }
1646 #endif
1647
1648 #ifdef CONFIG_IP_MASQUERADE
1649
1650 static int ip_msqhst_procinfo(char *buffer, char **start, off_t offset,
1651 int length, int unused)
1652 {
1653 off_t pos=0, begin=0;
1654 struct ip_masq *ms;
1655 unsigned long flags;
1656 int len=0;
1657
1658 len=sprintf(buffer,"Prc FromIP FPrt ToIP TPrt Masq Init-seq Delta PDelta Expires\n");
1659 save_flags(flags);
1660 cli();
1661
1662 ms=ip_msq_hosts;
1663 while (ms!=NULL)
1664 {
1665 int timer_active = del_timer(&ms->timer);
1666 if (!timer_active)
1667 ms->timer.expires = jiffies;
1668 len+=sprintf(buffer+len,"%s %08lX:%04X %08lX:%04X %04X %08X %5d %5d %lu\n",
1669 strProt[ms->protocol==IPPROTO_TCP],
1670 ntohl(ms->src),ntohs(ms->sport),
1671 ntohl(ms->dst),ntohs(ms->dport),
1672 ntohs(ms->mport),
1673 ms->init_seq,ms->delta,ms->previous_delta,ms->timer.expires-jiffies);
1674 if (timer_active)
1675 add_timer(&ms->timer);
1676
1677 pos=begin+len;
1678 if(pos<offset)
1679 {
1680 len=0;
1681 begin=pos;
1682 }
1683 if(pos>offset+length)
1684 break;
1685 ms=ms->next;
1686 }
1687 restore_flags(flags);
1688 *start=buffer+(offset-begin);
1689 len-=(offset-begin);
1690 if(len>length)
1691 len=length;
1692 return len;
1693 }
1694
1695 #endif
1696
1697 #ifdef CONFIG_IP_FIREWALL
1698
1699
1700
1701
1702 int ipfw_input_check(struct firewall_ops *this, int pf, struct sk_buff *skb, void *phdr)
1703 {
1704 return ip_fw_chk(phdr, skb->dev, ip_fw_blk_chain, ip_fw_blk_policy, 0);
1705 }
1706
1707 int ipfw_forward_check(struct firewall_ops *this, int pf, struct sk_buff *skb, void *phdr)
1708 {
1709 return ip_fw_chk(phdr, skb->dev, ip_fw_fwd_chain, ip_fw_fwd_policy, 0);
1710 }
1711
1712 struct firewall_ops ipfw_ops=
1713 {
1714 NULL,
1715 ipfw_forward_check,
1716 ipfw_input_check,
1717 ipfw_input_check,
1718 PF_INET,
1719 0
1720 };
1721
1722 #endif
1723
1724 void ip_fw_init(void)
1725 {
1726 #ifdef CONFIG_IP_ACCT
1727 proc_net_register(&(struct proc_dir_entry) {
1728 PROC_NET_IPACCT, 7, "ip_acct",
1729 S_IFREG | S_IRUGO | S_IWUSR, 1, 0, 0,
1730 0, &proc_net_inode_operations,
1731 ip_acct_procinfo
1732 });
1733 #endif
1734 #ifdef CONFIG_IP_FIREWALL
1735
1736 if(register_firewall(PF_INET,&ipfw_ops)<0)
1737 panic("Unable to register IP firewall.\n");
1738
1739 proc_net_register(&(struct proc_dir_entry) {
1740 PROC_NET_IPFWBLK, 8, "ip_block",
1741 S_IFREG | S_IRUGO | S_IWUSR, 1, 0, 0,
1742 0, &proc_net_inode_operations,
1743 ip_fw_blk_procinfo
1744 });
1745 proc_net_register(&(struct proc_dir_entry) {
1746 PROC_NET_IPFWFWD, 10, "ip_forward",
1747 S_IFREG | S_IRUGO | S_IWUSR, 1, 0, 0,
1748 0, &proc_net_inode_operations,
1749 ip_fw_fwd_procinfo
1750 });
1751 #endif
1752 #ifdef CONFIG_IP_MASQUERADE
1753 proc_net_register(&(struct proc_dir_entry) {
1754 PROC_NET_IPMSQHST, 13, "ip_masquerade",
1755 S_IFREG | S_IRUGO, 1, 0, 0,
1756 0, &proc_net_inode_operations,
1757 ip_msqhst_procinfo
1758 });
1759 #endif
1760 }