1diff -urN --exclude-from=diff.exclude-raw linux-2.4.18-orig/include/linux/netfilter_ipv6/ip6_tables.h linux-2.4.18-raw/include/linux/netfilter_ipv6/ip6_tables.h
2--- linux-2.4.18-orig/include/linux/netfilter_ipv6/ip6_tables.h	Mon Feb 25 20:38:13 2002
3+++ linux-2.4.18-raw/include/linux/netfilter_ipv6/ip6_tables.h	Wed Jun 12 17:17:45 2002
4@@ -451,5 +451,17 @@
5 
6 #define IP6T_ALIGN(s) (((s) + (__alignof__(struct ip6t_entry)-1)) & ~(__alignof__(struct ip6t_entry)-1))
7 
8+/* Internal packet logging interface */
9+extern void (*ip6t_packet_log_fn)(struct sk_buff **pskb,
10+				  unsigned int hooknum,
11+				  const struct net_device *in,
12+				  const struct net_device *out,
13+				  const char *prefix);
14+
15+extern void ip6t_log_packet(struct sk_buff **pskb,
16+			    unsigned int hooknum,
17+			    const struct net_device *in,
18+			    const struct net_device *out,
19+			    const char *prefix);
20 #endif /*__KERNEL__*/
21 #endif /* _IP6_TABLES_H */
22diff -urN --exclude-from=diff.exclude-raw linux-2.4.18-orig/net/ipv6/netfilter/ip6_tables.c linux-2.4.18-raw/net/ipv6/netfilter/ip6_tables.c
23--- linux-2.4.18-orig/net/ipv6/netfilter/ip6_tables.c	Mon Feb 25 20:38:14 2002
24+++ linux-2.4.18-raw/net/ipv6/netfilter/ip6_tables.c	Tue Jul 23 11:22:03 2002
25@@ -7,6 +7,8 @@
26  * 19 Jan 2002 Harald Welte <laforge@gnumonks.org>
27  * 	- increase module usage count as soon as we have rules inside
28  * 	  a table
29+ * 8  Jun 2002 Jozsef Kadlecsik <kadlec@blackhole.kfki.hu>
30+ *	- packet logging interface added
31  */
32 #include <linux/config.h>
33 #include <linux/skbuff.h>
34@@ -26,6 +28,16 @@
35 
36 #define IPV6_HDR_LEN	(sizeof(struct ipv6hdr))
37 
38+#ifdef CONFIG_IP6_NF_TARGET_TRACE_NEEDED
39+static const char *hook6names[]
40+= { [NF_IP6_PRE_ROUTING]  "PREROUTING",
41+    [NF_IP6_LOCAL_IN]     "INPUT",
42+    [NF_IP6_FORWARD]      "FORWARD",
43+    [NF_IP6_LOCAL_OUT]    "OUTPUT",
44+    [NF_IP6_POST_ROUTING] "POSTROUTING",
45+};
46+#endif
47+
48 /*#define DEBUG_IP_FIREWALL*/
49 /*#define DEBUG_ALLOW_ALL*/ /* Useful for remote debugging */
50 /*#define DEBUG_IP_FIREWALL_USER*/
51@@ -121,6 +133,31 @@
52 #define up(x) do { printk("UP:%u:" #x "\n", __LINE__); up(x); } while(0)
53 #endif
54 
55+/* We rely on the LOG targets */
56+void (*ip6t_packet_log_fn)(struct sk_buff **pskb,
57+			   unsigned int hooknum,
58+			   const struct net_device *in,
59+			   const struct net_device *out,
60+			   const char *prefix) = NULL;
61+
62+void ip6t_log_packet(struct sk_buff **pskb,
63+		     unsigned int hooknum,
64+		     const struct net_device *in,
65+		     const struct net_device *out,
66+		     const char *prefix)
67+{
68+	static unsigned int reported = 0;
69+	
70+	if (ip6t_packet_log_fn == NULL) {
71+		if (!reported) {
72+			printk(KERN_WARNING "ip_tables: can\'t log yet, "
73+			       "no backend logging module loaded in!\n");
74+			reported++;
75+		}
76+	} else
77+		ip6t_packet_log_fn(pskb, hooknum, in, out, prefix);
78+}
79+
80 static int ip6_masked_addrcmp(struct in6_addr addr1, struct in6_addr mask,
81 			      struct in6_addr addr2)
82 {
83@@ -298,6 +335,39 @@
84 	return (struct ip6t_entry *)(base + offset);
85 }
86 
87+static inline int
88+get_chainname_rulenum(struct ip6t_entry *s, struct ip6t_entry *e,
89+		      char **chainname, u_int16_t *rulenum)
90+{
91+	struct ip6t_entry_target *t;
92+	
93+	(*rulenum)++;
94+
95+	if (s == e)
96+		return 1;
97+
98+	t = ip6t_get_target(s);
99+	if (strcmp(t->u.kernel.target->name, IP6T_ERROR_TARGET) == 0) {
100+		*chainname = t->data;
101+		(*rulenum) = 0;
102+	}
103+	
104+	return 0;
105+}
106+
107+/* All zeroes == unconditional rule. */
108+static inline int
109+unconditional(const struct ip6t_ip6 *ipv6)
110+{
111+	unsigned int i;
112+
113+	for (i = 0; i < sizeof(*ipv6); i++)
114+		if (((char *)ipv6)[i])
115+			break;
116+
117+	return (i == sizeof(*ipv6));
118+}
119+
120 /* Returns one of the generic firewall policies, like NF_ACCEPT. */
121 unsigned int
122 ip6t_do_table(struct sk_buff **pskb,
123@@ -372,6 +442,32 @@
124 
125 			t = ip6t_get_target(e);
126 			IP_NF_ASSERT(t->u.kernel.target);
127+#ifdef CONFIG_IP6_NF_TARGET_TRACE_NEEDED
128+			/* The packet traced and the rule isn't an unconditional return/END. */
129+			if (((*pskb)->nfcache & NFC_TRACE)
130+			    && !(e->target_offset == sizeof(struct ip6t_entry)
131+			    	 && (strcmp(t->u.kernel.target->name,
132+				       IP6T_STANDARD_TARGET) == 0)
133+				 && !t->u.kernel.target->target
134+			    	 && ((struct ip6t_standard_target *)t)->verdict < 0
135+			    	 && unconditional(&e->ipv6))) {
136+				/* "TRACE: tablename/chainname/rulenum " */
137+				char prefix[11+2*IP6T_TABLE_MAXNAMELEN+6];
138+				char *chainname = (char *) hook6names[hook];
139+				u_int16_t rulenum = 0;
140+				
141+				IP6T_ENTRY_ITERATE(get_entry(table_base, table->private->hook_entry[hook]),
142+						   table->private->size,
143+						   get_chainname_rulenum,
144+						   e, &chainname, &rulenum);
145+						  
146+				snprintf(prefix, sizeof(prefix), "TRACE: %s/%s/%u ", 
147+					table->name,
148+					chainname, rulenum);
149+
150+				ip6t_log_packet(pskb, hook, in, out, prefix);
151+			}
152+#endif
153 			/* Standard target? */
154 			if (!t->u.kernel.target->target) {
155 				int v;
156@@ -528,19 +624,6 @@
157 	return find_inlist_lock(&ip6t_target, name, "ip6t_", error, mutex);
158 }
159 
160-/* All zeroes == unconditional rule. */
161-static inline int
162-unconditional(const struct ip6t_ip6 *ipv6)
163-{
164-	unsigned int i;
165-
166-	for (i = 0; i < sizeof(*ipv6); i++)
167-		if (((char *)ipv6)[i])
168-			break;
169-
170-	return (i == sizeof(*ipv6));
171-}
172-
173 /* Figures out from what hook each rule can be called: returns 0 if
174    there are loops.  Puts hook bitmask in comefrom. */
175 static int
176@@ -1820,6 +1903,8 @@
177 EXPORT_SYMBOL(ip6t_unregister_match);
178 EXPORT_SYMBOL(ip6t_register_target);
179 EXPORT_SYMBOL(ip6t_unregister_target);
180+EXPORT_SYMBOL(ip6t_packet_log_fn);
181+EXPORT_SYMBOL(ip6t_log_packet);
182 
183 module_init(init);
184 module_exit(fini);
185diff -urN --exclude-from=diff.exclude-raw linux-2.4.18-orig/net/ipv6/netfilter/ip6t_LOG.c linux-2.4.18-raw/net/ipv6/netfilter/ip6t_LOG.c
186--- linux-2.4.18-orig/net/ipv6/netfilter/ip6t_LOG.c	Mon Nov  5 18:53:07 2001
187+++ linux-2.4.18-raw/net/ipv6/netfilter/ip6t_LOG.c	Thu Jun 13 16:07:07 2002
188@@ -266,23 +266,21 @@
189 	}
190 }
191 
192-static unsigned int
193-ip6t_log_target(struct sk_buff **pskb,
194-		unsigned int hooknum,
195-		const struct net_device *in,
196-		const struct net_device *out,
197-		const void *targinfo,
198-		void *userinfo)
199+static void
200+ip6t_log(struct sk_buff **pskb,
201+	 unsigned int hooknum,
202+	 const struct net_device *in,
203+	 const struct net_device *out,
204+	 const struct ip6t_log_info *loginfo,
205+	 const char *level_string,
206+	 const char *prefix)
207 {
208 	struct ipv6hdr *ipv6h = (*pskb)->nh.ipv6h;
209-	const struct ip6t_log_info *loginfo = targinfo;
210-	char level_string[4] = "< >";
211 
212-	level_string[1] = '0' + (loginfo->level % 8);
213 	spin_lock_bh(&log_lock);
214 	printk(level_string);
215 	printk("%sIN=%s OUT=%s ",
216-		loginfo->prefix,
217+		prefix == NULL ? loginfo->prefix : prefix,
218 		in ? in->name : "",
219 		out ? out->name : "");
220 	if (in && !out) {
221@@ -302,10 +300,37 @@
222 	dump_packet(loginfo, ipv6h, 1);
223 	printk("\n");
224 	spin_unlock_bh(&log_lock);
225+}
226+
227+static unsigned int
228+ip6t_log_target(struct sk_buff **pskb,
229+		unsigned int hooknum,
230+		const struct net_device *in,
231+		const struct net_device *out,
232+		const void *targinfo,
233+		void *userinfo)
234+{
235+	const struct ip6t_log_info *loginfo = targinfo;
236+	char level_string[4] = "< >";
237+
238+	level_string[1] = '0' + (loginfo->level % 8);
239+	ip6t_log(pskb, hooknum, in, out, loginfo, level_string, NULL);
240 
241 	return IP6T_CONTINUE;
242 }
243 
244+static void
245+ip6t_log_fn(struct sk_buff **pskb,
246+	    unsigned int hooknum,
247+	    const struct net_device *in,
248+	    const struct net_device *out,
249+	    const char *prefix)
250+{
251+	struct ip6t_log_info loginfo = { 0, IP6T_LOG_MASK, ""};
252+
253+	ip6t_log(pskb, hooknum, in, out, &loginfo, KERN_WARNING, prefix);
254+}
255+
256 static int ip6t_log_checkentry(const char *tablename,
257 			       const struct ip6t_entry *e,
258 			       void *targinfo,
259@@ -343,12 +368,18 @@
260 	if (ip6t_register_target(&ip6t_log_reg))
261 		return -EINVAL;
262 
263+	if (ip6t_packet_log_fn == NULL)
264+		ip6t_packet_log_fn = ip6t_log_fn;
265+
266 	return 0;
267 }
268 
269 static void __exit fini(void)
270 {
271 	ip6t_unregister_target(&ip6t_log_reg);
272+
273+	if (ip6t_packet_log_fn == ip6t_log_fn)	
274+		ip6t_packet_log_fn = NULL;
275 }
276 
277 module_init(init);
278diff -urN --exclude-from=diff.exclude-raw linux-2.4.18-orig/net/ipv6/netfilter/ip6t_TRACE.c linux-2.4.18-raw/net/ipv6/netfilter/ip6t_TRACE.c
279--- linux-2.4.18-orig/net/ipv6/netfilter/ip6t_TRACE.c	Thu Jan  1 01:00:00 1970
280+++ linux-2.4.18-raw/net/ipv6/netfilter/ip6t_TRACE.c	Thu Jun 13 09:39:19 2002
281@@ -0,0 +1,60 @@
282+/* This is a module which is used for setting
283+   the NFC_TRACE flag in the nfcache field of an skb. */
284+#include <linux/module.h>
285+#include <linux/skbuff.h>
286+
287+#include <linux/netfilter_ipv6/ip6_tables.h>
288+
289+MODULE_LICENSE("GPL");
290+
291+static unsigned int
292+target(struct sk_buff **pskb,
293+	unsigned int hooknum,
294+	const struct net_device *in,
295+	const struct net_device *out,
296+	const void *targinfo,
297+	void *userinfo)
298+{
299+	(*pskb)->nfcache |= NFC_TRACE;
300+	return IP6T_CONTINUE;
301+}
302+
303+static int 
304+checkentry(const char *tablename,
305+       	   const struct ip6t_entry *e,
306+           void *targinfo,
307+           unsigned int targinfosize,
308+           unsigned int hook_mask)
309+{
310+	if (targinfosize != 0) {
311+		printk(KERN_WARNING "TRACE: targinfosize %u != 0\n",
312+		       targinfosize);
313+		return 0;
314+	}
315+
316+	if (strcmp(tablename, "raw") != 0) {
317+		printk(KERN_WARNING "TRACE: can only be called from \"raw\" table, not \"%s\"\n", tablename);
318+		return 0;
319+	}
320+
321+	return 1;
322+}
323+
324+static struct ip6t_target ip6t_trace_reg
325+= { { NULL, NULL }, "TRACE", target, checkentry, NULL, THIS_MODULE };
326+
327+static int __init init(void)
328+{
329+	if (ip6t_register_target(&ip6t_trace_reg))
330+		return -EINVAL;
331+
332+	return 0;
333+}
334+
335+static void __exit fini(void)
336+{
337+	ip6t_unregister_target(&ip6t_trace_reg);
338+}
339+
340+module_init(init);
341+module_exit(fini);
342diff -urN --exclude-from=diff.exclude-raw linux-2.4.18-orig/net/ipv6/netfilter/ip6table_raw.c linux-2.4.18-raw/net/ipv6/netfilter/ip6table_raw.c
343--- linux-2.4.18-orig/net/ipv6/netfilter/ip6table_raw.c	Thu Jan  1 01:00:00 1970
344+++ linux-2.4.18-raw/net/ipv6/netfilter/ip6table_raw.c	Thu Jun 13 09:38:08 2002
345@@ -0,0 +1,139 @@
346+/*
347+ * IPv6 raw table, a port of the IPv4 raw table to IPv6
348+ *
349+ */
350+#include <linux/module.h>
351+#include <linux/netfilter_ipv6/ip6_tables.h>
352+
353+#define RAW_VALID_HOOKS ((1 << NF_IP6_PRE_ROUTING) | (1 << NF_IP6_LOCAL_OUT))
354+
355+#if 0
356+#define DEBUGP(x, args...)	printk(KERN_DEBUG x, ## args)
357+#else
358+#define DEBUGP(x, args...)
359+#endif
360+
361+/* Standard entry. */
362+struct ip6t_standard
363+{
364+	struct ip6t_entry entry;
365+	struct ip6t_standard_target target;
366+};
367+
368+struct ip6t_error_target
369+{
370+	struct ip6t_entry_target target;
371+	char errorname[IP6T_FUNCTION_MAXNAMELEN];
372+};
373+
374+struct ip6t_error
375+{
376+	struct ip6t_entry entry;
377+	struct ip6t_error_target target;
378+};
379+
380+static struct
381+{
382+	struct ip6t_replace repl;
383+	struct ip6t_standard entries[2];
384+	struct ip6t_error term;
385+} initial_table __initdata
386+= { { "raw", RAW_VALID_HOOKS, 3,
387+      sizeof(struct ip6t_standard) * 2 + sizeof(struct ip6t_error),
388+      { [NF_IP6_PRE_ROUTING] 	0,
389+	[NF_IP6_LOCAL_OUT]	sizeof(struct ip6t_standard) },
390+      { [NF_IP6_PRE_ROUTING] 	0,
391+	[NF_IP6_LOCAL_OUT]	sizeof(struct ip6t_standard) },
392+      0, NULL, { } },
393+    {
394+	    /* PRE_ROUTING */
395+            { { { { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, "", "", { 0 }, { 0 }, 0, 0, 0 },
396+		0,
397+		sizeof(struct ip6t_entry),
398+		sizeof(struct ip6t_standard),
399+		0, { 0, 0 }, { } },
400+	      { { { { IP6T_ALIGN(sizeof(struct ip6t_standard_target)), "" } }, { } },
401+		-NF_ACCEPT - 1 } },
402+	    /* LOCAL_OUT */
403+            { { { { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, "", "", { 0 }, { 0 }, 0, 0, 0 },
404+		0,
405+		sizeof(struct ip6t_entry),
406+		sizeof(struct ip6t_standard),
407+		0, { 0, 0 }, { } },
408+	      { { { { IP6T_ALIGN(sizeof(struct ip6t_standard_target)), "" } }, { } },
409+		-NF_ACCEPT - 1 } },
410+    },
411+    /* ERROR */
412+    { { { { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, { { { 0 } } }, "", "", { 0 }, { 0 }, 0, 0, 0 },
413+	0,
414+	sizeof(struct ip6t_entry),
415+	sizeof(struct ip6t_error),
416+	0, { 0, 0 }, { } },
417+      { { { { IP6T_ALIGN(sizeof(struct ip6t_error_target)), IP6T_ERROR_TARGET } },
418+	  { } },
419+	"ERROR"
420+      }
421+    }
422+};
423+
424+static struct ip6t_table packet_raw
425+= { { NULL, NULL }, "raw", &initial_table.repl,
426+    RAW_VALID_HOOKS, RW_LOCK_UNLOCKED, NULL, THIS_MODULE };
427+
428+/* The work comes in here from netfilter.c. */
429+static unsigned int
430+ip6t_hook(unsigned int hook,
431+	 struct sk_buff **pskb,
432+	 const struct net_device *in,
433+	 const struct net_device *out,
434+	 int (*okfn)(struct sk_buff *))
435+{
436+	return ip6t_do_table(pskb, hook, in, out, &packet_raw, NULL);
437+}
438+
439+static struct nf_hook_ops ip6t_ops[]
440+= { { { NULL, NULL }, ip6t_hook, PF_INET6, NF_IP6_PRE_ROUTING,  NF_IP6_PRI_FIRST },
441+    { { NULL, NULL }, ip6t_hook, PF_INET6, NF_IP6_LOCAL_OUT,    NF_IP6_PRI_FIRST }
442+};
443+
444+static int __init init(void)
445+{
446+	int ret;
447+
448+	/* Register table */
449+	ret = ip6t_register_table(&packet_raw);
450+	if (ret < 0)
451+		return ret;
452+
453+	/* Register hooks */
454+	ret = nf_register_hook(&ip6t_ops[0]);
455+	if (ret < 0)
456+		goto cleanup_table;
457+
458+	ret = nf_register_hook(&ip6t_ops[1]);
459+	if (ret < 0)
460+		goto cleanup_hook0;
461+
462+	return ret;
463+
464+ cleanup_hook0:
465+	nf_unregister_hook(&ip6t_ops[0]);
466+ cleanup_table:
467+	ip6t_unregister_table(&packet_raw);
468+
469+	return ret;
470+}
471+
472+static void __exit fini(void)
473+{
474+	unsigned int i;
475+
476+	for (i = 0; i < sizeof(ip6t_ops)/sizeof(struct nf_hook_ops); i++)
477+		nf_unregister_hook(&ip6t_ops[i]);
478+
479+	ip6t_unregister_table(&packet_raw);
480+}
481+
482+module_init(init);
483+module_exit(fini);
484+MODULE_LICENSE("GPL");
485