2 * Automatic port forwarding target. When this target is entered, a
3 * related connection to a port in the reply direction will be
4 * expected. This connection may be mapped to a different port.
6 * Copyright 2005, Broadcom Corporation
9 * THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
10 * KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
11 * SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
12 * FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
14 * $Id: libipt_autofw.c,v 1.1.1.7 2005/03/07 07:31:14 kanki Exp $
17 /* Shared library add-on to iptables to add masquerade support. */
24 #include <linux/netfilter_ipv4/ip_tables.h>
25 #include <linux/netfilter_ipv4/ip_nat_rule.h>
26 #include <linux/netfilter_ipv4/ip_autofw.h>
28 /* Function which prints out usage message. */
33 "autofw v%s options:\n"
34 " --related-proto proto\n"
36 " --related-dport port[-port]\n"
37 " Related destination port range\n"
38 " --related-to port[-port]\n"
39 " Port range to map related destination port range to.\n\n",
43 static struct option opts
[] = {
44 { "related-proto", 1, 0, '1' },
45 { "related-dport", 1, 0, '2' },
46 { "related-to", 1, 0, '3' },
50 /* Initialize the target. */
52 init(struct ipt_entry_target
*t
, unsigned int *nfcache
)
54 /* Can't cache this */
55 *nfcache
|= NFC_UNKNOWN
;
60 parse_ports(const char *arg
, u_int16_t
*ports
)
66 if (port
== 0 || port
> 65535)
67 exit_error(PARAMETER_PROBLEM
, "Port `%s' not valid\n", arg
);
69 dash
= strchr(arg
, '-');
71 ports
[0] = ports
[1] = htons(port
);
75 maxport
= atoi(dash
+ 1);
76 if (maxport
== 0 || maxport
> 65535)
77 exit_error(PARAMETER_PROBLEM
,
78 "Port `%s' not valid\n", dash
+1);
80 /* People are stupid. */
81 exit_error(PARAMETER_PROBLEM
,
82 "Port range `%s' funky\n", arg
);
83 ports
[0] = htons(port
);
84 ports
[1] = htons(maxport
);
89 /* Function which parses command options; returns true if it
92 parse(int c
, char **argv
, int invert
, unsigned int *flags
,
93 const struct ipt_entry
*entry
,
94 struct ipt_entry_target
**target
)
96 struct ip_autofw_info
*info
= (struct ip_autofw_info
*)(*target
)->data
;
100 if (!strcasecmp(optarg
, "tcp"))
101 info
->proto
= IPPROTO_TCP
;
102 else if (!strcasecmp(optarg
, "udp"))
103 info
->proto
= IPPROTO_UDP
;
105 exit_error(PARAMETER_PROBLEM
,
106 "unknown protocol `%s' specified", optarg
);
110 if (check_inverse(optarg
, &invert
, &optind
, 0))
111 exit_error(PARAMETER_PROBLEM
,
112 "Unexpected `!' after --related-dport");
114 parse_ports(optarg
, info
->dport
);
118 if (check_inverse(optarg
, &invert
, &optind
, 0))
119 exit_error(PARAMETER_PROBLEM
,
120 "Unexpected `!' after --related-to");
122 parse_ports(optarg
, info
->to
);
123 *flags
|= IP_NAT_RANGE_PROTO_SPECIFIED
;
131 /* Final check; don't care. */
132 static void final_check(unsigned int flags
)
136 /* Prints out the targinfo. */
138 print(const struct ipt_ip
*ip
,
139 const struct ipt_entry_target
*target
,
142 struct ip_autofw_info
*info
= (struct ip_autofw_info
*)target
->data
;
145 if (info
->proto
== IPPROTO_TCP
)
147 else if (info
->proto
== IPPROTO_UDP
)
149 printf("dpt:%hu", ntohs(info
->dport
[0]));
150 if (ntohs(info
->dport
[1]) > ntohs(info
->dport
[0]))
151 printf("-%hu", ntohs(info
->dport
[1]));
153 printf("to:%hu", ntohs(info
->to
[0]));
154 if (ntohs(info
->to
[1]) > ntohs(info
->to
[0]))
155 printf("-%hu", ntohs(info
->to
[1]));
159 /* Saves the union ipt_targinfo in parsable form to stdout. */
161 save(const struct ipt_ip
*ip
, const struct ipt_entry_target
*target
)
163 struct ip_autofw_info
*info
= (struct ip_autofw_info
*)target
->data
;
165 printf("--related-proto ");
166 if (info
->proto
== IPPROTO_TCP
)
168 else if (info
->proto
== IPPROTO_UDP
)
170 printf("--related-dport %hu-%hu ", ntohs(info
->dport
[0]), ntohs(info
->dport
[1]));
171 printf("--related-to %hu-%hu ", ntohs(info
->to
[0]), ntohs(info
->to
[1]));
174 struct iptables_target autofw
178 IPT_ALIGN(sizeof(struct ip_autofw_info
)),
179 IPT_ALIGN(sizeof(struct ip_autofw_info
)),
191 register_target(&autofw
);