netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* pull request (net-next): ipsec-next 2015-10-30
@ 2015-10-30  6:16 Steffen Klassert
  2015-10-30  6:16 ` [PATCH 1/5] xfrm: Let the flowcache handle its size by default Steffen Klassert
                   ` (5 more replies)
  0 siblings, 6 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

1) The flow cache is limited by the flow cache limit which
   depends on the number of cpus and the xfrm garbage collector
   threshold which is independent of the number of cpus. This
   leads to the fact that on systems with more than 16 cpus
   we hit the xfrm garbage collector limit and refuse new
   allocations, so new flows are dropped. On systems with 16
   or less cpus, we hit the flowcache limit. In this case, we
   shrink the flow cache instead of refusing new flows. 

   We increase the xfrm garbage collector threshold to INT_MAX
   to get the same behaviour, independent of the number of cpus.

2) Fix some unaligned accesses on sparc systems.
   From Sowmini Varadhan.

3) Fix some header checks in _decode_session4. We may call
   pskb_may_pull with a negative value converted to unsigened
   int from pskb_may_pull. This can lead to incorrect policy
   lookups. We fix this by a check of the data pointer position
   before we call pskb_may_pull.

4) Reload skb header pointers after calling pskb_may_pull
   in _decode_session4 as this may change the pointers into
   the packet. 

5) Add a missing statistic counter on inner mode errors.

Please pull or let me know if there are problems.

Thanks!

The following changes since commit 8a4683a5e06efda7e1f327213678d4dcafc0d894:

  net: help compiler generate better code in eth_get_headlen (2015-09-28 22:51:15 -0700)

are available in the git repository at:

  git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec-next.git master

for you to fetch changes up to cb866e3298cd7412503fc7e2c265753c853fab9d:

  xfrm: Increment statistic counter on inner mode error (2015-10-23 07:52:58 +0200)

----------------------------------------------------------------
Sowmini Varadhan (1):
      xfrm: Fix unaligned access to stats in copy_to_user_state()

Steffen Klassert (4):
      xfrm: Let the flowcache handle its size by default.
      xfrm4: Fix header checks in _decode_session4.
      xfrm4: Reload skb header pointers after calling pskb_may_pull.
      xfrm: Increment statistic counter on inner mode error

 Documentation/networking/ip-sysctl.txt |  6 ++--
 net/ipv4/xfrm4_policy.c                | 50 +++++++++++++++++++++++++---------
 net/ipv6/xfrm6_policy.c                |  2 +-
 net/xfrm/xfrm_input.c                  |  4 ++-
 net/xfrm/xfrm_user.c                   |  5 +++-
 5 files changed, 49 insertions(+), 18 deletions(-)

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH 1/5] xfrm: Let the flowcache handle its size by default.
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
@ 2015-10-30  6:16 ` Steffen Klassert
  2015-10-30  6:16 ` [PATCH 2/5] xfrm: Fix unaligned access to stats in copy_to_user_state() Steffen Klassert
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

The xfrm flowcache size is limited by the flowcache limit
(4096 * number of online cpus) and the xfrm garbage collector
threshold (2 * 32768), whatever is reached first. This means
that we can hit the garbage collector limit only on systems
with more than 16 cpus. On such systems we simply refuse
new allocations if we reach the limit, so new flows are dropped.
On syslems with 16 or less cpus, we hit the flowcache limit.
In this case, we shrink the flow cache instead of refusing new
flows.

We increase the xfrm garbage collector threshold to INT_MAX
to get the same behaviour, independent of the number of cpus.

The xfrm garbage collector threshold can still be set below
the flowcache limit to reduce the memory usage of the flowcache.

Tested-by: Dan Streetman <dan.streetman@canonical.com>
Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 Documentation/networking/ip-sysctl.txt | 6 ++++--
 net/ipv4/xfrm4_policy.c                | 2 +-
 net/ipv6/xfrm6_policy.c                | 2 +-
 3 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt
index ebe94f2..260f30b 100644
--- a/Documentation/networking/ip-sysctl.txt
+++ b/Documentation/networking/ip-sysctl.txt
@@ -1199,7 +1199,8 @@ tag - INTEGER
 xfrm4_gc_thresh - INTEGER
 	The threshold at which we will start garbage collecting for IPv4
 	destination cache entries.  At twice this value the system will
