/*
 * ip_conntrack_proto_gre.c - Version 3.0 
 *
 * Connection tracking protocol helper module for GRE.
 *
 * GRE is a generic encapsulation protocol, which is generally not very
 * suited for NAT, as it has no protocol-specific part as port numbers.
 *
 * It has an optional key field, which may help us distinguishing two 
 * connections between the same two hosts.
 *
 * GRE is defined in RFC 1701 and RFC 1702, as well as RFC 2784 
 *
 * PPTP is built on top of a modified version of GRE, and has a mandatory
 * field called "CallID", which serves us for the same purpose as the key
 * field in plain GRE.
 *
 * Documentation about PPTP can be found in RFC 2637
 *
 * (C) 2000-2005 by Harald Welte <laforge@gnumonks.org>
 *
 * Development of this code funded by Astaro AG (http://www.astaro.com/)
 *
 */

#include <linux/module.h>
#include <linux/types.h>
#include <linux/timer.h>
#include <linux/netfilter.h>
#include <linux/ip.h>
#include <linux/in.h>
#include <linux/list.h>
#include <linux/seq_file.h>
#include <linux/interrupt.h>

static DEFINE_RWLOCK(ip_ct_gre_lock);
#define ASSERT_READ_LOCK(x)
#define ASSERT_WRITE_LOCK(x)

#include <linux/netfilter_ipv4/listhelp.h>
#include <linux/netfilter_ipv4/ip_conntrack_protocol.h>
#include <linux/netfilter_ipv4/ip_conntrack_helper.h>
#include <linux/netfilter_ipv4/ip_conntrack_core.h>

#include <linux/netfilter_ipv4/ip_conntrack_proto_gre.h>
#include <linux/netfilter_ipv4/ip_conntrack_pptp.h>

MODULE_LICENSE("GPL");
MODULE_AUTHOR("Harald Welte <laforge@gnumonks.org>");
MODULE_DESCRIPTION("netfilter connection tracking protocol helper for GRE");

/* shamelessly stolen from ip_conntrack_proto_udp.c */
#define GRE_TIMEOUT		(30*HZ)
#define GRE_STREAM_TIMEOUT	(180*HZ)

#if 0
#define DEBUGP(format, args...)	printk(KERN_DEBUG "%s:%s: " format, __FILE__, __FUNCTION__, ## args)
#define DUMP_TUPLE_GRE(x) printk("%u.%u.%u.%u:0x%x -> %u.%u.%u.%u:0x%x\n", \
			NIPQUAD((x)->src.ip), ntohs((x)->src.u.gre.key), \
			NIPQUAD((x)->dst.ip), ntohs((x)->dst.u.gre.key))
#else
#define DEBUGP(x, args...)
#define DUMP_TUPLE_GRE(x)
#endif
				
/* GRE KEYMAP HANDLING FUNCTIONS */
static LIST_HEAD(gre_keymap_list);

static inline int gre_key_cmpfn(const struct ip_ct_gre_keymap *km,
				const struct ip_conntrack_tuple *t)
{
	return ((km->tuple.src.ip == t->src.ip) &&
		(km->tuple.dst.ip == t->dst.ip) &&
		(km->tuple.dst.protonum == t->dst.protonum) &&
		(km->tuple.dst.u.all == t->dst.u.all));
}

/* look up the source key for a given tuple */
static __be16 gre_keymap_lookup(struct ip_conntrack_tuple *t)
{
	struct ip_ct_gre_keymap *km;
	__be16 key = 0;

	read_lock_bh(&ip_ct_gre_lock);
	km = LIST_FIND(&gre_keymap_list, gre_key_cmpfn,
			struct ip_ct_gre_keymap *, t);
	if (km)
		key = km->tuple.src.u.gre.key;
	read_unlock_bh(&ip_ct_gre_lock);
	
	DEBUGP("lookup src key 0x%x up key for ", key);
	DUMP_TUPLE_GRE(t);

	return key;
}

/* add a single keymap entry, associate with specified master ct */
int
ip_ct_gre_keymap_add(struct ip_conntrack *ct,
		     struct ip_conntrack_tuple *t, int reply)
{
	struct ip_ct_gre_keymap **exist_km, *km, *old;

