* [netfilter socket hooks 1/5]: Add socket hook infrastructure
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
@ 2005-05-10 16:00 ` Patrick McHardy
2005-05-11 23:22 ` James Morris
2005-05-10 16:00 ` [netfilter socket hooks 2/5]: Add protocol hooks Patrick McHardy
` (7 subsequent siblings)
8 siblings, 1 reply; 30+ messages in thread
From: Patrick McHardy @ 2005-05-10 16:00 UTC (permalink / raw)
To: netfilter-devel; +Cc: juha.heljoranta, Rusty Russell
[-- Attachment #1: 01.diff --]
[-- Type: text/x-patch, Size: 7679 bytes --]
[NETFILTER]: Add socket hook infrastructure
Signed-off-by: Patrick McHardy <kaber@trash.net>
---
commit 4ca9ffc0b58dd44e91cbaaa2de3c27faa220e047
tree e97143c76936d02bb1817a1e109e36707202a6bb
parent e8108c98dd6d65613fa0ec9d2300f89c48d554bf
author Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 16:47:43 +0200
committer Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 16:47:43 +0200
include/linux/netfilter.h | 44 +++++++++++++++++++++
net/core/netfilter.c | 96 +++++++++++++++++++++++++++++++++++++++++++++-
2 files changed, 139 insertions(+), 1 deletion(-)
Index: include/linux/netfilter.h
===================================================================
--- 3608de2fc88b062070a9d197eda9cac1fb9635d3/include/linux/netfilter.h (mode:100644)
+++ e97143c76936d02bb1817a1e109e36707202a6bb/include/linux/netfilter.h (mode:100644)
@@ -57,6 +57,25 @@
int priority;
};
+typedef unsigned int nf_sk_hookfn(unsigned int hooknum,
+ struct sock *sk, struct sk_buff **skb,
+ const struct net_device *in,
+ const struct net_device *out,
+ int (*okfn)(struct sock *sk, struct sk_buff *));
+
+struct nf_sk_hook_ops
+{
+ struct list_head list;
+
+ /* User fills in from here down. */
+ nf_sk_hookfn *hook;
+ struct module *owner;
+ unsigned int pf;
+ unsigned int hooknum;
+ /* Hooks are ordered in ascending priority. */
+ int priority;
+};
+
struct nf_sockopt_ops
{
struct list_head list;
@@ -94,12 +113,16 @@
int nf_register_hook(struct nf_hook_ops *reg);
void nf_unregister_hook(struct nf_hook_ops *reg);
+int nf_register_sk_hook(struct nf_sk_hook_ops *reg);
+void nf_unregister_sk_hook(struct nf_sk_hook_ops *reg);
+
/* Functions to register get/setsockopt ranges (non-inclusive). You
need to check permissions yourself! */
int nf_register_sockopt(struct nf_sockopt_ops *reg);
void nf_unregister_sockopt(struct nf_sockopt_ops *reg);
extern struct list_head nf_hooks[NPROTO][NF_MAX_HOOKS];
+extern struct list_head nf_sk_hooks[NPROTO][NF_MAX_HOOKS];
typedef void nf_logfn(unsigned int hooknum,
const struct sk_buff *skb,
@@ -149,6 +172,13 @@
if ((__ret=nf_hook_slow(pf, hook, &(skb), indev, outdev, okfn, thresh)) == 1) \
__ret = (okfn)(skb); \
__ret;})
+#define NF_SK_HOOK(pf, hook, sk, skb, indev, outdev, okfn, skputfn) \
+({int __ret; \
+if ((__ret=nf_sk_hook_slow(pf, hook, sk, &(skb), indev, outdev, okfn)) == 0) \
+ __ret = (okfn)(sk, skb); \
+else if (sk && skputfn) \
+ ((void (*)(struct sock *))skputfn)(sk); \
+__ret;})
#else
#define NF_HOOK(pf, hook, skb, indev, outdev, okfn) \
({int __ret; \
@@ -162,12 +192,25 @@
(__ret=nf_hook_slow(pf, hook, &(skb), indev, outdev, okfn, thresh)) == 1) \
__ret = (okfn)(skb); \
__ret;})
+#define NF_SK_HOOK(pf, hook, sk, skb, indev, outdev, okfn, skputfn) \
+({int __ret; \
+if (list_empty(&nf_sk_hooks[pf][hook]) || \
+ (__ret=nf_sk_hook_slow(pf, hook, sk, &(skb), indev, outdev, okfn)) == 0) \
+ __ret = (okfn)(sk, skb); \
+else if (sk && skputfn) \
+ ((void (*)(struct sock *))skputfn)(sk); \
+__ret;})
#endif
int nf_hook_slow(int pf, unsigned int hook, struct sk_buff **pskb,
struct net_device *indev, struct net_device *outdev,
int (*okfn)(struct sk_buff *), int thresh);
+int nf_sk_hook_slow(int pf, unsigned int hook,
+ struct sock *sk, struct sk_buff **pskb,
+ struct net_device *indev, struct net_device *outdev,
+ int (*okfn)(struct sock *, struct sk_buff *));
+
/* Call setsockopt() */
int nf_setsockopt(struct sock *sk, int pf, int optval, char __user *opt,
int len);
@@ -192,6 +235,7 @@
#else /* !CONFIG_NETFILTER */
#define NF_HOOK(pf, hook, skb, indev, outdev, okfn) (okfn)(skb)
+#define NF_SK_HOOK(pf, hook, sk, skb, indev, outdev, okfn, skputfn) (okfn)(sk, skb)
static inline void nf_ct_attach(struct sk_buff *new, struct sk_buff *skb) {}
#endif /*CONFIG_NETFILTER*/
Index: net/core/netfilter.c
===================================================================
--- 3608de2fc88b062070a9d197eda9cac1fb9635d3/net/core/netfilter.c (mode:100644)
+++ e97143c76936d02bb1817a1e109e36707202a6bb/net/core/netfilter.c (mode:100644)
@@ -46,6 +46,7 @@
static DECLARE_MUTEX(nf_sockopt_mutex);
struct list_head nf_hooks[NPROTO][NF_MAX_HOOKS];
+struct list_head nf_sk_hooks[NPROTO][NF_MAX_HOOKS];
static LIST_HEAD(nf_sockopts);
static DEFINE_SPINLOCK(nf_hook_lock);
@@ -598,6 +599,97 @@
return;
}
+static unsigned int
+nf_sk_iterate(unsigned int hook, struct list_head *head,
+ struct sock *sk, struct sk_buff **skb,
+ const struct net_device *indev,
+ const struct net_device *outdev, struct list_head **i,
+ int (*okfn)(struct sock *sk, struct sk_buff *))
+{
+ unsigned int verdict;
+
+ /*
+ * The caller must not block between calls to this
+ * function because of risk of continuing from deleted element.
+ */
+ list_for_each_continue_rcu(*i, head) {
+ struct nf_sk_hook_ops *elem = (struct nf_sk_hook_ops *)*i;
+ /* Optimization: we don't need to hold module
+ reference here, since function can't sleep. --RR */
+ verdict = elem->hook(hook, sk, skb, indev, outdev, okfn);
+ if (verdict != NF_ACCEPT) {
+#ifdef CONFIG_NETFILTER_DEBUG
+ if (unlikely(verdict > NF_MAX_VERDICT)) {
+ NFDEBUG("Evil return from %p(%u).\n",
+ elem->hook, hook);
+ continue;
+ }
+#endif
+ if (verdict != NF_REPEAT)
+ return verdict;
+ *i = (*i)->prev;
+ }
+ }
+ return NF_ACCEPT;
+}
+
+int nf_sk_hook_slow(int pf, unsigned int hook,
+ struct sock *sk, struct sk_buff **pskb,
+ struct net_device *indev, struct net_device *outdev,
+ int (*okfn)(struct sock *sk, struct sk_buff *))
+{
+ struct list_head *elem;
+ unsigned int verdict;
+ int ret = 1;
+
+ /* We may already have this, but read-locks nest anyway */
+ rcu_read_lock();
+
+ elem = &nf_sk_hooks[pf][hook];
+ verdict = nf_sk_iterate(hook, &nf_sk_hooks[pf][hook], sk, pskb,
+ indev, outdev, &elem, okfn);
+ if (verdict == NF_ACCEPT || verdict == NF_STOP) {
+ ret = 0;
+ goto unlock;
+ } else if (verdict == NF_DROP) {
+ kfree_skb(*pskb);
+ /* Don't trigger retransmit in ip_local_deliver_finish() */
+ if (indev == NULL)
+ ret = -EPERM;
+ }
+unlock:
+ rcu_read_unlock();
+ return ret;
+}
+EXPORT_SYMBOL(nf_sk_hook_slow);
+
+int nf_register_sk_hook(struct nf_sk_hook_ops *reg)
+{
+ struct list_head *i;
+
+ spin_lock_bh(&nf_hook_lock);
+ list_for_each(i, &nf_sk_hooks[reg->pf][reg->hooknum]) {
+ if (reg->priority < ((struct nf_sk_hook_ops *)i)->priority)
+ break;
+ }
+ list_add_rcu(®->list, i->prev);
+ spin_unlock_bh(&nf_hook_lock);
+
+ synchronize_net();
+ return 0;
+}
+EXPORT_SYMBOL(nf_register_sk_hook);
+
+void nf_unregister_sk_hook(struct nf_sk_hook_ops *reg)
+{
+ spin_lock_bh(&nf_hook_lock);
+ list_del_rcu(®->list);
+ spin_unlock_bh(&nf_hook_lock);
+
+ synchronize_net();
+}
+EXPORT_SYMBOL(nf_unregister_sk_hook);
+
#ifdef CONFIG_INET
/* route_me_harder function, used by iptable_nat, iptable_mangle + ip_queue */
int ip_route_me_harder(struct sk_buff **pskb)
@@ -779,8 +871,10 @@
int i, h;
for (i = 0; i < NPROTO; i++) {
- for (h = 0; h < NF_MAX_HOOKS; h++)
+ for (h = 0; h < NF_MAX_HOOKS; h++) {
INIT_LIST_HEAD(&nf_hooks[i][h]);
+ INIT_LIST_HEAD(&nf_sk_hooks[i][h]);
+ }
}
}
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: [netfilter socket hooks 1/5]: Add socket hook infrastructure
2005-05-10 16:00 ` [netfilter socket hooks 1/5]: Add socket hook infrastructure Patrick McHardy
@ 2005-05-11 23:22 ` James Morris
2005-05-11 23:27 ` James Morris
2005-05-11 23:27 ` Patrick McHardy
0 siblings, 2 replies; 30+ messages in thread
From: James Morris @ 2005-05-11 23:22 UTC (permalink / raw)
To: Patrick McHardy; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
On Tue, 10 May 2005, Patrick McHardy wrote:
> +struct nf_sk_hook_ops
> +{
> + struct list_head list;
> +
> + /* User fills in from here down. */
> + nf_sk_hookfn *hook;
> + struct module *owner;
> + unsigned int pf;
> + unsigned int hooknum;
> + /* Hooks are ordered in ascending priority. */
> + int priority;
> +};
Do you need to add this struct? It's the same as nf_hook_ops.
- James
--
James Morris
<jmorris@redhat.com>
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: [netfilter socket hooks 1/5]: Add socket hook infrastructure
2005-05-11 23:22 ` James Morris
@ 2005-05-11 23:27 ` James Morris
2005-05-11 23:27 ` Patrick McHardy
1 sibling, 0 replies; 30+ messages in thread
From: James Morris @ 2005-05-11 23:27 UTC (permalink / raw)
To: Patrick McHardy; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
On Wed, 11 May 2005, James Morris wrote:
> Do you need to add this struct? It's the same as nf_hook_ops.
Don't worry, I can see nf_sk_hookfn is differnt.
- James
--
James Morris
<jmorris@redhat.com>
^ permalink raw reply [flat|nested] 30+ messages in thread
* Re: [netfilter socket hooks 1/5]: Add socket hook infrastructure
2005-05-11 23:22 ` James Morris
2005-05-11 23:27 ` James Morris
@ 2005-05-11 23:27 ` Patrick McHardy
1 sibling, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-11 23:27 UTC (permalink / raw)
To: James Morris; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
James Morris wrote:
> On Tue, 10 May 2005, Patrick McHardy wrote:
>
>
>>+struct nf_sk_hook_ops
>>+{
>>+ struct list_head list;
>>+
>>+ /* User fills in from here down. */
>>+ nf_sk_hookfn *hook;
>>+ struct module *owner;
>>+ unsigned int pf;
>>+ unsigned int hooknum;
>>+ /* Hooks are ordered in ascending priority. */
>>+ int priority;
>>+};
>
>
> Do you need to add this struct? It's the same as nf_hook_ops.
Unfortunately yes, the hook functions have different prototypes.
Regards
Patrick
^ permalink raw reply [flat|nested] 30+ messages in thread
* [netfilter socket hooks 2/5]: Add protocol hooks
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
2005-05-10 16:00 ` [netfilter socket hooks 1/5]: Add socket hook infrastructure Patrick McHardy
@ 2005-05-10 16:00 ` Patrick McHardy
2005-05-10 16:01 ` [netfilter socket hooks 3/5]: Add struct sock * argument to ipt_do_table() Patrick McHardy
` (6 subsequent siblings)
8 siblings, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-10 16:00 UTC (permalink / raw)
To: netfilter-devel; +Cc: juha.heljoranta, Rusty Russell
[-- Attachment #1: 02.diff --]
[-- Type: text/x-patch, Size: 9709 bytes --]
[NETFILTER]: Add protocol hooks
Signed-off-by: Patrick McHardy <kaber@trash.net>
---
commit 03a2e97e71c3c9bfbfc3d357544348d393551658
tree b53df6f327c03ec282a1b75326db321dbd2f0bc0
parent 4ca9ffc0b58dd44e91cbaaa2de3c27faa220e047
author Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:34:53 +0200
committer Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:34:53 +0200
net/ipv4/raw.c | 8 ++-
net/ipv4/tcp_ipv4.c | 123 +++++++++++++++++++++++++++++++++-------------------
net/ipv4/udp.c | 109 +++++++++++++++++++++++++++-------------------
3 files changed, 151 insertions(+), 89 deletions(-)
Index: net/ipv4/raw.c
===================================================================
--- e97143c76936d02bb1817a1e109e36707202a6bb/net/ipv4/raw.c (mode:100644)
+++ b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/raw.c (mode:100644)
@@ -246,7 +246,7 @@
return NET_RX_SUCCESS;
}
-int raw_rcv(struct sock *sk, struct sk_buff *skb)
+static inline int raw_rcv_finish(struct sock *sk, struct sk_buff *skb)
{
if (!xfrm4_policy_check(sk, XFRM_POLICY_IN, skb)) {
kfree_skb(skb);
@@ -259,6 +259,12 @@
return 0;
}
+int raw_rcv(struct sock *sk, struct sk_buff *skb)
+{
+ return NF_SK_HOOK(AF_INET, NF_IP_LOCAL_IN, sk, skb, skb->dev, NULL,
+ raw_rcv_finish, NULL);
+}
+
static int raw_send_hdrinc(struct sock *sk, void *from, int length,
struct rtable *rt,
unsigned int flags)
Index: net/ipv4/tcp_ipv4.c
===================================================================
--- e97143c76936d02bb1817a1e109e36707202a6bb/net/ipv4/tcp_ipv4.c (mode:100644)
+++ b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/tcp_ipv4.c (mode:100644)
@@ -62,6 +62,8 @@
#include <linux/jhash.h>
#include <linux/init.h>
#include <linux/times.h>
+#include <linux/netfilter.h>
+#include <linux/netfilter_ipv4.h>
#include <net/icmp.h>
#include <net/tcp.h>
@@ -1713,52 +1715,24 @@
goto discard;
}
-/*
- * From tcp_input.c
- */
-
-int tcp_v4_rcv(struct sk_buff *skb)
+/* Dummy outfn for netfilter - caller still owns the skb */
+static inline int tcp_v4_rcv_finish2(struct sock *sk, struct sk_buff *skb)
{
- struct tcphdr *th;
- struct sock *sk;
- int ret;
-
- if (skb->pkt_type != PACKET_HOST)
- goto discard_it;
-
- /* Count it even if it's bad */
- TCP_INC_STATS_BH(TCP_MIB_INSEGS);
-
- if (!pskb_may_pull(skb, sizeof(struct tcphdr)))
- goto discard_it;
-
- th = skb->h.th;
-
- if (th->doff < sizeof(struct tcphdr) / 4)
- goto bad_packet;
- if (!pskb_may_pull(skb, th->doff * 4))
- goto discard_it;
-
- /* An explanation is required here, I think.
- * Packet length and doff are validated by header prediction,
- * provided case of th->doff==0 is elimineted.
- * So, we defer the checks. */
- if ((skb->ip_summed != CHECKSUM_UNNECESSARY &&
- tcp_v4_checksum_init(skb) < 0))
- goto bad_packet;
+ return 0;
+}
- th = skb->h.th;
- TCP_SKB_CB(skb)->seq = ntohl(th->seq);
- TCP_SKB_CB(skb)->end_seq = (TCP_SKB_CB(skb)->seq + th->syn + th->fin +
- skb->len - th->doff * 4);
- TCP_SKB_CB(skb)->ack_seq = ntohl(th->ack_seq);
- TCP_SKB_CB(skb)->when = 0;
- TCP_SKB_CB(skb)->flags = skb->nh.iph->tos;
- TCP_SKB_CB(skb)->sacked = 0;
+static inline void tcp_sock_put(struct sock *sk)
+{
+ if (sk->sk_state == TCP_TIME_WAIT)
+ tcp_tw_put((struct tcp_tw_bucket *)sk);
+ else
+ sock_put(sk);
+}
- sk = __tcp_v4_lookup(skb->nh.iph->saddr, th->source,
- skb->nh.iph->daddr, ntohs(th->dest),
- tcp_v4_iif(skb));
+static inline int tcp_v4_rcv_finish(struct sock *sk, struct sk_buff *skb)
+{
+ struct tcphdr *th = skb->h.th;
+ int ret;
if (!sk)
goto no_tcp_socket;
@@ -1793,7 +1767,6 @@
goto discard_it;
if (skb->len < (th->doff << 2) || tcp_checksum_complete(skb)) {
-bad_packet:
TCP_INC_STATS_BH(TCP_MIB_INERRS);
} else {
tcp_v4_send_reset(skb);
@@ -1829,6 +1802,11 @@
tcp_tw_deschedule((struct tcp_tw_bucket *)sk);
tcp_tw_put((struct tcp_tw_bucket *)sk);
sk = sk2;
+ ret = NF_SK_HOOK(AF_INET, NF_IP_LOCAL_IN, sk, skb,
+ skb->dev, NULL, tcp_v4_rcv_finish2,
+ tcp_sock_put);
+ if (ret)
+ return ret;
goto process;
}
/* Fall through to ACK */
@@ -1843,6 +1821,63 @@
goto discard_it;
}
+/*
+ * From tcp_input.c
+ */
+
+int tcp_v4_rcv(struct sk_buff *skb)
+{
+ struct tcphdr *th;
+ struct sock *sk;
+
+ if (skb->pkt_type != PACKET_HOST)
+ goto discard_it;
+
+ /* Count it even if it's bad */
+ TCP_INC_STATS_BH(TCP_MIB_INSEGS);
+
+ if (!pskb_may_pull(skb, sizeof(struct tcphdr)))
+ goto discard_it;
+
+ th = skb->h.th;
+
+ if (th->doff < sizeof(struct tcphdr) / 4)
+ goto bad_packet;
+ if (!pskb_may_pull(skb, th->doff * 4))
+ goto discard_it;
+
+ /* An explanation is required here, I think.
+ * Packet length and doff are validated by header prediction,
+ * provided case of th->doff==0 is elimineted.
+ * So, we defer the checks. */
+ if ((skb->ip_summed != CHECKSUM_UNNECESSARY &&
+ tcp_v4_checksum_init(skb) < 0))
+ goto bad_packet;
+
+ th = skb->h.th;
+ TCP_SKB_CB(skb)->seq = ntohl(th->seq);
+ TCP_SKB_CB(skb)->end_seq = (TCP_SKB_CB(skb)->seq + th->syn + th->fin +
+ skb->len - th->doff * 4);
+ TCP_SKB_CB(skb)->ack_seq = ntohl(th->ack_seq);
+ TCP_SKB_CB(skb)->when = 0;
+ TCP_SKB_CB(skb)->flags = skb->nh.iph->tos;
+ TCP_SKB_CB(skb)->sacked = 0;
+
+ sk = __tcp_v4_lookup(skb->nh.iph->saddr, th->source,
+ skb->nh.iph->daddr, ntohs(th->dest),
+ tcp_v4_iif(skb));
+
+ return NF_SK_HOOK(AF_INET, NF_IP_LOCAL_IN, sk, skb, skb->dev, NULL,
+ tcp_v4_rcv_finish, tcp_sock_put);
+
+bad_packet:
+ TCP_INC_STATS_BH(TCP_MIB_INERRS);
+discard_it:
+ /* Discard frame. */
+ kfree_skb(skb);
+ return 0;
+}
+
/* With per-bucket locks this operation is not-atomic, so that
* this version is not worse.
*/
Index: net/ipv4/udp.c
===================================================================
--- e97143c76936d02bb1817a1e109e36707202a6bb/net/ipv4/udp.c (mode:100644)
+++ b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/udp.c (mode:100644)
@@ -94,6 +94,8 @@
#include <linux/inet.h>
#include <linux/ipv6.h>
#include <linux/netdevice.h>
+#include <linux/netfilter.h>
+#include <linux/netfilter_ipv4.h>
#include <net/snmp.h>
#include <net/tcp.h>
#include <net/protocol.h>
@@ -1113,6 +1115,55 @@
return 0;
}
+static inline int udp_rcv_finish(struct sock *sk, struct sk_buff *skb)
+{
+ if (sk != NULL) {
+ int ret = udp_queue_rcv_skb(sk, skb);
+ sock_put(sk);
+
+ /* a return value > 0 means to resubmit the input, but
+ * it it wants the return to be -protocol, or 0
+ */
+ if (ret > 0)
+ return -ret;
+ return 0;
+ }
+
+ if (!xfrm4_policy_check(NULL, XFRM_POLICY_IN, skb))
+ goto drop;
+
+ /* No socket. Drop packet silently, if checksum is wrong */
+ if (udp_checksum_complete(skb))
+ goto csum_error;
+
+ UDP_INC_STATS_BH(UDP_MIB_NOPORTS);
+ icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
+
+ /*
+ * Hmm. We got an UDP packet to a port to which we
+ * don't wanna listen. Ignore it.
+ */
+ kfree_skb(skb);
+ return(0);
+
+csum_error:
+ /*
+ * RFC1122: OK. Discards the bad packet silently (as far as
+ * the network is concerned, anyway) as per 4.1.3.4 (MUST).
+ */
+ NETDEBUG(if (net_ratelimit())
+ printk(KERN_DEBUG "UDP: bad checksum. From %d.%d.%d.%d:%d to %d.%d.%d.%d:%d ulen %d\n",
+ NIPQUAD(skb->nh.iph->saddr),
+ ntohs(skb->h.uh->source),
+ NIPQUAD(skb->nh.iph->daddr),
+ ntohs(skb->h.uh->dest),
+ ntohs(skb->h.uh->len)));
+drop:
+ UDP_INC_STATS_BH(UDP_MIB_INERRORS);
+ kfree_skb(skb);
+ return(0);
+}
+
/*
* All we need to do is get the socket, and then do a checksum.
*/
@@ -1151,35 +1202,21 @@
sk = udp_v4_lookup(saddr, uh->source, daddr, uh->dest, skb->dev->ifindex);
- if (sk != NULL) {
- int ret = udp_queue_rcv_skb(sk, skb);
- sock_put(sk);
-
- /* a return value > 0 means to resubmit the input, but
- * it it wants the return to be -protocol, or 0
- */
- if (ret > 0)
- return -ret;
- return 0;
- }
-
- if (!xfrm4_policy_check(NULL, XFRM_POLICY_IN, skb))
- goto drop;
-
- /* No socket. Drop packet silently, if checksum is wrong */
- if (udp_checksum_complete(skb))
- goto csum_error;
-
- UDP_INC_STATS_BH(UDP_MIB_NOPORTS);
- icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
-
- /*
- * Hmm. We got an UDP packet to a port to which we
- * don't wanna listen. Ignore it.
+ return NF_SK_HOOK(AF_INET, NF_IP_LOCAL_IN, sk, skb, skb->dev, NULL,
+ udp_rcv_finish, sock_put);
+csum_error:
+ /*
+ * RFC1122: OK. Discards the bad packet silently (as far as
+ * the network is concerned, anyway) as per 4.1.3.4 (MUST).
*/
- kfree_skb(skb);
- return(0);
-
+ NETDEBUG(if (net_ratelimit())
+ printk(KERN_DEBUG "UDP: bad checksum. From %d.%d.%d.%d:%d to %d.%d.%d.%d:%d ulen %d\n",
+ NIPQUAD(skb->nh.iph->saddr),
+ ntohs(skb->h.uh->source),
+ NIPQUAD(skb->nh.iph->daddr),
+ ntohs(skb->h.uh->dest),
+ ntohs(skb->h.uh->len)));
+ goto drop;
short_packet:
NETDEBUG(if (net_ratelimit())
printk(KERN_DEBUG "UDP: short packet: From %u.%u.%u.%u:%u %d/%d to %u.%u.%u.%u:%u\n",
@@ -1191,23 +1228,7 @@
ntohs(uh->dest)));
no_header:
UDP_INC_STATS_BH(UDP_MIB_INERRORS);
- kfree_skb(skb);
- return(0);
-
-csum_error:
- /*
- * RFC1122: OK. Discards the bad packet silently (as far as
- * the network is concerned, anyway) as per 4.1.3.4 (MUST).
- */
- NETDEBUG(if (net_ratelimit())
- printk(KERN_DEBUG "UDP: bad checksum. From %d.%d.%d.%d:%d to %d.%d.%d.%d:%d ulen %d\n",
- NIPQUAD(saddr),
- ntohs(uh->source),
- NIPQUAD(daddr),
- ntohs(uh->dest),
- ulen));
drop:
- UDP_INC_STATS_BH(UDP_MIB_INERRORS);
kfree_skb(skb);
return(0);
}
^ permalink raw reply [flat|nested] 30+ messages in thread* [netfilter socket hooks 3/5]: Add struct sock * argument to ipt_do_table()
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
2005-05-10 16:00 ` [netfilter socket hooks 1/5]: Add socket hook infrastructure Patrick McHardy
2005-05-10 16:00 ` [netfilter socket hooks 2/5]: Add protocol hooks Patrick McHardy
@ 2005-05-10 16:01 ` Patrick McHardy
2005-05-10 16:01 ` [netfilter socket hooks 4/5]: Add struct sock * argument to match functions Patrick McHardy
` (5 subsequent siblings)
8 siblings, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-10 16:01 UTC (permalink / raw)
To: netfilter-devel; +Cc: juha.heljoranta, Rusty Russell
[-- Attachment #1: 03.diff --]
[-- Type: text/x-patch, Size: 4900 bytes --]
[NETFILTER]: Add struct sock * argument to ipt_do_table()
Signed-off-by: Patrick McHardy <kaber@trash.net>
---
commit 2816668ea745b16e1da608bf4d7b638a75389bd6
tree 8bd69ddefbecc96b2253453c6b4da15bbff92988
parent 03a2e97e71c3c9bfbfc3d357544348d393551658
author Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:36:10 +0200
committer Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:36:10 +0200
include/linux/netfilter_ipv4/ip_tables.h | 3 ++-
net/ipv4/netfilter/ip_nat_rule.c | 2 +-
net/ipv4/netfilter/ip_tables.c | 3 ++-
net/ipv4/netfilter/iptable_filter.c | 4 ++--
net/ipv4/netfilter/iptable_mangle.c | 4 ++--
net/ipv4/netfilter/iptable_raw.c | 2 +-
6 files changed, 10 insertions(+), 8 deletions(-)
Index: include/linux/netfilter_ipv4/ip_tables.h
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/include/linux/netfilter_ipv4/ip_tables.h (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/include/linux/netfilter_ipv4/ip_tables.h (mode:100644)
@@ -478,7 +478,8 @@
extern int ipt_register_table(struct ipt_table *table,
const struct ipt_replace *repl);
extern void ipt_unregister_table(struct ipt_table *table);
-extern unsigned int ipt_do_table(struct sk_buff **pskb,
+extern unsigned int ipt_do_table(struct sock *sk,
+ struct sk_buff **pskb,
unsigned int hook,
const struct net_device *in,
const struct net_device *out,
Index: net/ipv4/netfilter/ip_nat_rule.c
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/netfilter/ip_nat_rule.c (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ip_nat_rule.c (mode:100644)
@@ -264,7 +264,7 @@
{
int ret;
- ret = ipt_do_table(pskb, hooknum, in, out, &nat_table, NULL);
+ ret = ipt_do_table(NULL, pskb, hooknum, in, out, &nat_table, NULL);
if (ret == NF_ACCEPT) {
if (!ip_nat_initialized(ct, HOOK2MANIP(hooknum)))
Index: net/ipv4/netfilter/ip_tables.c
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/netfilter/ip_tables.c (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ip_tables.c (mode:100644)
@@ -257,7 +257,8 @@
/* Returns one of the generic firewall policies, like NF_ACCEPT. */
unsigned int
-ipt_do_table(struct sk_buff **pskb,
+ipt_do_table(struct sock *sk,
+ struct sk_buff **pskb,
unsigned int hook,
const struct net_device *in,
const struct net_device *out,
Index: net/ipv4/netfilter/iptable_filter.c
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/netfilter/iptable_filter.c (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/iptable_filter.c (mode:100644)
@@ -89,7 +89,7 @@
const struct net_device *out,
int (*okfn)(struct sk_buff *))
{
- return ipt_do_table(pskb, hook, in, out, &packet_filter, NULL);
+ return ipt_do_table(NULL, pskb, hook, in, out, &packet_filter, NULL);
}
static unsigned int
@@ -107,7 +107,7 @@
return NF_ACCEPT;
}
- return ipt_do_table(pskb, hook, in, out, &packet_filter, NULL);
+ return ipt_do_table(NULL, pskb, hook, in, out, &packet_filter, NULL);
}
static struct nf_hook_ops ipt_ops[] = {
Index: net/ipv4/netfilter/iptable_mangle.c
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/netfilter/iptable_mangle.c (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/iptable_mangle.c (mode:100644)
@@ -119,7 +119,7 @@
const struct net_device *out,
int (*okfn)(struct sk_buff *))
{
- return ipt_do_table(pskb, hook, in, out, &packet_mangler, NULL);
+ return ipt_do_table(NULL, pskb, hook, in, out, &packet_mangler, NULL);
}
static unsigned int
@@ -148,7 +148,7 @@
daddr = (*pskb)->nh.iph->daddr;
tos = (*pskb)->nh.iph->tos;
- ret = ipt_do_table(pskb, hook, in, out, &packet_mangler, NULL);
+ ret = ipt_do_table(NULL, pskb, hook, in, out, &packet_mangler, NULL);
/* Reroute for ANY change. */
if (ret != NF_DROP && ret != NF_STOLEN && ret != NF_QUEUE
&& ((*pskb)->nh.iph->saddr != saddr
Index: net/ipv4/netfilter/iptable_raw.c
===================================================================
--- b53df6f327c03ec282a1b75326db321dbd2f0bc0/net/ipv4/netfilter/iptable_raw.c (mode:100644)
+++ 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/iptable_raw.c (mode:100644)
@@ -94,7 +94,7 @@
const struct net_device *out,
int (*okfn)(struct sk_buff *))
{
- return ipt_do_table(pskb, hook, in, out, &packet_raw, NULL);
+ return ipt_do_table(NULL, pskb, hook, in, out, &packet_raw, NULL);
}
/* 'raw' is the very first table. */
^ permalink raw reply [flat|nested] 30+ messages in thread* [netfilter socket hooks 4/5]: Add struct sock * argument to match functions
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (2 preceding siblings ...)
2005-05-10 16:01 ` [netfilter socket hooks 3/5]: Add struct sock * argument to ipt_do_table() Patrick McHardy
@ 2005-05-10 16:01 ` Patrick McHardy
2005-05-10 16:01 ` [netfilter socket hooks 5/5]: Add skfilter table Patrick McHardy
` (4 subsequent siblings)
8 siblings, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-10 16:01 UTC (permalink / raw)
To: netfilter-devel; +Cc: juha.heljoranta, Rusty Russell
[-- Attachment #1: 04.diff --]
[-- Type: text/x-patch, Size: 20978 bytes --]
[NETFILTER]: Add struct sock * argument to match functions
Signed-off-by: Patrick McHardy <kaber@trash.net>
---
commit 3e78de8c1e4b12407299b48cf9f024786415639f
tree a24014694fc1a7ed32010fe4524b2601c6516eaf
parent 2816668ea745b16e1da608bf4d7b638a75389bd6
author Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:37:19 +0200
committer Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:37:19 +0200
include/linux/netfilter_ipv4/ip_tables.h | 3 ++-
net/ipv4/netfilter/ip_tables.c | 14 +++++++++-----
net/ipv4/netfilter/ipt_addrtype.c | 6 +++---
net/ipv4/netfilter/ipt_ah.c | 3 ++-
net/ipv4/netfilter/ipt_comment.c | 3 ++-
net/ipv4/netfilter/ipt_connmark.c | 3 ++-
net/ipv4/netfilter/ipt_conntrack.c | 3 ++-
net/ipv4/netfilter/ipt_dscp.c | 6 +++---
net/ipv4/netfilter/ipt_ecn.c | 6 +++---
net/ipv4/netfilter/ipt_esp.c | 3 ++-
net/ipv4/netfilter/ipt_hashlimit.c | 3 ++-
net/ipv4/netfilter/ipt_helper.c | 3 ++-
net/ipv4/netfilter/ipt_iprange.c | 3 ++-
net/ipv4/netfilter/ipt_length.c | 3 ++-
net/ipv4/netfilter/ipt_limit.c | 3 ++-
net/ipv4/netfilter/ipt_mac.c | 3 ++-
net/ipv4/netfilter/ipt_mark.c | 3 ++-
net/ipv4/netfilter/ipt_multiport.c | 6 ++++--
net/ipv4/netfilter/ipt_owner.c | 3 ++-
net/ipv4/netfilter/ipt_physdev.c | 3 ++-
net/ipv4/netfilter/ipt_pkttype.c | 13 +++++++------
net/ipv4/netfilter/ipt_realm.c | 3 ++-
net/ipv4/netfilter/ipt_recent.c | 8 +++++---
net/ipv4/netfilter/ipt_sctp.c | 3 ++-
net/ipv4/netfilter/ipt_state.c | 3 ++-
net/ipv4/netfilter/ipt_tcpmss.c | 3 ++-
net/ipv4/netfilter/ipt_tos.c | 3 ++-
net/ipv4/netfilter/ipt_ttl.c | 6 +++---
28 files changed, 77 insertions(+), 48 deletions(-)
Index: include/linux/netfilter_ipv4/ip_tables.h
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/include/linux/netfilter_ipv4/ip_tables.h (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/include/linux/netfilter_ipv4/ip_tables.h (mode:100644)
@@ -368,7 +368,8 @@
/* Arguments changed since 2.4, as this must now handle
non-linear skbs, using skb_copy_bits and
skb_ip_make_writable. */
- int (*match)(const struct sk_buff *skb,
+ int (*match)(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ip_tables.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ip_tables.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ip_tables.c (mode:100644)
@@ -236,6 +236,7 @@
static inline
int do_match(struct ipt_entry_match *m,
+ const struct sock *sk,
const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
@@ -243,7 +244,7 @@
int *hotdrop)
{
/* Stop iteration if it doesn't match */
- if (!m->u.kernel.match->match(skb, in, out, m->data, offset, hotdrop))
+ if (!m->u.kernel.match->match(sk, skb, in, out, m->data, offset, hotdrop))
return 1;
else
return 0;
@@ -319,7 +320,7 @@
struct ipt_entry_target *t;
if (IPT_MATCH_ITERATE(e, do_match,
- *pskb, in, out,
+ sk, *pskb, in, out,
offset, &hotdrop) != 0)
goto no_match;
@@ -1569,7 +1570,8 @@
}
static int
-tcp_match(const struct sk_buff *skb,
+tcp_match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
@@ -1650,7 +1652,8 @@
}
static int
-udp_match(const struct sk_buff *skb,
+udp_match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
@@ -1723,7 +1726,8 @@
}
static int
-icmp_match(const struct sk_buff *skb,
+icmp_match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_addrtype.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_addrtype.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_addrtype.c (mode:100644)
@@ -27,9 +27,9 @@
return !!(mask & (1 << inet_addr_type(addr)));
}
-static int match(const struct sk_buff *skb, const struct net_device *in,
- const struct net_device *out, const void *matchinfo,
- int offset, int *hotdrop)
+static int match(const struct sock *sk, const struct sk_buff *skb,
+ const struct net_device *in, const struct net_device *out,
+ const void *matchinfo, int offset, int *hotdrop)
{
const struct ipt_addrtype_info *info = matchinfo;
const struct iphdr *iph = skb->nh.iph;
Index: net/ipv4/netfilter/ipt_ah.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_ah.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_ah.c (mode:100644)
@@ -36,7 +36,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_comment.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_comment.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_comment.c (mode:100644)
@@ -14,7 +14,8 @@
MODULE_LICENSE("GPL");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_connmark.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_connmark.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_connmark.c (mode:100644)
@@ -31,7 +31,8 @@
#include <linux/netfilter_ipv4/ip_conntrack.h>
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_conntrack.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_conntrack.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_conntrack.c (mode:100644)
@@ -19,7 +19,8 @@
MODULE_DESCRIPTION("iptables connection tracking match module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_dscp.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_dscp.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_dscp.c (mode:100644)
@@ -19,9 +19,9 @@
MODULE_DESCRIPTION("iptables DSCP matching module");
MODULE_LICENSE("GPL");
-static int match(const struct sk_buff *skb, const struct net_device *in,
- const struct net_device *out, const void *matchinfo,
- int offset, int *hotdrop)
+static int match(const struct sock *sk, const struct sk_buff *skb,
+ const struct net_device *in, const struct net_device *out,
+ const void *matchinfo, int offset, int *hotdrop)
{
const struct ipt_dscp_info *info = matchinfo;
const struct iphdr *iph = skb->nh.iph;
Index: net/ipv4/netfilter/ipt_ecn.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_ecn.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_ecn.c (mode:100644)
@@ -65,9 +65,9 @@
return 1;
}
-static int match(const struct sk_buff *skb, const struct net_device *in,
- const struct net_device *out, const void *matchinfo,
- int offset, int *hotdrop)
+static int match(const struct sock *sk, const struct sk_buff *skb,
+ const struct net_device *in, const struct net_device *out,
+ const void *matchinfo, int offset, int *hotdrop)
{
const struct ipt_ecn_info *info = matchinfo;
Index: net/ipv4/netfilter/ipt_esp.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_esp.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_esp.c (mode:100644)
@@ -37,7 +37,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_hashlimit.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_hashlimit.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_hashlimit.c (mode:100644)
@@ -425,7 +425,8 @@
static int
-hashlimit_match(const struct sk_buff *skb,
+hashlimit_match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_helper.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_helper.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_helper.c (mode:100644)
@@ -30,7 +30,8 @@
#endif
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_iprange.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_iprange.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_iprange.c (mode:100644)
@@ -24,7 +24,8 @@
#endif
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_length.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_length.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_length.c (mode:100644)
@@ -17,7 +17,8 @@
MODULE_LICENSE("GPL");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_limit.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_limit.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_limit.c (mode:100644)
@@ -63,7 +63,8 @@
#define CREDITS_PER_JIFFY POW2_BELOW32(MAX_CPJ)
static int
-ipt_limit_match(const struct sk_buff *skb,
+ipt_limit_match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_mac.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_mac.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_mac.c (mode:100644)
@@ -20,7 +20,8 @@
MODULE_DESCRIPTION("iptables mac matching module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_mark.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_mark.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_mark.c (mode:100644)
@@ -18,7 +18,8 @@
MODULE_DESCRIPTION("iptables mark matching module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_multiport.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_multiport.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_multiport.c (mode:100644)
@@ -92,7 +92,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
@@ -123,7 +124,8 @@
}
static int
-match_v1(const struct sk_buff *skb,
+match_v1(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_owner.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_owner.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_owner.c (mode:100644)
@@ -121,7 +121,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_physdev.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_physdev.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_physdev.c (mode:100644)
@@ -21,7 +21,8 @@
MODULE_DESCRIPTION("iptables bridge physical device match module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_pkttype.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_pkttype.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_pkttype.c (mode:100644)
@@ -17,12 +17,13 @@
MODULE_AUTHOR("Michal Ludvig <michal@logix.cz>");
MODULE_DESCRIPTION("IP tables match to match on linklayer packet type");
-static int match(const struct sk_buff *skb,
- const struct net_device *in,
- const struct net_device *out,
- const void *matchinfo,
- int offset,
- int *hotdrop)
+static int match(const struct sock *sk,
+ const struct sk_buff *skb,
+ const struct net_device *in,
+ const struct net_device *out,
+ const void *matchinfo,
+ int offset,
+ int *hotdrop)
{
const struct ipt_pkttype_info *info = matchinfo;
Index: net/ipv4/netfilter/ipt_realm.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_realm.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_realm.c (mode:100644)
@@ -22,7 +22,8 @@
MODULE_DESCRIPTION("iptables realm match");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_recent.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_recent.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_recent.c (mode:100644)
@@ -99,7 +99,8 @@
/* Function declaration for later. */
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
@@ -317,7 +318,7 @@
skb->nh.iph->daddr = 0;
/* Clear ttl since we have no way of knowing it */
skb->nh.iph->ttl = 0;
- match(skb,NULL,NULL,info,0,NULL);
+ match(NULL,skb,NULL,NULL,info,0,NULL);
kfree(skb->nh.iph);
out_free_skb:
@@ -352,7 +353,8 @@
* --seconds and --hitcount can be combined
*/
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_sctp.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_sctp.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_sctp.c (mode:100644)
@@ -113,7 +113,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_state.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_state.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_state.c (mode:100644)
@@ -19,7 +19,8 @@
MODULE_DESCRIPTION("iptables connection tracking state match module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_tcpmss.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_tcpmss.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_tcpmss.c (mode:100644)
@@ -74,7 +74,8 @@
}
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_tos.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_tos.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_tos.c (mode:100644)
@@ -18,7 +18,8 @@
MODULE_DESCRIPTION("iptables TOS match module");
static int
-match(const struct sk_buff *skb,
+match(const struct sock *sk,
+ const struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
const void *matchinfo,
Index: net/ipv4/netfilter/ipt_ttl.c
===================================================================
--- 8bd69ddefbecc96b2253453c6b4da15bbff92988/net/ipv4/netfilter/ipt_ttl.c (mode:100644)
+++ a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/ipt_ttl.c (mode:100644)
@@ -19,9 +19,9 @@
MODULE_DESCRIPTION("IP tables TTL matching module");
MODULE_LICENSE("GPL");
-static int match(const struct sk_buff *skb, const struct net_device *in,
- const struct net_device *out, const void *matchinfo,
- int offset, int *hotdrop)
+static int match(const struct sock *sk, const struct sk_buff *skb,
+ const struct net_device *in, const struct net_device *out,
+ const void *matchinfo, int offset, int *hotdrop)
{
const struct ipt_ttl_info *info = matchinfo;
^ permalink raw reply [flat|nested] 30+ messages in thread* [netfilter socket hooks 5/5]: Add skfilter table
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (3 preceding siblings ...)
2005-05-10 16:01 ` [netfilter socket hooks 4/5]: Add struct sock * argument to match functions Patrick McHardy
@ 2005-05-10 16:01 ` Patrick McHardy
2005-05-10 18:26 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) James Morris
` (3 subsequent siblings)
8 siblings, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-10 16:01 UTC (permalink / raw)
To: netfilter-devel; +Cc: juha.heljoranta, Rusty Russell
[-- Attachment #1: 05.diff --]
[-- Type: text/x-patch, Size: 5009 bytes --]
[NETFILTER]: Add skfilter table
Signed-off-by: Patrick McHardy <kaber@trash.net>
---
commit 52c8e9e72ec788e5829c6e3d412ab9d1816d79a0
tree 4919a5761d3ba1c668a54d32a8f028f002c8ff24
parent 3e78de8c1e4b12407299b48cf9f024786415639f
author Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:41:31 +0200
committer Patrick McHardy <kaber@trash.net> Mon, 09 May 2005 18:41:31 +0200
net/ipv4/netfilter/Kconfig | 4
net/ipv4/netfilter/Makefile | 2
net/ipv4/netfilter/iptable_skfilter.c | 140 ++++++++++++++++++++++++++++++++++
3 files changed, 146 insertions(+)
Index: net/ipv4/netfilter/Kconfig
===================================================================
--- a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/Kconfig (mode:100644)
+++ 4919a5761d3ba1c668a54d32a8f028f002c8ff24/net/ipv4/netfilter/Kconfig (mode:100644)
@@ -386,6 +386,10 @@
To compile it as a module, choose M here. If unsure, say N.
+config IP_NF_SK_FILTER
+ tristate "Socket packet filtering"
+ depends on IP_NF_IPTABLES
+
config IP_NF_TARGET_REJECT
tristate "REJECT target support"
depends on IP_NF_FILTER
Index: net/ipv4/netfilter/Makefile
===================================================================
--- a24014694fc1a7ed32010fe4524b2601c6516eaf/net/ipv4/netfilter/Makefile (mode:100644)
+++ 4919a5761d3ba1c668a54d32a8f028f002c8ff24/net/ipv4/netfilter/Makefile (mode:100644)
@@ -33,6 +33,8 @@
obj-$(CONFIG_IP_NF_NAT) += iptable_nat.o
obj-$(CONFIG_IP_NF_RAW) += iptable_raw.o
+obj-$(CONFIG_IP_NF_SK_FILTER) += iptable_skfilter.o
+
# matches
obj-$(CONFIG_IP_NF_MATCH_HELPER) += ipt_helper.o
obj-$(CONFIG_IP_NF_MATCH_LIMIT) += ipt_limit.o
Index: net/ipv4/netfilter/iptable_skfilter.c
===================================================================
--- /dev/null (tree:a24014694fc1a7ed32010fe4524b2601c6516eaf)
+++ 4919a5761d3ba1c668a54d32a8f028f002c8ff24/net/ipv4/netfilter/iptable_skfilter.c (mode:100644)
@@ -0,0 +1,140 @@
+/*
+ * iptables 'skfilter' table
+ *
+ * Copyright (C) 2005 Patrick McHardy <kaber@trash.net>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#include <linux/module.h>
+#include <linux/netfilter_ipv4/ip_tables.h>
+
+#define SKFILTER_VALID_HOOKS ((1 << NF_IP_LOCAL_IN))
+
+static struct
+{
+ struct ipt_replace repl;
+ struct ipt_standard entries[1];
+ struct ipt_error term;
+} initial_table __initdata = {
+ .repl = {
+ .name = "skfilter",
+ .valid_hooks = SKFILTER_VALID_HOOKS,
+ .num_entries = 2,
+ .size = sizeof(struct ipt_standard) * 1 + sizeof(struct ipt_error),
+ .hook_entry = {
+ [NF_IP_LOCAL_IN] = 0,
+ },
+ .underflow = {
+ [NF_IP_LOCAL_IN] = 0,
+ },
+ },
+ .entries = {
+ /* LOCAL_IN */
+ {
+ .entry = {
+ .target_offset = sizeof(struct ipt_entry),
+ .next_offset = sizeof(struct ipt_standard),
+ },
+ .target = {
+ .target = {
+ .u = {
+ .target_size = IPT_ALIGN(sizeof(struct ipt_standard_target)),
+ },
+ },
+ .verdict = -NF_ACCEPT - 1,
+ },
+ },
+ },
+ /* ERROR */
+ .term = {
+ .entry = {
+ .target_offset = sizeof(struct ipt_entry),
+ .next_offset = sizeof(struct ipt_error),
+ },
+ .target = {
+ .target = {
+ .u = {
+ .user = {
+ .target_size = IPT_ALIGN(sizeof(struct ipt_error_target)),
+ .name = IPT_ERROR_TARGET,
+ },
+ },
+ },
+ .errorname = "ERROR",
+ },
+ }
+};
+
+static struct ipt_table skfilter = {
+ .name = "skfilter",
+ .valid_hooks = SKFILTER_VALID_HOOKS,
+ .lock = RW_LOCK_UNLOCKED,
+ .me = THIS_MODULE
+};
+
+/* The work comes in here from netfilter.c. */
+static unsigned int
+ipt_hook(unsigned int hook,
+ struct sock *sk,
+ struct sk_buff **pskb,
+ const struct net_device *in,
+ const struct net_device *out,
+ int (*okfn)(struct sock *, struct sk_buff *))
+{
+ unsigned int ret;
+ int pull = 0;
+
+ if ((*pskb)->data != (*pskb)->nh.raw) {
+ __skb_push(*pskb, (*pskb)->data - (*pskb)->nh.raw);
+ pull = 1;
+ }
+ ret = ipt_do_table(NULL, pskb, hook, in, out, &skfilter, NULL);
+ if (pull)
+ __skb_pull(*pskb, (*pskb)->nh.iph->ihl * 4);
+ return ret;
+}
+
+static struct nf_sk_hook_ops ipt_ops[] = {
+ {
+ .hook = ipt_hook,
+ .owner = THIS_MODULE,
+ .pf = PF_INET,
+ .hooknum = NF_IP_LOCAL_IN,
+ .priority = NF_IP_PRI_FILTER,
+ },
+};
+
+static int __init init(void)
+{
+ int ret;
+
+ /* Register table */
+ ret = ipt_register_table(&skfilter, &initial_table.repl);
+ if (ret < 0)
+ return ret;
+
+ /* Register hooks */
+ ret = nf_register_sk_hook(&ipt_ops[0]);
+ if (ret < 0)
+ goto cleanup_table;
+
+ return ret;
+
+ cleanup_table:
+ ipt_unregister_table(&skfilter);
+
+ return ret;
+}
+
+static void __exit fini(void)
+{
+ nf_unregister_sk_hook(&ipt_ops[0]);
+ ipt_unregister_table(&skfilter);
+}
+
+module_init(init);
+module_exit(fini);
+MODULE_LICENSE("GPL");
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: Netfilter socket hooks (was: Re: Status of owner-socketlookup)
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (4 preceding siblings ...)
2005-05-10 16:01 ` [netfilter socket hooks 5/5]: Add skfilter table Patrick McHardy
@ 2005-05-10 18:26 ` James Morris
2005-05-10 20:37 ` Netfilter socket hooks Jonas Berlin
` (2 subsequent siblings)
8 siblings, 0 replies; 30+ messages in thread
From: James Morris @ 2005-05-10 18:26 UTC (permalink / raw)
To: Patrick McHardy; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
On Tue, 10 May 2005, Patrick McHardy wrote:
> Here is a first shot at socket hooks.
Cool, I'll try and get them working with the SELinux/iptables code I've
been working on:
http://people.redhat.com/jmorris/selinux/selipt/
- James
--
James Morris
<jmorris@redhat.com>
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: Netfilter socket hooks
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (5 preceding siblings ...)
2005-05-10 18:26 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) James Morris
@ 2005-05-10 20:37 ` Jonas Berlin
2005-05-11 0:04 ` David S. Miller
2005-05-11 23:57 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) James Morris
8 siblings, 0 replies; 30+ messages in thread
From: Jonas Berlin @ 2005-05-10 20:37 UTC (permalink / raw)
To: Patrick McHardy; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Quoting Patrick McHardy on 2005-05-10 15:59 UTC:
> Here is a first shot at socket hooks.
Great :)
> Comments?
On what level will this be.. would one be able to filter what userspace
programs do in addition to filtering what internet clients are allowed
to do?
I.e. would one be able to filter userspace socket calls like accept(),
connect(), bind(), recv(), send(), and maybe even setsockopt() etc?
Isn't it almost as important to protect the internet from malicious
users as to protect users from the internet ?-) SELinux could maybe add
features to base web access policies on SELinux's normal mechanism that
currently grants/restricts access.
Example: If wget tryes to access the internet as a child of process A
(which has been granted all web access), then wget would be allowed to
do whatever it wants. Otherwise, wget's connect() call (when connecting
to a http server) would fail with some Exxxx errno code..
It would also be nice if this skfilter provided something similar to the
QUEUE target to allow users yet another level to hook in.. This could
possibly allow quite clean implementations of interactive firewall clients..
//
I would also be interested if you could give some idea of what kind of
commands you were thinking of that would be used to control skfilter..
- --
- - xkr47
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.1 (GNU/Linux)
iD8DBQFCgRt0xyF48ZTvn+4RAr3iAJ9Hl3TNHKn6wlBQNXUCgBtK7LY3tQCfWsM3
6TfPFQaGf02SD9XZVHOmmd0=
=n1tg
-----END PGP SIGNATURE-----
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: Netfilter socket hooks
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (6 preceding siblings ...)
2005-05-10 20:37 ` Netfilter socket hooks Jonas Berlin
@ 2005-05-11 0:04 ` David S. Miller
2005-05-11 23:57 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) James Morris
8 siblings, 0 replies; 30+ messages in thread
From: David S. Miller @ 2005-05-11 0:04 UTC (permalink / raw)
To: kaber; +Cc: juha.heljoranta, rusty, netfilter-devel
From: Patrick McHardy <kaber@trash.net>
Subject: Netfilter socket hooks (was: Re: Status of owner-socketlookup)
Date: Tue, 10 May 2005 17:59:13 +0200
> Here is a first shot at socket hooks. Nothing uses them yet,
> and at least two things are still missing:
>
> - conntrack reference should not be dropped before socket hooks
> - conntrack should be confirmed in socket hooks
>
> Comments?
No major objections here, in fact it's actually kind of nice. :-)
I'd like to go over the TCP input changes with a very fine toothed
comb before integration, but that's it.
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: Netfilter socket hooks (was: Re: Status of owner-socketlookup)
2005-05-10 15:59 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) Patrick McHardy
` (7 preceding siblings ...)
2005-05-11 0:04 ` David S. Miller
@ 2005-05-11 23:57 ` James Morris
2005-05-12 0:12 ` Netfilter socket hooks Patrick McHardy
8 siblings, 1 reply; 30+ messages in thread
From: James Morris @ 2005-05-11 23:57 UTC (permalink / raw)
To: Patrick McHardy; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
What about adding an output hook to the table? This would make it much
easier to manage rules.
Something like:
diff -purN -X dontdiff linux-2.6.12-rc4-sk.o/net/ipv4/netfilter/iptable_skfilter.c linux-2.6.12-rc4-sk.w/net/ipv4/netfilter/iptable_skfilter.c
--- linux-2.6.12-rc4-sk.o/net/ipv4/netfilter/iptable_skfilter.c 2005-05-11 18:57:17.000000000 -0400
+++ linux-2.6.12-rc4-sk.w/net/ipv4/netfilter/iptable_skfilter.c 2005-05-11 19:30:44.000000000 -0400
@@ -11,24 +11,26 @@
#include <linux/module.h>
#include <linux/netfilter_ipv4/ip_tables.h>
-#define SKFILTER_VALID_HOOKS ((1 << NF_IP_LOCAL_IN))
+#define SKFILTER_VALID_HOOKS ((1 << NF_IP_LOCAL_IN) | (1 << NF_IP_LOCAL_OUT))
static struct
{
struct ipt_replace repl;
- struct ipt_standard entries[1];
+ struct ipt_standard entries[2];
struct ipt_error term;
} initial_table __initdata = {
.repl = {
.name = "skfilter",
.valid_hooks = SKFILTER_VALID_HOOKS,
- .num_entries = 2,
- .size = sizeof(struct ipt_standard) * 1 + sizeof(struct ipt_error),
+ .num_entries = 3,
+ .size = sizeof(struct ipt_standard) * 2 + sizeof(struct ipt_error),
.hook_entry = {
- [NF_IP_LOCAL_IN] = 0,
+ [NF_IP_LOCAL_IN] = 0,
+ [NF_IP_LOCAL_OUT] = sizeof(struct ipt_standard),
},
.underflow = {
- [NF_IP_LOCAL_IN] = 0,
+ [NF_IP_LOCAL_IN] = 0,
+ [NF_IP_LOCAL_OUT] = sizeof(struct ipt_standard),
},
},
.entries = {
@@ -47,6 +49,21 @@ static struct
.verdict = -NF_ACCEPT - 1,
},
},
+ /* LOCAL_OUT */
+ {
+ .entry = {
+ .target_offset = sizeof(struct ipt_entry),
+ .next_offset = sizeof(struct ipt_standard),
+ },
+ .target = {
+ .target = {
+ .u = {
+ .target_size = IPT_ALIGN(sizeof(struct ipt_standard_target)),
+ },
+ },
+ .verdict = -NF_ACCEPT - 1,
+ },
+ },
},
/* ERROR */
.term = {
@@ -77,12 +94,12 @@ static struct ipt_table skfilter = {
/* The work comes in here from netfilter.c. */
static unsigned int
-ipt_hook(unsigned int hook,
- struct sock *sk,
- struct sk_buff **pskb,
- const struct net_device *in,
- const struct net_device *out,
- int (*okfn)(struct sock *, struct sk_buff *))
+ipt_sk_hook(unsigned int hook,
+ struct sock *sk,
+ struct sk_buff **pskb,
+ const struct net_device *in,
+ const struct net_device *out,
+ int (*okfn)(struct sock *, struct sk_buff *))
{
unsigned int ret;
int pull = 0;
@@ -97,9 +114,19 @@ ipt_hook(unsigned int hook,
return ret;
}
-static struct nf_sk_hook_ops ipt_ops[] = {
+static unsigned int
+ipt_hook(unsigned int hook,
+ struct sk_buff **pskb,
+ const struct net_device *in,
+ const struct net_device *out,
+ int (*okfn)(struct sk_buff *))
+{
+ return ipt_do_table(NULL, pskb, hook, in, out, &skfilter, NULL);
+}
+
+static struct nf_sk_hook_ops ipt_sk_ops[] = {
{
- .hook = ipt_hook,
+ .hook = ipt_sk_hook,
.owner = THIS_MODULE,
.pf = PF_INET,
.hooknum = NF_IP_LOCAL_IN,
@@ -107,6 +134,16 @@ static struct nf_sk_hook_ops ipt_ops[] =
},
};
+static struct nf_hook_ops ipt_ops[] = {
+ {
+ .hook = ipt_hook,
+ .owner = THIS_MODULE,
+ .pf = PF_INET,
+ .hooknum = NF_IP_LOCAL_OUT,
+ .priority = NF_IP_PRI_FILTER,
+ },
+};
+
static int __init init(void)
{
int ret;
@@ -117,12 +154,18 @@ static int __init init(void)
return ret;
/* Register hooks */
- ret = nf_register_sk_hook(&ipt_ops[0]);
+ ret = nf_register_sk_hook(&ipt_sk_ops[0]);
if (ret < 0)
goto cleanup_table;
+ ret = nf_register_hook(&ipt_ops[0]);
+ if (ret < 0)
+ goto cleanup_hook0;
+
return ret;
+ cleanup_hook0:
+ nf_unregister_sk_hook(&ipt_sk_ops[0]);
cleanup_table:
ipt_unregister_table(&skfilter);
@@ -131,7 +174,8 @@ static int __init init(void)
static void __exit fini(void)
{
- nf_unregister_sk_hook(&ipt_ops[0]);
+ nf_unregister_hook(&ipt_ops[0]);
+ nf_unregister_sk_hook(&ipt_sk_ops[0]);
ipt_unregister_table(&skfilter);
}
^ permalink raw reply [flat|nested] 30+ messages in thread* Re: Netfilter socket hooks
2005-05-11 23:57 ` Netfilter socket hooks (was: Re: Status of owner-socketlookup) James Morris
@ 2005-05-12 0:12 ` Patrick McHardy
0 siblings, 0 replies; 30+ messages in thread
From: Patrick McHardy @ 2005-05-12 0:12 UTC (permalink / raw)
To: James Morris; +Cc: juha.heljoranta, Rusty Russell, netfilter-devel
James Morris wrote:
> What about adding an output hook to the table? This would make it much
> easier to manage rules.
Sure. For symetry, I would prefer only to pass packets with
skb->sk != NULL through OUTPUT and use skb->sk as socket argument
to ipt_do_table(). But rule mangement is still tricky since
only protocols which use sockets can be handled in the skfilter
table. A more radical approach would be to use the socket hooks
for filter/INPUT for all protocols with hooks - but I haven't
thought much about this yet.
Regards
Patrick
^ permalink raw reply [flat|nested] 30+ messages in thread