// SPDX-License-Identifier: GPL-2.0-only
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
#include <linux/module.h>
#include <linux/kernel.h>

#include <linux/capability.h>
#include <linux/if.h>
#include <linux/inetdevice.h>
#include <linux/ip.h>
#include <linux/list.h>
#include <linux/rculist.h>
#include <linux/skbuff.h>
#include <linux/slab.h>
#include <linux/tcp.h>

#include <net/ip.h>
#include <net/tcp.h>

#include <linux/netfilter/nfnetlink.h>
#include <linux/netfilter/x_tables.h>
#include <net/netfilter/nf_log.h>
#include <linux/netfilter/nfnetlink_osf.h>

/*
 * Indexed by dont-fragment bit.
 * It is the only constant value in the fingerprint.
 */
struct list_head nf_osf_fingers[2];
EXPORT_SYMBOL_GPL(nf_osf_fingers);

static inline int nf_osf_ttl(const struct sk_buff *skb,
			     int ttl_check, unsigned char f_ttl)
{
	struct in_device *in_dev = __in_dev_get_rcu(skb->dev);
	const struct iphdr *ip = ip_hdr(skb);
	const struct in_ifaddr *ifa;
	int ret = 0;

	if (ttl_check == NF_OSF_TTL_TRUE)
		return ip->ttl == f_ttl;
	if (ttl_check == NF_OSF_TTL_NOCHECK)
		return 1;
	else if (ip->ttl <= f_ttl)
		return 1;

	in_dev_for_each_ifa_rcu(ifa, in_dev) {
		if (inet_ifa_match(ip->saddr, ifa)) {
			ret = (ip->ttl == f_ttl);
			break;
		}
	}

	return ret;
}

struct nf_osf_hdr_ctx {
	bool			df;
	u16			window;
	u16			totlen;
	const unsigned char	*optp;
	unsigned int		optsize;
};

static bool nf_osf_match_one(const struct sk_buff *skb,
			     const struct nf_osf_user_finger *f,
			     int ttl_check,
			     struct nf_osf_hdr_ctx *ctx)
{
	const __u8 *optpinit = ctx->optp;
	unsigned int check_WSS = 0;
	int fmatch = FMATCH_WRONG;
	int foptsize, optnum;
	u16 mss = 0;

	if (ctx->totlen != f->ss || !nf_osf_ttl(skb, ttl_check, f->ttl))
		return false;

	/*
	 * Should not happen if userspace parser was written correctly.
	 */
	if (f->wss.wc >= OSF_WSS_MAX)
		return false;

	/* Check options */

	foptsize = 0;
	for (optnum = 0; optnum < f->opt_num; ++optnum)
		foptsize += f->opt[optnum].length;

	if (foptsize > MAX_IPOPTLEN ||
	    ctx->optsize > MAX_IPOPTLEN ||
	    ctx->optsize != foptsize)
		return false;

	check_WSS = f->wss.wc;

	for (optnum = 0; optnum < f->opt_num; ++optnum) {
		if (f->opt[optnum].kind == *ctx->optp) {
			__u32 len = f->opt[optnum].length;
			const __u8 *optend = ctx->optp + len;

			fmatch = FMATCH_OK;

			switch (*ctx->optp) {
			case OSFOPT_MSS:
				mss = ctx->optp[3];
				mss <<= 8;
				mss |= ctx->optp[2];

				mss = ntohs((__force __be16)mss);
				break;
			case OSFOPT_TS:
				break;
			}

			ctx->optp = optend;
		} else
			fmatch = FMATCH_OPT_WRONG;

		if (fmatch != FMATCH_OK)
			break;
	}

	if (fmatch != FMATCH_OPT_WRONG) {
		fmatch = FMATCH_WRONG;

		switch (check_WSS) {
		case OSF_WSS_PLAIN:
			if (f->wss.val == 0 || ctx->window == f->wss.val)
				fmatch = FMATCH_OK;
			break;
		case OSF_WSS_MSS:
			/*
			 * Some smart modems decrease mangle MSS to
			 * SMART_MSS_2, so we check standard, decreased
			 * and the one provided in the fingerprint MSS
			 * values.
			 */
#define SMART_MSS_1	1460
#define SMART_MSS_2	1448
			if (ctx->window == f->wss.val * mss ||
			    ctx->window == f->wss.val * SMART_MSS_1 ||
			    ctx->window == f->wss.val * SMART_MSS_2)
				fmatch = FMATCH_OK;
			break;
		case OSF_WSS_MTU:
			if (ctx->window == f->wss.val * (mss + 40) ||
			    ctx->window == f->wss.val * (SMART_MSS_1 + 40) ||
			    ctx->window == f->wss.val * (SMART_MSS_2 + 40))
				fmatch = FMATCH_OK;
			break;
		case OSF_WSS_MODULO:
			if ((ctx->window % f->wss.val) == 0)
				fmatch = FMATCH_OK;
			break;
		}
	}

