1 /* Shared library add-on to iptables to add connection limit support. */
9 #include <linux/netfilter_ipv4/ip_conntrack.h>
10 #include <linux/netfilter_ipv4/ipt_connlimit.h>
12 /* Function which prints out usage message. */
17 "connlimit v%s options:\n"
18 "[!] --connlimit-above n match if the number of existing tcp connections is (not) above n\n"
19 " --connlimit-mask n group hosts using mask\n"
20 "\n", IPTABLES_VERSION);
23 static struct option opts[] = {
24 { "connlimit-above", 1, 0, '1' },
25 { "connlimit-mask", 1, 0, '2' },
29 /* Initialize the match. */
31 init(struct ipt_entry_match *m, unsigned int *nfcache)
33 /* Can't cache this */
34 *nfcache |= NFC_UNKNOWN;
37 /* Function which parses command options; returns true if it
40 parse(int c, char **argv, int invert, unsigned int *flags,
41 const struct ipt_entry *entry,
42 unsigned int *nfcache,
43 struct ipt_entry_match **match)
45 struct ipt_connlimit_info *info = (struct ipt_connlimit_info*)(*match)->data;
47 if (0 == (*flags & 2)) {
48 /* set default mask unless we've already seen a mask option */
49 info->mask = htonl(0xFFFFFFFF);
54 check_inverse(optarg, &invert, &optind, 0);
55 info->limit = atoi(argv[optind-1]);
56 info->inverse = invert;
61 info->mask = htonl(0xFFFFFFFF << (32 - atoi(argv[optind-1])));
73 static void final_check(unsigned int flags)
76 exit_error(PARAMETER_PROBLEM, "You must specify `--connlimit-above'");
80 count_bits(u_int32_t mask)
84 for (bits = 0, i = 31; i >= 0; i--) {
85 if (mask & htonl((u_int32_t)1 << i)) {
94 /* Prints out the matchinfo. */
96 print(const struct ipt_ip *ip,
97 const struct ipt_entry_match *match,
100 struct ipt_connlimit_info *info = (struct ipt_connlimit_info*)match->data;
102 printf("#conn/%d %s %d ", count_bits(info->mask),
103 info->inverse ? "<" : ">", info->limit);
106 /* Saves the matchinfo in parsable form to stdout. */
107 static void save(const struct ipt_ip *ip, const struct ipt_entry_match *match)
109 struct ipt_connlimit_info *info = (struct ipt_connlimit_info*)match->data;
111 printf("%s--connlimit-above %d ",info->inverse ? "! " : "",info->limit);
112 printf("--connlimit-mask %d ",count_bits(info->mask));
115 static struct iptables_match connlimit = {
117 version: IPTABLES_VERSION,
118 size: IPT_ALIGN(sizeof(struct ipt_connlimit_info)),
119 userspacesize: offsetof(struct ipt_connlimit_info,data),
123 final_check: final_check,
131 register_match(&connlimit);