	if (!ct->helper || strcmp(ct->helper->name, "pptp")) {
		DEBUGP("refusing to add GRE keymap to non-pptp session\n");
		return -1;
	}

	if (!reply) 
		exist_km = &ct->help.ct_pptp_info.keymap_orig;
	else
		exist_km = &ct->help.ct_pptp_info.keymap_reply;

	if (*exist_km) {
		/* check whether it's a retransmission */
		old = LIST_FIND(&gre_keymap_list, gre_key_cmpfn,
				struct ip_ct_gre_keymap *, t);
		if (old == *exist_km) {
			DEBUGP("retransmission\n");
			return 0;
		}

		DEBUGP("trying to override keymap_%s for ct %p\n", 
			reply? "reply":"orig", ct);
		return -EEXIST;
	}

	km = kmalloc(sizeof(*km), GFP_ATOMIC);
	if (!km)
		return -ENOMEM;

	memcpy(&km->tuple, t, sizeof(*t));
	*exist_km = km;

	DEBUGP("adding new entry %p: ", km);
	DUMP_TUPLE_GRE(&km->tuple);

	write_lock_bh(&ip_ct_gre_lock);
	list_append(&gre_keymap_list, km);
	write_unlock_bh(&ip_ct_gre_lock);

	return 0;
}

/* destroy the keymap entries associated with specified master ct */
void ip_ct_gre_keymap_destroy(struct ip_conntrack *ct)
{
	DEBUGP("entering for ct %p\n", ct);

	if (!ct->helper || strcmp(ct->helper->name, "pptp")) {
		DEBUGP("refusing to destroy GRE keymap to non-pptp session\n");
		return;
	}

	write_lock_bh(&ip_ct_gre_lock);
	if (ct->help.ct_pptp_info.keymap_orig) {
		DEBUGP("removing %p from list\n", 
			ct->help.ct_pptp_info.keymap_orig);
		list_del(&ct->help.ct_pptp_info.keymap_orig->list);
		kfree(ct->help.ct_pptp_info.keymap_orig);
		ct->help.ct_pptp_info.keymap_orig = NULL;
	}
	if (ct->help.ct_pptp_info.keymap_reply) {
		DEBUGP("removing %p from list\n",
			ct->help.ct_pptp_info.keymap_reply);
		list_del(&ct->help.ct_pptp_info.keymap_reply->list);
		kfree(ct->help.ct_pptp_info.keymap_reply);
		ct->help.ct_pptp_info.keymap_reply = NULL;
	}
	write_unlock_bh(&ip_ct_gre_lock);
}


/* PUBLIC CONNTRACK PROTO HELPER FUNCTIONS */

/* invert gre part of tuple */
static int gre_invert_tuple(struct ip_conntrack_tuple *tuple,
			    const struct ip_conntrack_tuple *orig)
{
	tuple->dst.u.gre.key = orig->src.u.gre.key;
	tuple->src.u.gre.key = orig->dst.u.gre.key;

	return 1;
}

/* gre hdr info to tuple */
static int gre_pkt_to_tuple(const struct sk_buff *skb,
			   unsigned int dataoff,
			   struct ip_conntrack_tuple *tuple)
{
	struct gre_hdr_pptp _pgrehdr, *pgrehdr;
	__be16 srckey;
	struct gre_hdr _grehdr, *grehdr;

	/* first only delinearize old RFC1701 GRE header */
	grehdr = skb_header_pointer(skb, dataoff, sizeof(_grehdr), &_grehdr);
	if (!grehdr || grehdr->version != GRE_VERSION_PPTP) {
		/* try to behave like "ip_conntrack_proto_generic" */
		tuple->src.u.all = 0;
		tuple->dst.u.all = 0;
		return 1;
	}

	/* PPTP header is variable length, only need up to the call_id field */
	pgrehdr = skb_header_pointer(skb, dataoff, 8, &_pgrehdr);
	if (!pgrehdr)
		return 1;

	if (ntohs(grehdr->protocol) != GRE_PROTOCOL_PPTP) {
		DEBUGP("GRE_VERSION_PPTP but unknown proto\n");
		return 0;
	}

	tuple->dst.u.gre.key = pgrehdr->call_id;
	srckey = gre_keymap_lookup(tuple);
	tuple->src.u.gre.key = srckey;