	if (fmatch != FMATCH_OK)
		ctx->optp = optpinit;

	return fmatch == FMATCH_OK;
}

static const struct tcphdr *nf_osf_hdr_ctx_init(struct nf_osf_hdr_ctx *ctx,
						const struct sk_buff *skb,
						const struct iphdr *ip,
						unsigned char *opts,
						struct tcphdr *_tcph)
{
	const struct tcphdr *tcp;

	tcp = skb_header_pointer(skb, ip_hdrlen(skb), sizeof(struct tcphdr), _tcph);
	if (!tcp)
		return NULL;

	if (!tcp->syn)
		return NULL;

	ctx->totlen = ntohs(ip->tot_len);
	ctx->df = ntohs(ip->frag_off) & IP_DF;
	ctx->window = ntohs(tcp->window);

	if (tcp->doff * 4 > sizeof(struct tcphdr)) {
		ctx->optsize = tcp->doff * 4 - sizeof(struct tcphdr);

		ctx->optp = skb_header_pointer(skb, ip_hdrlen(skb) +
				sizeof(struct tcphdr), ctx->optsize, opts);
		if (!ctx->optp)
			return NULL;
	}

	return tcp;
}

bool
nf_osf_match(const struct sk_buff *skb, u_int8_t family,
	     int hooknum, struct net_device *in, struct net_device *out,
	     const struct nf_osf_info *info, struct net *net,
	     const struct list_head *nf_osf_fingers)
{
	const struct iphdr *ip = ip_hdr(skb);
	const struct nf_osf_user_finger *f;
	unsigned char opts[MAX_IPOPTLEN];
	const struct nf_osf_finger *kf;
	int fcount = 0, ttl_check;
	int fmatch = FMATCH_WRONG;
	struct nf_osf_hdr_ctx ctx;
	const struct tcphdr *tcp;
	struct tcphdr _tcph;

	memset(&ctx, 0, sizeof(ctx));

	tcp = nf_osf_hdr_ctx_init(&ctx, skb, ip, opts, &_tcph);
	if (!tcp)
		return false;

	ttl_check = (info->flags & NF_OSF_TTL) ? info->ttl : 0;

	list_for_each_entry_rcu(kf, &nf_osf_fingers[ctx.df], finger_entry) {

		f = &kf->finger;

		if (!(info->flags & NF_OSF_LOG) && strcmp(info->genre, f->genre))
			continue;

		if (!nf_osf_match_one(skb, f, ttl_check, &ctx))
			continue;

		fmatch = FMATCH_OK;

		fcount++;

		if (info->flags & NF_OSF_LOG)
			nf_log_packet(net, family, hooknum, skb,
				      in, out, NULL,
				      "%s [%s:%s] : %pI4:%d -> %pI4:%d hops=%d\n",
				      f->genre, f->version, f->subtype,
				      &ip->saddr, ntohs(tcp->source),
				      &ip->daddr, ntohs(tcp->dest),
				      f->ttl - ip->ttl);

		if ((info->flags & NF_OSF_LOG) &&
		    info->loglevel == NF_OSF_LOGLEVEL_FIRST)
			break;
	}

	if (!fcount && (info->flags & NF_OSF_LOG))
		nf_log_packet(net, family, hooknum, skb, in, out, NULL,
			      "Remote OS is not known: %pI4:%u -> %pI4:%u\n",
			      &ip->saddr, ntohs(tcp->source),
			      &ip->daddr, ntohs(tcp->dest));

	if (fcount)
		fmatch = FMATCH_OK;

	return fmatch == FMATCH_OK;
}
EXPORT_SYMBOL_GPL(nf_osf_match);

bool nf_osf_find(const struct sk_buff *skb,
		 const struct list_head *nf_osf_fingers,
		 const int ttl_check, struct nf_osf_data *data)
{
	const struct iphdr *ip = ip_hdr(skb);
	const struct nf_osf_user_finger *f;
	unsigned char opts[MAX_IPOPTLEN];
	const struct nf_osf_finger *kf;
	struct nf_osf_hdr_ctx ctx;
	const struct tcphdr *tcp;
	struct tcphdr _tcph;
	bool found = false;

	memset(&ctx, 0, sizeof(ctx));

	tcp = nf_osf_hdr_ctx_init(&ctx, skb, ip, opts, &_tcph);
	if (!tcp)
		return false;

	list_for_each_entry_rcu(kf, &nf_osf_fingers[ctx.df], finger_entry) {
		f = &kf->finger;
		if (!nf_osf_match_one(skb, f, ttl_check, &ctx))
			continue;

		data->genre = f->genre;
		data->version = f->version;
		found = true;
		break;
	}

	return found;
}
EXPORT_SYMBOL_GPL(nf_osf_find);

static const struct nla_policy nfnl_osf_policy[OSF_ATTR_MAX + 1] = {
	[OSF_ATTR_FINGER]	= { .len = sizeof(struct nf_osf_user_finger) },
};

