Linux Audio

Check our new training course

Loading...
Note: File does not exist in v3.1.
  1/*
  2 * (C) 1999-2001 Paul `Rusty' Russell
  3 * (C) 2002-2006 Netfilter Core Team <coreteam@netfilter.org>
  4 * (C) 2011 Patrick McHardy <kaber@trash.net>
  5 *
  6 * This program is free software; you can redistribute it and/or modify
  7 * it under the terms of the GNU General Public License version 2 as
  8 * published by the Free Software Foundation.
  9 */
 10
 11#include <linux/module.h>
 12#include <linux/skbuff.h>
 13#include <linux/netfilter.h>
 14#include <linux/netfilter/x_tables.h>
 15#include <net/netfilter/nf_nat_core.h>
 16
 17static int xt_nat_checkentry_v0(const struct xt_tgchk_param *par)
 18{
 19	const struct nf_nat_ipv4_multi_range_compat *mr = par->targinfo;
 20
 21	if (mr->rangesize != 1) {
 22		pr_info("%s: multiple ranges no longer supported\n",
 23			par->target->name);
 24		return -EINVAL;
 25	}
 26	return nf_ct_netns_get(par->net, par->family);
 27}
 28
 29static int xt_nat_checkentry(const struct xt_tgchk_param *par)
 30{
 31	return nf_ct_netns_get(par->net, par->family);
 32}
 33
 34static void xt_nat_destroy(const struct xt_tgdtor_param *par)
 35{
 36	nf_ct_netns_put(par->net, par->family);
 37}
 38
 39static void xt_nat_convert_range(struct nf_nat_range *dst,
 40				 const struct nf_nat_ipv4_range *src)
 41{
 42	memset(&dst->min_addr, 0, sizeof(dst->min_addr));
 43	memset(&dst->max_addr, 0, sizeof(dst->max_addr));
 44
 45	dst->flags	 = src->flags;
 46	dst->min_addr.ip = src->min_ip;
 47	dst->max_addr.ip = src->max_ip;
 48	dst->min_proto	 = src->min;
 49	dst->max_proto	 = src->max;
 50}
 51
 52static unsigned int
 53xt_snat_target_v0(struct sk_buff *skb, const struct xt_action_param *par)
 54{
 55	const struct nf_nat_ipv4_multi_range_compat *mr = par->targinfo;
 56	struct nf_nat_range range;
 57	enum ip_conntrack_info ctinfo;
 58	struct nf_conn *ct;
 59
 60	ct = nf_ct_get(skb, &ctinfo);
 61	NF_CT_ASSERT(ct != NULL &&
 62		     (ctinfo == IP_CT_NEW || ctinfo == IP_CT_RELATED ||
 63		      ctinfo == IP_CT_RELATED_REPLY));
 64
 65	xt_nat_convert_range(&range, &mr->range[0]);
 66	return nf_nat_setup_info(ct, &range, NF_NAT_MANIP_SRC);
 67}
 68
 69static unsigned int
 70xt_dnat_target_v0(struct sk_buff *skb, const struct xt_action_param *par)
 71{
 72	const struct nf_nat_ipv4_multi_range_compat *mr = par->targinfo;
 73	struct nf_nat_range range;
 74	enum ip_conntrack_info ctinfo;
 75	struct nf_conn *ct;
 76
 77	ct = nf_ct_get(skb, &ctinfo);
 78	NF_CT_ASSERT(ct != NULL &&
 79		     (ctinfo == IP_CT_NEW || ctinfo == IP_CT_RELATED));
 80
 81	xt_nat_convert_range(&range, &mr->range[0]);
 82	return nf_nat_setup_info(ct, &range, NF_NAT_MANIP_DST);
 83}
 84
 85static unsigned int
 86xt_snat_target_v1(struct sk_buff *skb, const struct xt_action_param *par)
 87{
 88	const struct nf_nat_range *range = par->targinfo;
 89	enum ip_conntrack_info ctinfo;
 90	struct nf_conn *ct;
 91
 92	ct = nf_ct_get(skb, &ctinfo);
 93	NF_CT_ASSERT(ct != NULL &&
 94		     (ctinfo == IP_CT_NEW || ctinfo == IP_CT_RELATED ||
 95		      ctinfo == IP_CT_RELATED_REPLY));
 96
 97	return nf_nat_setup_info(ct, range, NF_NAT_MANIP_SRC);
 98}
 99
