All of lore.kernel.org
 help / color / mirror / Atom feed
From: Philip Craig <philipc@snapgear.com>
To: Netfilter Developer Mailing List <netfilter-devel@lists.netfilter.org>
Subject: [PATCH 1/3] libnl: add netfilter support
Date: Mon, 03 Sep 2007 15:11:18 +1000	[thread overview]
Message-ID: <46DB9776.8020209@snapgear.com> (raw)
In-Reply-To: <46DB9716.1020400@snapgear.com>

[-- Attachment #1: Type: text/plain, Size: 1 bytes --]



[-- Attachment #2: nfnl.patch --]
[-- Type: text/x-diff, Size: 13989 bytes --]

---
 include/linux/netfilter/nfnetlink.h |  106 +++++++++++++++
 include/netlink/netfilter/nfnl.h    |   44 ++++++
 include/netlink/netlink.h           |    1 
 lib/Makefile                        |    2 
 lib/attr.c                          |    3 
 lib/netfilter/nfnl.c                |  246 ++++++++++++++++++++++++++++++++++++
 6 files changed, 401 insertions(+), 1 deletion(-)

Index: libnl/lib/Makefile
===================================================================
--- libnl.orig/lib/Makefile	2007-09-03 14:24:29.000000000 +1000
+++ libnl/lib/Makefile	2007-09-03 14:24:45.000000000 +1000
@@ -25,6 +25,8 @@ CIN      += $(wildcard route/cls/*.c)
 CIN      += $(wildcard genl/*.c)
 # fib lookup
 CIN      += $(wildcard fib_lookup/*.c)
+# Netfilter
+CIN      += $(wildcard netfilter/*.c)
 
 DEPS     := $(CIN:%.c=%.d)
 OBJ      := $(CIN:%.c=%.o)
Index: libnl/lib/attr.c
===================================================================
--- libnl.orig/lib/attr.c	2007-09-03 14:24:29.000000000 +1000
+++ libnl/lib/attr.c	2007-09-03 14:24:45.000000000 +1000
@@ -261,7 +261,8 @@ int nla_parse(struct nlattr *tb[], int m
 	memset(tb, 0, sizeof(struct nlattr *) * (maxtype + 1));
 
 	nla_for_each_attr(nla, head, len, rem) {
-		uint16_t type = nla->nla_type;
+		/* Ignore NFNL_NFA_NEST bit, hope nothing else uses it */
+		uint16_t type = nla->nla_type & 0x7fff;
 
 		if (type == 0) {
 			fprintf(stderr, "Illegal nla->nla_type == 0\n");
Index: libnl/include/netlink/netfilter/nfnl.h
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ libnl/include/netlink/netfilter/nfnl.h	2007-09-03 14:24:45.000000000 +1000
@@ -0,0 +1,44 @@
+/*
+ * netlink/nfnl/nfnl.h		Netfilter Netlink
+ *
+ *	This library is free software; you can redistribute it and/or
+ *	modify it under the terms of the GNU Lesser General Public
+ *	License as published by the Free Software Foundation version 2.1
+ *	of the License.
+ *
+ * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch>
+ * Copyright (c) 2007 Philip Craig <philipc@snapgear.com>
+ * Copyright (c) 2007 Secure Computing Corporation
+ */
+
+#ifndef NETLINK_NFNL_H_
+#define NETLINK_NFNL_H_
+
+#include <netlink/netlink.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define NFNL_HDRLEN NLMSG_ALIGN(sizeof(struct nfgenmsg))
+#define NFNLMSG_TYPE(subsys, subtype) (((subsys) << 8) | (subtype))
+
+extern int		nfnl_connect(struct nl_handle *);
+
+extern uint8_t		nfnlmsg_subsys(struct nlmsghdr *);
+extern uint8_t		nfnlmsg_subtype(struct nlmsghdr *);
+extern uint8_t		nfnlmsg_family(struct nlmsghdr *);
+extern uint16_t		nfnlmsg_res_id(struct nlmsghdr *);
+
+extern int		nfnl_send_simple(struct nl_handle *, uint8_t, uint8_t,
+					 int, uint8_t, uint16_t);
+extern struct nl_msg *	nfnlmsg_alloc_simple(uint8_t, uint8_t, int,
+					     uint8_t, uint16_t);
+extern int		nfnlmsg_put(struct nl_msg *, uint32_t, uint32_t,
+				    uint8_t, uint8_t, int, uint8_t, uint16_t);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
Index: libnl/lib/netfilter/nfnl.c
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ libnl/lib/netfilter/nfnl.c	2007-09-03 14:24:45.000000000 +1000
@@ -0,0 +1,246 @@
+/*
+ * lib/netfilter/nfnl.c		Netfilter Netlink
+ *
+ *	This library is free software; you can redistribute it and/or
+ *	modify it under the terms of the GNU Lesser General Public
+ *	License as published by the Free Software Foundation version 2.1
+ *	of the License.
+ *
+ * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch>
+ * Copyright (c) 2007 Philip Craig <philipc@snapgear.com>
+ * Copyright (c) 2007 Secure Computing Corporation
+ */
+
+/**
+ * @ingroup nlfam
+ * @defgroup nfnl Netfilter Netlink
+ *
+ * @par Message Format
+ * @code
+ *  <------- NLMSG_ALIGN(hlen) ------> <---- NLMSG_ALIGN(len) --->
+ * +----------------------------+- - -+- - - - - - - - - - -+- - -+
+ * |           Header           | Pad |       Payload       | Pad |
+ * |      struct nlmsghdr       |     |                     |     |
+ * +----------------------------+- - -+- - - - - - - - - - -+- - -+
+ * @endcode
+ * @code
+ *  <-------- NFNL_HDRLEN --------->
+ * +--------------------------+- - -+------------+
+ * | Netfilter Netlink Header | Pad | Attributes |
+ * |    struct nfgenmsg       |     |            |
+ * +--------------------------+- - -+------------+
+ * nfnlmsg_attrdata(nfg, hdrlen)-----^
+ * @endcode
+ *
+ * @par 1) Creating a new netfilter netlink message
+ * @code
+ * struct nl_msg *msg;
+ *
+ * // Create a new empty netlink message
+ * msg = nlmsg_alloc();
+ *
+ * // Append the netlink and netfilter netlink message header
+ * hdr = nfnlmsg_put(msg, PID, SEQ, SUBSYS, TYPE, NLM_F_ECHO,
+ *                   FAMILY, RES_ID);
+ *
+ * // Append the attributes.
+ * nla_put_u32(msg, 1, 0x10);
+ *
+ * // Message is ready to be sent.
+ * nl_send_auto_complete(nl_handle, msg);
+ *
+ * // All done? Free the message.
+ * nlmsg_free(msg);
+ * @endcode
+ *
+ * @par 2) Sending of trivial messages
+ * @code
+ * // For trivial messages not requiring any subsys specific header or
+ * // attributes, nfnl_send_simple() may be used to send messages directly.
+ * nfnl_send_simple(nl_handle, SUBSYS, TYPE, 0, FAMILY, RES_ID);
+ * @endcode
+ * @{
+ */
+
+#include <netlink-local.h>
+#include <netlink/netlink.h>
+#include <netlink/netfilter/nfnl.h>
+
+/**
+ * @name Socket Creating
+ * @{
+ */
+
+/**
+ * Create and connect netfilter netlink socket.
+ * @arg handle		Netlink handle.
+ *
+ * Creates a NETLINK_NETFILTER netlink socket, binds the socket and
+ * issues a connection attempt.
+ *
+ * @see nl_connect()
+ *
+ * @return 0 on success or a negative error code.
+ */
+int nfnl_connect(struct nl_handle *handle)
+{
+	return nl_connect(handle, NETLINK_NETFILTER);
+}
+
+/** @} */
+
+/**
+ * @name Sending
+ * @{
+ */
+
+/**
+ * Send trivial netfilter netlink message
+ * @arg handle		Netlink handle.
+ * @arg subsys_id	nfnetlink subsystem
+ * @arg type		nfnetlink message type
+ * @arg flags		message flags
+ * @arg family		nfnetlink address family
+ * @arg res_id		nfnetlink resource id
+ *
+ * @return Newly allocated netlink message or NULL.
+ */
+int nfnl_send_simple(struct nl_handle *handle, uint8_t subsys_id, uint8_t type,
+		     int flags, uint8_t family, uint16_t res_id)
+{
+	struct nfgenmsg hdr = {
+		.nfgen_family = family,
+		.version = NFNETLINK_V0,
+		.res_id = htons(res_id),
+	};
+
+	return nl_send_simple(handle, NFNLMSG_TYPE(subsys_id, type), flags,
+			      &hdr, sizeof(hdr));
+}
+
+/** @} */
+
+/**
+ * @name Message Parsing
+ * @{
+ */
+
+/**
+ * Get netfilter subsystem id from message
+ * @arg nlh	netlink messsage header
+ */
+uint8_t nfnlmsg_subsys(struct nlmsghdr *nlh)
+{
+	return NFNL_SUBSYS_ID(nlh->nlmsg_type);
+}
+
+/**
+ * Get netfilter message type from message
+ * @arg nlh	netlink messsage header
+ */
+uint8_t nfnlmsg_subtype(struct nlmsghdr *nlh)
+{
+	return NFNL_MSG_TYPE(nlh->nlmsg_type);
+}
+
+/**
+ * Get netfilter family from message
+ * @arg nlh	netlink messsage header
+ */
+uint8_t nfnlmsg_family(struct nlmsghdr *nlh)
+{
+	struct nfgenmsg *nfg = nlmsg_data(nlh);
+
+	return nfg->nfgen_family;
+}
+
+/**
+ * Get netfilter resource id from message
+ * @arg nlh	netlink messsage header
+ */
+uint16_t nfnlmsg_res_id(struct nlmsghdr *nlh)
+{
+	struct nfgenmsg *nfg = nlmsg_data(nlh);
+
+	return ntohs(nfg->res_id);
+}
+
+/** @} */
+
+/**
+ * @name Message Building
+ * @{
+ */
+
+static int nfnlmsg_append(struct nl_msg *msg, uint8_t family, uint16_t res_id)
+{
+	struct nfgenmsg *nfg;
+
+	nfg = nlmsg_reserve(msg, sizeof(*nfg), NLMSG_ALIGNTO);
+	if (nfg == NULL)
+		return nl_errno(ENOMEM);
+
+	nfg->nfgen_family = family;
+	nfg->version = NFNETLINK_V0;
+	nfg->res_id = htons(res_id);
+	NL_DBG(2, "msg %p: Added nfnetlink header family=%d res_id=%d\n",
+	       msg, family, res_id);
+	return 0;
+}
+
+/**
+ * Allocate a new netfilter netlink message
+ * @arg subsys_id	nfnetlink subsystem
+ * @arg type		nfnetlink message type
+ * @arg flags		message flags
+ * @arg family		nfnetlink address family
+ * @arg res_id		nfnetlink resource id
+ *
+ * @return Newly allocated netlink message or NULL.
+ */
+struct nl_msg *nfnlmsg_alloc_simple(uint8_t subsys_id, uint8_t type, int flags,
+				    uint8_t family, uint16_t res_id)
+{
+	struct nl_msg *msg;
+
+	msg = nlmsg_alloc_simple(NFNLMSG_TYPE(subsys_id, type), flags);
+	if (msg == NULL)
+		return NULL;
+
+	if (nfnlmsg_append(msg, family, res_id) < 0)
+		goto nla_put_failure;
+
+	return msg;
+
+nla_put_failure:
+	nlmsg_free(msg);
+	return NULL;
+}
+
+/**
+ * Add netlink and netfilter netlink headers to netlink message
+ * @arg msg		netlink message
+ * @arg pid		netlink process id
+ * @arg seq		sequence number of message
+ * @arg subsys_id	nfnetlink subsystem
+ * @arg type		nfnetlink message type
+ * @arg flags		message flags
+ * @arg family		nfnetlink address family
+ * @arg res_id		nfnetlink resource id
+ */
+int nfnlmsg_put(struct nl_msg *msg, uint32_t pid, uint32_t seq,
+		uint8_t subsys_id, uint8_t type, int flags, uint8_t family,
+		uint16_t res_id)
+{
+	struct nlmsghdr *nlh;
+
+	nlh = nlmsg_put(msg, pid, seq, NFNLMSG_TYPE(subsys_id, type), 0, flags);
+	if (nlh == NULL)
+		return nl_get_errno();
+
+	return nfnlmsg_append(msg, family, res_id);
+}
+
+/** @} */
+
+/** @} */
Index: libnl/include/netlink/netlink.h
===================================================================
--- libnl.orig/include/netlink/netlink.h	2007-09-03 14:24:29.000000000 +1000
+++ libnl/include/netlink/netlink.h	2007-09-03 14:24:45.000000000 +1000
@@ -25,6 +25,7 @@
 #include <linux/rtnetlink.h>
 #include <linux/genetlink.h>
 #include <linux/ip_mp_alg.h>
+#include <linux/netfilter/nfnetlink.h>
 #include <netlink/types.h>
 #include <netlink/handlers.h>
 #include <netlink/socket.h>
Index: libnl/include/linux/netfilter/nfnetlink.h
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ libnl/include/linux/netfilter/nfnetlink.h	2007-09-03 14:24:45.000000000 +1000
@@ -0,0 +1,106 @@
+#ifndef _NFNETLINK_H
+#define _NFNETLINK_H
+#include <linux/types.h>
+
+#ifndef __KERNEL__
+/* nfnetlink groups: Up to 32 maximum - backwards compatibility for userspace */
+#define NF_NETLINK_CONNTRACK_NEW 		0x00000001
+#define NF_NETLINK_CONNTRACK_UPDATE		0x00000002
+#define NF_NETLINK_CONNTRACK_DESTROY		0x00000004
+#define NF_NETLINK_CONNTRACK_EXP_NEW		0x00000008
+#define NF_NETLINK_CONNTRACK_EXP_UPDATE		0x00000010
+#define NF_NETLINK_CONNTRACK_EXP_DESTROY	0x00000020
+#endif
+
+enum nfnetlink_groups {
+	NFNLGRP_NONE,
+#define NFNLGRP_NONE			NFNLGRP_NONE
+	NFNLGRP_CONNTRACK_NEW,
+#define NFNLGRP_CONNTRACK_NEW		NFNLGRP_CONNTRACK_NEW
+	NFNLGRP_CONNTRACK_UPDATE,
+#define NFNLGRP_CONNTRACK_UPDATE	NFNLGRP_CONNTRACK_UPDATE
+	NFNLGRP_CONNTRACK_DESTROY,
+#define NFNLGRP_CONNTRACK_DESTROY	NFNLGRP_CONNTRACK_DESTROY
+	NFNLGRP_CONNTRACK_EXP_NEW,
+#define	NFNLGRP_CONNTRACK_EXP_NEW	NFNLGRP_CONNTRACK_EXP_NEW
+	NFNLGRP_CONNTRACK_EXP_UPDATE,
+#define NFNLGRP_CONNTRACK_EXP_UPDATE	NFNLGRP_CONNTRACK_EXP_UPDATE
+	NFNLGRP_CONNTRACK_EXP_DESTROY,
+#define NFNLGRP_CONNTRACK_EXP_DESTROY	NFNLGRP_CONNTRACK_EXP_DESTROY
+	__NFNLGRP_MAX,
+};
+#define NFNLGRP_MAX	(__NFNLGRP_MAX - 1)
+
+/* Generic structure for encapsulation optional netfilter information.
+ * It is reminiscent of sockaddr, but with sa_family replaced
+ * with attribute type. 
+ * ! This should someday be put somewhere generic as now rtnetlink and
+ * ! nfnetlink use the same attributes methods. - J. Schulist.
+ */
+
+struct nfattr
+{
+	u_int16_t nfa_len;
+	u_int16_t nfa_type;	/* we use 15 bits for the type, and the highest
+				 * bit to indicate whether the payload is nested */
+};
+
+/* FIXME: Apart from NFNL_NFA_NESTED shamelessly copy and pasted from
+ * rtnetlink.h, it's time to put this in a generic file */
+
+#define NFNL_NFA_NEST	0x8000
+#define NFA_TYPE(attr) 	((attr)->nfa_type & 0x7fff)
+
+#define NFA_ALIGNTO     4
+#define NFA_ALIGN(len)	(((len) + NFA_ALIGNTO - 1) & ~(NFA_ALIGNTO - 1))
+#define NFA_OK(nfa,len)	((len) > 0 && (nfa)->nfa_len >= sizeof(struct nfattr) \
+	&& (nfa)->nfa_len <= (len))
+#define NFA_NEXT(nfa,attrlen)	((attrlen) -= NFA_ALIGN((nfa)->nfa_len), \
+	(struct nfattr *)(((char *)(nfa)) + NFA_ALIGN((nfa)->nfa_len)))
+#define NFA_LENGTH(len)	(NFA_ALIGN(sizeof(struct nfattr)) + (len))
+#define NFA_SPACE(len)	NFA_ALIGN(NFA_LENGTH(len))
+#define NFA_DATA(nfa)   ((void *)(((char *)(nfa)) + NFA_LENGTH(0)))
+#define NFA_PAYLOAD(nfa) ((int)((nfa)->nfa_len) - NFA_LENGTH(0))
+#define NFA_NEST(skb, type) \
+({	struct nfattr *__start = (struct nfattr *)skb_tail_pointer(skb); \
+	NFA_PUT(skb, (NFNL_NFA_NEST | type), 0, NULL); \
+	__start;  })
+#define NFA_NEST_END(skb, start) \
+({      (start)->nfa_len = skb_tail_pointer(skb) - (unsigned char *)(start); \
+        (skb)->len; })
+#define NFA_NEST_CANCEL(skb, start) \
+({      if (start) \
+                skb_trim(skb, (unsigned char *) (start) - (skb)->data); \
+        -1; })
+
+/* General form of address family dependent message.
+ */
+struct nfgenmsg {
+	u_int8_t  nfgen_family;		/* AF_xxx */
+	u_int8_t  version;		/* nfnetlink version */
+	__be16    res_id;		/* resource id */
+};
+
+#define NFNETLINK_V0	0
+
+#define NFM_NFA(n)      ((struct nfattr *)(((char *)(n)) \
+        + NLMSG_ALIGN(sizeof(struct nfgenmsg))))
+#define NFM_PAYLOAD(n)  NLMSG_PAYLOAD(n, sizeof(struct nfgenmsg))
+
+/* netfilter netlink message types are split in two pieces:
+ * 8 bit subsystem, 8bit operation.
+ */
+
+#define NFNL_SUBSYS_ID(x)	((x & 0xff00) >> 8)
+#define NFNL_MSG_TYPE(x)	(x & 0x00ff)
+
+/* No enum here, otherwise __stringify() trick of MODULE_ALIAS_NFNL_SUBSYS()
+ * won't work anymore */
+#define NFNL_SUBSYS_NONE 		0
+#define NFNL_SUBSYS_CTNETLINK		1
+#define NFNL_SUBSYS_CTNETLINK_EXP	2
+#define NFNL_SUBSYS_QUEUE		3
+#define NFNL_SUBSYS_ULOG		4
+#define NFNL_SUBSYS_COUNT		5
+
+#endif	/* _NFNETLINK_H */

  reply	other threads:[~2007-09-03  5:11 UTC|newest]