-	refuse new allocations.
+	refuse new allocations. The value must be set below the flowcache
+	limit (4096 * number of online cpus) to take effect.
 
 igmp_link_local_mcast_reports - BOOLEAN
 	Enable IGMP reports for link local multicast groups in the
@@ -1645,7 +1646,8 @@ ratelimit - INTEGER
 xfrm6_gc_thresh - INTEGER
 	The threshold at which we will start garbage collecting for IPv6
 	destination cache entries.  At twice this value the system will
-	refuse new allocations.
+	refuse new allocations. The value must be set below the flowcache
+	limit (4096 * number of online cpus) to take effect.
 
 
 IPv6 Update by:
diff --git a/net/ipv4/xfrm4_policy.c b/net/ipv4/xfrm4_policy.c
index 0304d16..75e8d48 100644
--- a/net/ipv4/xfrm4_policy.c
+++ b/net/ipv4/xfrm4_policy.c
@@ -246,7 +246,7 @@ static struct dst_ops xfrm4_dst_ops = {
 	.destroy =		xfrm4_dst_destroy,
 	.ifdown =		xfrm4_dst_ifdown,
 	.local_out =		__ip_local_out,
-	.gc_thresh =		32768,
+	.gc_thresh =		INT_MAX,
 };
 
 static struct xfrm_policy_afinfo xfrm4_policy_afinfo = {
diff --git a/net/ipv6/xfrm6_policy.c b/net/ipv6/xfrm6_policy.c
index 30caa28..2fad593 100644
--- a/net/ipv6/xfrm6_policy.c
+++ b/net/ipv6/xfrm6_policy.c
@@ -287,7 +287,7 @@ static struct dst_ops xfrm6_dst_ops = {
 	.destroy =		xfrm6_dst_destroy,
 	.ifdown =		xfrm6_dst_ifdown,
 	.local_out =		__ip6_local_out,
-	.gc_thresh =		32768,
+	.gc_thresh =		INT_MAX,
 };
 
 static struct xfrm_policy_afinfo xfrm6_policy_afinfo = {
-- 
1.9.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH 2/5] xfrm: Fix unaligned access to stats in copy_to_user_state()
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
  2015-10-30  6:16 ` [PATCH 1/5] xfrm: Let the flowcache handle its size by default Steffen Klassert
@ 2015-10-30  6:16 ` Steffen Klassert
  2015-10-30  6:16 ` [PATCH 3/5] xfrm4: Fix header checks in _decode_session4 Steffen Klassert
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

From: Sowmini Varadhan <sowmini.varadhan@oracle.com>

On sparc, deleting established SAs (e.g., by restarting ipsec)
results in unaligned access messages via xfrm_del_sa ->
km_state_notify -> xfrm_send_state_notify().

Even though struct xfrm_usersa_info is aligned on 8-byte boundaries,
netlink attributes are fundamentally only 4 byte aligned, and this
cannot be changed for nla_data() that is passed up to userspace.
As a result, the put_unaligned() macro needs to be used to
set up potentially unaligned fields such as the xfrm_stats in
copy_to_user_state()

Signed-off-by: Sowmini Varadhan <sowmini.varadhan@oracle.com>
Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 net/xfrm/xfrm_user.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/net/xfrm/xfrm_user.c b/net/xfrm/xfrm_user.c
index a8de9e3..639e0d5 100644
--- a/net/xfrm/xfrm_user.c
+++ b/net/xfrm/xfrm_user.c
@@ -31,6 +31,7 @@
 #if IS_ENABLED(CONFIG_IPV6)
 #include <linux/in6.h>
 #endif
+#include <asm/unaligned.h>
 
 static int verify_one_alg(struct nlattr **attrs, enum xfrm_attr_type_t type)
 {
@@ -728,7 +729,9 @@ static void copy_to_user_state(struct xfrm_state *x, struct xfrm_usersa_info *p)
 	memcpy(&p->sel, &x->sel, sizeof(p->sel));
 	memcpy(&p->lft, &x->lft, sizeof(p->lft));
 	memcpy(&p->curlft, &x->curlft, sizeof(p->curlft));
-	memcpy(&p->stats, &x->stats, sizeof(p->stats));
+	put_unaligned(x->stats.replay_window, &p->stats.replay_window);
+	put_unaligned(x->stats.replay, &p->stats.replay);
+	put_unaligned(x->stats.integrity_failed, &p->stats.integrity_failed);
 	memcpy(&p->saddr, &x->props.saddr, sizeof(p->saddr));
 	p->mode = x->props.mode;
 	p->replay_window = x->props.replay_window;
-- 
1.9.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH 3/5] xfrm4: Fix header checks in _decode_session4.
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
  2015-10-30  6:16 ` [PATCH 1/5] xfrm: Let the flowcache handle its size by default Steffen Klassert
  2015-10-30  6:16 ` [PATCH 2/5] xfrm: Fix unaligned access to stats in copy_to_user_state() Steffen Klassert
@ 2015-10-30  6:16 ` Steffen Klassert
  2015-10-30  6:16 ` [PATCH 4/5] xfrm4: Reload skb header pointers after calling pskb_may_pull Steffen Klassert
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

We skip the header informations if the data pointer points
already behind the header in question for some protocols.
This is because we call pskb_may_pull with a negative value
converted to unsigened int from pskb_may_pull in this case.
Skipping the header informations can lead to incorrect policy
lookups, so fix it by a check of the data pointer position
before we call pskb_may_pull.

Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 net/ipv4/xfrm4_policy.c | 15 ++++++++++-----
 1 file changed, 10 insertions(+), 5 deletions(-)

diff --git a/net/ipv4/xfrm4_policy.c b/net/ipv4/xfrm4_policy.c
index 75e8d48..e4d533c 100644
--- a/net/ipv4/xfrm4_policy.c
+++ b/net/ipv4/xfrm4_policy.c
@@ -137,7 +137,8 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 			break;
 
 		case IPPROTO_ICMP:
-			if (pskb_may_pull(skb, xprth + 2 - skb->data)) {
+			if (xprth + 2 < skb->data ||
+			    pskb_may_pull(skb, xprth + 2 - skb->data)) {
 				u8 *icmp = xprth;
 
 				fl4->fl4_icmp_type = icmp[0];
@@ -146,7 +147,8 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 			break;
 
 		case IPPROTO_ESP:
-			if (pskb_may_pull(skb, xprth + 4 - skb->data)) {
+			if (xprth + 4 < skb->data ||
+			    pskb_may_pull(skb, xprth + 4 - skb->data)) {
 				__be32 *ehdr = (__be32 *)xprth;
 
 				fl4->fl4_ipsec_spi = ehdr[0];
@@ -154,7 +156,8 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 			break;
 
 		case IPPROTO_AH:
-			if (pskb_may_pull(skb, xprth + 8 - skb->data)) {
+			if (xprth + 8 < skb->data ||
+			    pskb_may_pull(skb, xprth + 8 - skb->data)) {
 				__be32 *ah_hdr = (__be32 *)xprth;
 
 				fl4->fl4_ipsec_spi = ah_hdr[1];
@@ -162,7 +165,8 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 			break;
 
 		case IPPROTO_COMP:
-			if (pskb_may_pull(skb, xprth + 4 - skb->data)) {
+			if (xprth + 4 < skb->data ||
+			    pskb_may_pull(skb, xprth + 4 - skb->data)) {
 				__be16 *ipcomp_hdr = (__be16 *)xprth;
 
 				fl4->fl4_ipsec_spi = htonl(ntohs(ipcomp_hdr[1]));
@@ -170,7 +174,8 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 			break;
 
 		case IPPROTO_GRE:
-			if (pskb_may_pull(skb, xprth + 12 - skb->data)) {
+			if (xprth + 12 < skb->data ||
+			    pskb_may_pull(skb, xprth + 12 - skb->data)) {
 				__be16 *greflags = (__be16 *)xprth;
 				__be32 *gre_hdr = (__be32 *)xprth;
 
-- 
1.9.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH 4/5] xfrm4: Reload skb header pointers after calling pskb_may_pull.
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
                   ` (2 preceding siblings ...)
  2015-10-30  6:16 ` [PATCH 3/5] xfrm4: Fix header checks in _decode_session4 Steffen Klassert
@ 2015-10-30  6:16 ` Steffen Klassert
  2015-10-30  6:16 ` [PATCH 5/5] xfrm: Increment statistic counter on inner mode error Steffen Klassert
  2015-10-30 11:53 ` pull request (net-next): ipsec-next 2015-10-30 David Miller
  5 siblings, 0 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

A call to pskb_may_pull may change the pointers into the packet,
so reload the pointers after the call.

Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 net/ipv4/xfrm4_policy.c | 33 ++++++++++++++++++++++++++-------
 1 file changed, 26 insertions(+), 7 deletions(-)

diff --git a/net/ipv4/xfrm4_policy.c b/net/ipv4/xfrm4_policy.c
index e4d533c..269b137 100644
--- a/net/ipv4/xfrm4_policy.c
+++ b/net/ipv4/xfrm4_policy.c
@@ -129,7 +129,10 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_DCCP:
 			if (xprth + 4 < skb->data ||
 			    pskb_may_pull(skb, xprth + 4 - skb->data)) {
-				__be16 *ports = (__be16 *)xprth;
+				__be16 *ports;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				ports = (__be16 *)xprth;
 
 				fl4->fl4_sport = ports[!!reverse];
 				fl4->fl4_dport = ports[!reverse];
@@ -139,7 +142,10 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_ICMP:
 			if (xprth + 2 < skb->data ||
 			    pskb_may_pull(skb, xprth + 2 - skb->data)) {
-				u8 *icmp = xprth;
+				u8 *icmp;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				icmp = xprth;
 
 				fl4->fl4_icmp_type = icmp[0];
 				fl4->fl4_icmp_code = icmp[1];
@@ -149,7 +155,10 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_ESP:
 			if (xprth + 4 < skb->data ||
 			    pskb_may_pull(skb, xprth + 4 - skb->data)) {
-				__be32 *ehdr = (__be32 *)xprth;
+				__be32 *ehdr;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				ehdr = (__be32 *)xprth;
 
 				fl4->fl4_ipsec_spi = ehdr[0];
 			}
@@ -158,7 +167,10 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_AH:
 			if (xprth + 8 < skb->data ||
 			    pskb_may_pull(skb, xprth + 8 - skb->data)) {
-				__be32 *ah_hdr = (__be32 *)xprth;
+				__be32 *ah_hdr;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				ah_hdr = (__be32 *)xprth;
 
 				fl4->fl4_ipsec_spi = ah_hdr[1];
 			}
@@ -167,7 +179,10 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_COMP:
 			if (xprth + 4 < skb->data ||
 			    pskb_may_pull(skb, xprth + 4 - skb->data)) {
-				__be16 *ipcomp_hdr = (__be16 *)xprth;
+				__be16 *ipcomp_hdr;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				ipcomp_hdr = (__be16 *)xprth;
 
 				fl4->fl4_ipsec_spi = htonl(ntohs(ipcomp_hdr[1]));
 			}
@@ -176,8 +191,12 @@ _decode_session4(struct sk_buff *skb, struct flowi *fl, int reverse)
 		case IPPROTO_GRE:
 			if (xprth + 12 < skb->data ||
 			    pskb_may_pull(skb, xprth + 12 - skb->data)) {
-				__be16 *greflags = (__be16 *)xprth;
-				__be32 *gre_hdr = (__be32 *)xprth;
+				__be16 *greflags;
+				__be32 *gre_hdr;
+
+				xprth = skb_network_header(skb) + iph->ihl * 4;
+				greflags = (__be16 *)xprth;
+				gre_hdr = (__be32 *)xprth;
 
 				if (greflags[0] & GRE_KEY) {
 					if (greflags[0] & GRE_CSUM)
-- 
1.9.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH 5/5] xfrm: Increment statistic counter on inner mode error
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
                   ` (3 preceding siblings ...)
  2015-10-30  6:16 ` [PATCH 4/5] xfrm4: Reload skb header pointers after calling pskb_may_pull Steffen Klassert
@ 2015-10-30  6:16 ` Steffen Klassert
  2015-10-30 11:53 ` pull request (net-next): ipsec-next 2015-10-30 David Miller
  5 siblings, 0 replies; 7+ messages in thread
From: Steffen Klassert @ 2015-10-30  6:16 UTC (permalink / raw)
  To: David Miller; +Cc: Herbert Xu, Steffen Klassert, netdev

Increment the LINUX_MIB_XFRMINSTATEMODEERROR statistic counter
to notify about dropped packets if we fail to fetch a inner mode.

Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 net/xfrm/xfrm_input.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/net/xfrm/xfrm_input.c b/net/xfrm/xfrm_input.c
index 60ce701..ad7f5b3 100644
--- a/net/xfrm/xfrm_input.c
+++ b/net/xfrm/xfrm_input.c
@@ -330,8 +330,10 @@ resume:
 
 		if (x->sel.family == AF_UNSPEC) {
 			inner_mode = xfrm_ip2inner_mode(x, XFRM_MODE_SKB_CB(skb)->protocol);
-			if (inner_mode == NULL)
+			if (inner_mode == NULL) {
+				XFRM_INC_STATS(net, LINUX_MIB_XFRMINSTATEMODEERROR);
 				goto drop;
+			}
 		}
 
 		if (inner_mode->input(x, skb)) {
-- 
1.9.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* Re: pull request (net-next): ipsec-next 2015-10-30
  2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
                   ` (4 preceding siblings ...)
  2015-10-30  6:16 ` [PATCH 5/5] xfrm: Increment statistic counter on inner mode error Steffen Klassert
@ 2015-10-30 11:53 ` David Miller
  5 siblings, 0 replies; 7+ messages in thread
From: David Miller @ 2015-10-30 11:53 UTC (permalink / raw)
  To: steffen.klassert; +Cc: herbert, netdev

From: Steffen Klassert <steffen.klassert@secunet.com>
Date: Fri, 30 Oct 2015 07:16:25 +0100

> 1) The flow cache is limited by the flow cache limit which
>    depends on the number of cpus and the xfrm garbage collector
>    threshold which is independent of the number of cpus. This
>    leads to the fact that on systems with more than 16 cpus
>    we hit the xfrm garbage collector limit and refuse new
>    allocations, so new flows are dropped. On systems with 16
>    or less cpus, we hit the flowcache limit. In this case, we
>    shrink the flow cache instead of refusing new flows. 
> 
>    We increase the xfrm garbage collector threshold to INT_MAX
>    to get the same behaviour, independent of the number of cpus.
> 
> 2) Fix some unaligned accesses on sparc systems.
>    From Sowmini Varadhan.
> 
> 3) Fix some header checks in _decode_session4. We may call
>    pskb_may_pull with a negative value converted to unsigened
>    int from pskb_may_pull. This can lead to incorrect policy
>    lookups. We fix this by a check of the data pointer position
>    before we call pskb_may_pull.
> 
> 4) Reload skb header pointers after calling pskb_may_pull
>    in _decode_session4 as this may change the pointers into
>    the packet. 
> 
> 5) Add a missing statistic counter on inner mode errors.
> 
> Please pull or let me know if there are problems.
 ...
>   git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec-next.git master

Pulled, thanks a lot Steffen!

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2015-10-30 11:53 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-10-30  6:16 pull request (net-next): ipsec-next 2015-10-30 Steffen Klassert
2015-10-30  6:16 ` [PATCH 1/5] xfrm: Let the flowcache handle its size by default Steffen Klassert
2015-10-30  6:16 ` [PATCH 2/5] xfrm: Fix unaligned access to stats in copy_to_user_state() Steffen Klassert
2015-10-30  6:16 ` [PATCH 3/5] xfrm4: Fix header checks in _decode_session4 Steffen Klassert
2015-10-30  6:16 ` [PATCH 4/5] xfrm4: Reload skb header pointers after calling pskb_may_pull Steffen Klassert
2015-10-30  6:16 ` [PATCH 5/5] xfrm: Increment statistic counter on inner mode error Steffen Klassert
2015-10-30 11:53 ` pull request (net-next): ipsec-next 2015-10-30 David Miller

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).