100static unsigned int
101xt_dnat_target_v1(struct sk_buff *skb, const struct xt_action_param *par)
102{
103	const struct nf_nat_range *range = par->targinfo;
104	enum ip_conntrack_info ctinfo;
105	struct nf_conn *ct;
106
107	ct = nf_ct_get(skb, &ctinfo);
108	NF_CT_ASSERT(ct != NULL &&
109		     (ctinfo == IP_CT_NEW || ctinfo == IP_CT_RELATED));
110
111	return nf_nat_setup_info(ct, range, NF_NAT_MANIP_DST);
112}
113
114static struct xt_target xt_nat_target_reg[] __read_mostly = {
115	{
116		.name		= "SNAT",
117		.revision	= 0,
118		.checkentry	= xt_nat_checkentry_v0,
119		.destroy	= xt_nat_destroy,
120		.target		= xt_snat_target_v0,
121		.targetsize	= sizeof(struct nf_nat_ipv4_multi_range_compat),
122		.family		= NFPROTO_IPV4,
123		.table		= "nat",
124		.hooks		= (1 << NF_INET_POST_ROUTING) |
125				  (1 << NF_INET_LOCAL_IN),
126		.me		= THIS_MODULE,
127	},
128	{
129		.name		= "DNAT",
130		.revision	= 0,
131		.checkentry	= xt_nat_checkentry_v0,
132		.destroy	= xt_nat_destroy,
133		.target		= xt_dnat_target_v0,
134		.targetsize	= sizeof(struct nf_nat_ipv4_multi_range_compat),
135		.family		= NFPROTO_IPV4,
136		.table		= "nat",
137		.hooks		= (1 << NF_INET_PRE_ROUTING) |
138				  (1 << NF_INET_LOCAL_OUT),
139		.me		= THIS_MODULE,
140	},
141	{
142		.name		= "SNAT",
143		.revision	= 1,
144		.checkentry	= xt_nat_checkentry,
145		.destroy	= xt_nat_destroy,
146		.target		= xt_snat_target_v1,
147		.targetsize	= sizeof(struct nf_nat_range),
148		.table		= "nat",
149		.hooks		= (1 << NF_INET_POST_ROUTING) |
150				  (1 << NF_INET_LOCAL_IN),
151		.me		= THIS_MODULE,
152	},
153	{
154		.name		= "DNAT",
155		.revision	= 1,
156		.checkentry	= xt_nat_checkentry,
157		.destroy	= xt_nat_destroy,
158		.target		= xt_dnat_target_v1,
159		.targetsize	= sizeof(struct nf_nat_range),
160		.table		= "nat",
161		.hooks		= (1 << NF_INET_PRE_ROUTING) |
162				  (1 << NF_INET_LOCAL_OUT),
163		.me		= THIS_MODULE,
164	},
165};
166
167static int __init xt_nat_init(void)
168{
169	return xt_register_targets(xt_nat_target_reg,
170				   ARRAY_SIZE(xt_nat_target_reg));
171}
172
173static void __exit xt_nat_exit(void)
174{
175	xt_unregister_targets(xt_nat_target_reg, ARRAY_SIZE(xt_nat_target_reg));
176}
177
178module_init(xt_nat_init);
179module_exit(xt_nat_exit);
180
181MODULE_LICENSE("GPL");
182MODULE_AUTHOR("Patrick McHardy <kaber@trash.net>");
183MODULE_ALIAS("ipt_SNAT");
184MODULE_ALIAS("ipt_DNAT");
185MODULE_ALIAS("ip6t_SNAT");
186MODULE_ALIAS("ip6t_DNAT");