Thread overview: 22+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2007-09-03  5:09 netfilter support in libnl Philip Craig
2007-09-03  5:11 ` Philip Craig [this message]
2007-09-03  9:50   ` [PATCH 1/3] libnl: add netfilter support Patrick McHardy
2007-09-03 10:01     ` Thomas Graf
2007-09-03 10:06       ` Patrick McHardy
2007-09-03 10:15         ` Thomas Graf
2007-09-03 10:53           ` Patrick McHardy
2007-09-03 11:03             ` Thomas Graf
2007-09-03 11:13               ` Patrick McHardy
2007-09-04  1:18     ` Philip Craig
2007-09-03 10:09   ` Thomas Graf
2007-09-04  2:12     ` Philip Craig
2007-09-04  9:39       ` Thomas Graf
2007-09-04 11:36   ` Thomas Graf
2007-09-03  5:11 ` [PATCH 2/3] libnl: add netfilter conntrack support Philip Craig
2007-09-04 16:45   ` Thomas Graf
2007-09-03  5:12 ` [PATCH 3/3] libnl: add netfilter log support Philip Craig
2007-09-04 16:48   ` Thomas Graf
2007-09-03  9:30 ` netfilter support in libnl Patrick McHardy
2007-09-03  9:59   ` Thomas Graf
2007-09-03 10:05     ` Patrick McHardy
2007-09-03 10:16       ` Thomas Graf

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=46DB9776.8020209@snapgear.com \
    --to=philipc@snapgear.com \
    --cc=netfilter-devel@lists.netfilter.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.