version 1.0.0.-a - significat iptables parsing speed improvement
[svn/Prometheus-QoS/.git] / parseiptables.c
1 /* Modified by: xChaos, 20131208 */
2
3 #include "cll1-0.6.2.h"
4 #include "ipstruct.h"
5
6 #define STRLEN 256
7
8 /* globals declared in prometheus.c */
9 extern struct IP *ips, *ip, *sharedip;
10 extern char *mark;
11 /* extern char *proxy_ip; */
12 extern int free_min;
13 extern int free_max;
14 extern int include_upload;
15
16 int traffic_detected = 0;
17 extern char *iptablesdump;
18
19 /* ===================== traffic analyser - uses iptables ================ */
20
21 void get_traffic_statistics(const char *whichiptables, int ipv6)
22 {
23 char *str,*cmd;
24 int downloadflag = 0;
25 FILE *f;
26 string(cmd,STRLEN);
27
28 sprintf(cmd, "%s -L -v -x -n -t mangle>%s", whichiptables, iptablesdump);
29 /*-----------------------------------------------------------------*/
30 printf("Running %s ...\n", cmd);
31 /*-----------------------------------------------------------------*/
32 system(cmd);
33 /*-----------------------------------------------------------------*/
34 printf("Processing %s ...\n", iptablesdump);
35 /*-----------------------------------------------------------------*/
36 f = fopen(iptablesdump,"r");
37 if(!f)
38 perror(iptablesdump);
39
40 while(!feof(f))
41 {
42 int col, accept = 0, /*proxyflag = 0, */valid = 1, setchainname = 0, commonflag = 0;
43 unsigned long long traffic = 0;
44 unsigned long pkts = 0;
45 char *ipaddr = NULL,*ptr;
46
47 string(str, STRLEN);
48 fgets(str, STRLEN, f);
49 valid_columns(ptr, str, ' ', col)
50 if(valid) switch(col)
51 {
52 case 1: if(eq(ptr,"Chain"))
53 {
54 setchainname = 1;
55 }
56 else if(eq(ptr,"pkts"))
57 {
58 valid = 0;
59 }
60 else
61 {
62 sscanf(ptr,"%lu",&pkts);
63 }
64 break;
65 case 2: if(setchainname)
66 {
67 if(!strncmp(ptr,"post_",5) || eq(ptr,"POSTROUTING"))
68 {
69 downloadflag = 1;
70 }
71 else
72 {
73 if(!strncmp(ptr,"forw_",5) || eq(ptr,"FORWARD"))
74 {
75 downloadflag = 0;
76 }
77 }
78 if(eq(ptr,"post_common") || eq(ptr,"forw_common"))
79 {
80 commonflag = 1;
81 }
82 }
83 else
84 {
85 sscanf(ptr,"%Lu",&traffic);
86 traffic += (1<<19);
87 traffic >>= 20;
88 }
89 break;
90 case 3: if((strncmp(ptr,"post_",5) && strncmp(ptr,"forw_",5)) || commonflag)
91 {
92 accept = eq(ptr,mark);
93 }
94 break;
95 case 7: if(ipv6 && !downloadflag)
96 {
97 ipaddr = ptr;
98 }
99 break;
100 case 8: if(ipv6 && downloadflag)
101 {
102 ipaddr = ptr;
103 }
104 else if(!ipv6)
105 {
106 /* if(downloadflag)
107 {
108 if(strstr(proxy_ip,ptr))
109 {
110 proxyflag = 1;
111 }
112
113 }
114 else
115 { */
116 if(!downloadflag)
117 {
118 ipaddr = ptr;
119 }
120 }
121 break;
122 case 9: if(!ipv6 && downloadflag)
123 {
124 ipaddr = ptr;
125 }
126 break;
127 }
128
129 if(accept && traffic>0 && ipaddr)
130 {
131 /* IPv6 subnet - /64 */
132 char *isipv6 = strstr(ipaddr,"/64");
133 if(ipv6 && isipv6)
134 {
135 *isipv6=0;
136 printf("(IPv6) ");
137 }
138 else
139 {
140 printf("(IPv4) ");
141 }
142 /*
143 if(proxyflag)
144 {
145 printf("(proxy) ");
146 }
147 else
148 */
149 if(!downloadflag)
150 {
151 printf("(up) ");
152 }
153 else
154 {
155 printf("(down) ");
156 }
157
158 traffic_detected = 1;
159 printf("%s %Lu MB (%ld pkts)\n", ipaddr, traffic, pkts);
160
161 if_exists(ip, ips, eqi(ip->addr,ipaddr));
162 else
163 {
164 TheIP(ipaddr, FALSE);
165 if(eq(ip->addr,"0.0.0.0/0"))
166 {
167 ip->name = "(unregistered)";
168 ip->min = free_min;
169 ip->max = ip->desired=free_max;
170 }
171 else
172 {
173 ip->name = ipaddr;
174 }
175 }
176
177 if(downloadflag)
178 {
179 /*
180 if(proxyflag)
181 {
182 ip->proxy = traffic;
183 }
184 else
185 {*/
186 ip->traffic += traffic;
187 ip->traffic_down += traffic;
188 /* } */
189 ip->direct += traffic; /*-ip->proxy;*/
190 ip->pktsdown += pkts;
191 }
192 else
193 {
194 ip->upload += traffic;
195 ip->traffic_up += traffic;
196 ip->pktsup += pkts;
197 if(include_upload)
198 {
199 ip->traffic += traffic;
200 }
201 else
202 {
203 if(ip->upload > ip->traffic)
204 {
205 ip->traffic = ip->upload;
206 }
207 }
208 }
209 }
210 }
211 free(cmd);
212 }
This page took 0.51582 seconds and 4 git commands to generate.