static int nfnl_osf_add_callback(struct net *net, struct sock *ctnl,
				 struct sk_buff *skb, const struct nlmsghdr *nlh,
				 const struct nlattr * const osf_attrs[],
				 struct netlink_ext_ack *extack)
{
	struct nf_osf_user_finger *f;
	struct nf_osf_finger *kf = NULL, *sf;
	int err = 0;

	if (!capable(CAP_NET_ADMIN))
		return -EPERM;

	if (!osf_attrs[OSF_ATTR_FINGER])
		return -EINVAL;

	if (!(nlh->nlmsg_flags & NLM_F_CREATE))
		return -EINVAL;

	f = nla_data(osf_attrs[OSF_ATTR_FINGER]);

	if (f->opt_num > ARRAY_SIZE(f->opt))
		return -EINVAL;

	if (!memchr(f->genre, 0, MAXGENRELEN) ||
	    !memchr(f->subtype, 0, MAXGENRELEN) ||
	    !memchr(f->version, 0, MAXGENRELEN))
		return -EINVAL;

	kf = kmalloc(sizeof(struct nf_osf_finger), GFP_KERNEL);
	if (!kf)
		return -ENOMEM;

	memcpy(&kf->finger, f, sizeof(struct nf_osf_user_finger));

	list_for_each_entry(sf, &nf_osf_fingers[!!f->df], finger_entry) {
		if (memcmp(&sf->finger, f, sizeof(struct nf_osf_user_finger)))
			continue;

		kfree(kf);
		kf = NULL;

		if (nlh->nlmsg_flags & NLM_F_EXCL)
			err = -EEXIST;
		break;
	}

	/*
	 * We are protected by nfnl mutex.
	 */
	if (kf)
		list_add_tail_rcu(&kf->finger_entry, &nf_osf_fingers[!!f->df]);

	return err;
}

static int nfnl_osf_remove_callback(struct net *net, struct sock *ctnl,
				    struct sk_buff *skb,
				    const struct nlmsghdr *nlh,
				    const struct nlattr * const osf_attrs[],
				    struct netlink_ext_ack *extack)
{
	struct nf_osf_user_finger *f;
	struct nf_osf_finger *sf;
	int err = -ENOENT;

	if (!capable(CAP_NET_ADMIN))
		return -EPERM;

	if (!osf_attrs[OSF_ATTR_FINGER])
		return -EINVAL;

	f = nla_data(osf_attrs[OSF_ATTR_FINGER]);

	list_for_each_entry(sf, &nf_osf_fingers[!!f->df], finger_entry) {
		if (memcmp(&sf->finger, f, sizeof(struct nf_osf_user_finger)))
			continue;

		/*
		 * We are protected by nfnl mutex.
		 */
		list_del_rcu(&sf->finger_entry);
		kfree_rcu(sf, rcu_head);

		err = 0;
		break;
	}

	return err;
}

static const struct nfnl_callback nfnl_osf_callbacks[OSF_MSG_MAX] = {
	[OSF_MSG_ADD]	= {
		.call		= nfnl_osf_add_callback,
		.attr_count	= OSF_ATTR_MAX,
		.policy		= nfnl_osf_policy,
	},
	[OSF_MSG_REMOVE]	= {
		.call		= nfnl_osf_remove_callback,
		.attr_count	= OSF_ATTR_MAX,
		.policy		= nfnl_osf_policy,
	},
};

static const struct nfnetlink_subsystem nfnl_osf_subsys = {
	.name			= "osf",
	.subsys_id		= NFNL_SUBSYS_OSF,
	.cb_count		= OSF_MSG_MAX,
	.cb			= nfnl_osf_callbacks,
};

static int __init nfnl_osf_init(void)
{
	int err = -EINVAL;
	int i;

	for (i = 0; i < ARRAY_SIZE(nf_osf_fingers); ++i)
		INIT_LIST_HEAD(&nf_osf_fingers[i]);

	err = nfnetlink_subsys_register(&nfnl_osf_subsys);
	if (err < 0) {
		pr_err("Failed to register OSF nsfnetlink helper (%d)\n", err);
		goto err_out_exit;
	}
	return 0;

err_out_exit:
	return err;
}

static void __exit nfnl_osf_fini(void)
{
	struct nf_osf_finger *f;
	int i;

	nfnetlink_subsys_unregister(&nfnl_osf_subsys);

	rcu_read_lock();
	for (i = 0; i < ARRAY_SIZE(nf_osf_fingers); ++i) {
		list_for_each_entry_rcu(f, &nf_osf_fingers[i], finger_entry) {
			list_del_rcu(&f->finger_entry);
			kfree_rcu(f, rcu_head);
		}
	}
	rcu_read_unlock();

	rcu_barrier();
}

module_init(nfnl_osf_init);
module_exit(nfnl_osf_fini);

MODULE_LICENSE("GPL");
MODULE_ALIAS_NFNL_SUBSYS(NFNL_SUBSYS_OSF);