	return 1;
}

/* print gre part of tuple */
static int gre_print_tuple(struct seq_file *s,
			   const struct ip_conntrack_tuple *tuple)
{
	return seq_printf(s, "srckey=0x%x dstkey=0x%x ", 
			  ntohs(tuple->src.u.gre.key),
			  ntohs(tuple->dst.u.gre.key));
}

/* print private data for conntrack */
static int gre_print_conntrack(struct seq_file *s,
			       const struct ip_conntrack *ct)
{
	return seq_printf(s, "timeout=%u, stream_timeout=%u ",
			  (ct->proto.gre.timeout / HZ),
			  (ct->proto.gre.stream_timeout / HZ));
}

/* Returns verdict for packet, and may modify conntrack */
static int gre_packet(struct ip_conntrack *ct,
		      const struct sk_buff *skb,
		      enum ip_conntrack_info conntrackinfo)
{
	/* If we've seen traffic both ways, this is a GRE connection.
	 * Extend timeout. */
	if (ct->status & IPS_SEEN_REPLY) {
		ip_ct_refresh_acct(ct, conntrackinfo, skb,
				   ct->proto.gre.stream_timeout);
		/* Also, more likely to be important, and not a probe. */
		set_bit(IPS_ASSURED_BIT, &ct->status);
		ip_conntrack_event_cache(IPCT_STATUS, skb);
	} else
		ip_ct_refresh_acct(ct, conntrackinfo, skb,
				   ct->proto.gre.timeout);
	
	return NF_ACCEPT;
}

/* Called when a new connection for this protocol found. */
static int gre_new(struct ip_conntrack *ct,
		   const struct sk_buff *skb)
{ 
	DEBUGP(": ");
	DUMP_TUPLE_GRE(&ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple);

	/* initialize to sane value.  Ideally a conntrack helper
	 * (e.g. in case of pptp) is increasing them */
	ct->proto.gre.stream_timeout = GRE_STREAM_TIMEOUT;
	ct->proto.gre.timeout = GRE_TIMEOUT;

	return 1;
}

/* Called when a conntrack entry has already been removed from the hashes
 * and is about to be deleted from memory */
static void gre_destroy(struct ip_conntrack *ct)
{
	struct ip_conntrack *master = ct->master;
	DEBUGP(" entering\n");

	if (!master)
		DEBUGP("no master !?!\n");
	else
		ip_ct_gre_keymap_destroy(master);
}

/* protocol helper struct */
static struct ip_conntrack_protocol gre = { 
	.proto		 = IPPROTO_GRE,
	.name		 = "gre", 
	.pkt_to_tuple	 = gre_pkt_to_tuple,
	.invert_tuple	 = gre_invert_tuple,
	.print_tuple	 = gre_print_tuple,
	.print_conntrack = gre_print_conntrack,
	.packet		 = gre_packet,
	.new		 = gre_new,
	.destroy	 = gre_destroy,
	.me 		 = THIS_MODULE,
#if defined(CONFIG_IP_NF_CONNTRACK_NETLINK) || \
    defined(CONFIG_IP_NF_CONNTRACK_NETLINK_MODULE)
	.tuple_to_nfattr = ip_ct_port_tuple_to_nfattr,
	.nfattr_to_tuple = ip_ct_port_nfattr_to_tuple,
#endif
};

/* ip_conntrack_proto_gre initialization */
int __init ip_ct_proto_gre_init(void)
{
	return ip_conntrack_protocol_register(&gre);
}

/* This cannot be __exit, as it is invoked from ip_conntrack_helper_pptp.c's
 * init() code on errors.
 */
void ip_ct_proto_gre_fini(void)
{
	struct list_head *pos, *n;

	/* delete all keymap entries */
	write_lock_bh(&ip_ct_gre_lock);
	list_for_each_safe(pos, n, &gre_keymap_list) {
		DEBUGP("deleting keymap %p at module unload time\n", pos);
		list_del(pos);
		kfree(pos);
	}
	write_unlock_bh(&ip_ct_gre_lock);

	ip_conntrack_protocol_unregister(&gre); 
}

EXPORT_SYMBOL(ip_ct_gre_keymap_add);
EXPORT_SYMBOL(ip_ct_gre_keymap_destroy);
