* Re: [PATCH 3/6] new pcmcia IDs for hostap - NETGEAR MA701
From: Jeff Garzik @ 2006-05-16 14:38 UTC (permalink / raw)
To: Marcin Juszkiewicz; +Cc: netdev, Jouni Malinen, Pavel Roskin
In-Reply-To: <200605161621.22459.linux-arm@hrw.one.pl>
Marcin Juszkiewicz wrote:
> One more Prism2 card which works with HostAP.
Please roll these into a single patch. There's no need to split it up
such that there is one ID per patch.
Jeff
^ permalink raw reply
* Re: [PATCH 3/6] new pcmcia IDs for hostap - NETGEAR MA701
From: Marcin Juszkiewicz @ 2006-05-16 14:48 UTC (permalink / raw)
To: Jeff Garzik; +Cc: netdev, Jouni Malinen, Pavel Roskin
In-Reply-To: <4469E3F6.5070302@garzik.org>
Dnia wtorek, 16 maja 2006 16:38, Jeff Garzik napisał:
> Marcin Juszkiewicz wrote:
> > One more Prism2 card which works with HostAP.
>
> Please roll these into a single patch. There's no need to split it up
> such that there is one ID per patch.
Index: netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c
===================================================================
--- netdev-2.6.orig/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:27.469628352 +0200
+++ netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:48.882373120 +0200
@@ -881,6 +881,21 @@
PCMCIA_DEVICE_PROD_ID12(
"ZoomAir 11Mbps High", "Rate wireless Networking",
0x273fe3db, 0x32a1eaee),
+ PCMCIA_DEVICE_PROD_ID1234("ASUS", "802_11B_CF_CARD_25", "Version 01.00", "",
+ 0x78fc06ee, 0x45a50c1e, 0xa57adb8c, 0x00000000),
+ PCMCIA_DEVICE_PROD_ID12("D-Link", "DCF-660W",
+ 0x1a424a1c, 0xe78b6dcc),
+ PCMCIA_DEVICE_PROD_ID12("NETGEAR", "MA701 Wireless CF Card",
+ 0x9aa79dc3, 0xd9ec98e),
+ PCMCIA_DEVICE_PROD_ID12("PLANEX COMMUNICATION INC",
+ "PLANEX GW-CF11X Wireless CF Card",
+ 0x4703cf68, 0xfad7318d),
+ PCMCIA_DEVICE_PROD_ID123(
+ "Pretec", "CompactWLAN Card 802.11b", "2.5",
+ 0x1cadd3e5, 0xe697636c, 0x7a5bfcf1),
+ PCMCIA_DEVICE_PROD_ID1234(
+ "U.S. Robotics", "IEEE 802.11b PC-CARD", "Version 01.02", ""
+ 0xc7b8df9d, 0x1700d087, 0x4b74baa0, 0x00000000),
PCMCIA_DEVICE_NULL
};
MODULE_DEVICE_TABLE(pcmcia, hostap_cs_ids);
--
JID: hrw-jabber.org
Sharp Zaurus C-760 (OZ 3.5.x)
OpenEmbedded/OpenZaurus/OPIE developer
If it works, don't fix it.
-- Sam Rayburn
^ permalink raw reply
* Re: [PATCH 3/6] new pcmcia IDs for hostap - NETGEAR MA701
From: Jeff Garzik @ 2006-05-16 15:01 UTC (permalink / raw)
To: Marcin Juszkiewicz; +Cc: netdev, Jouni Malinen, Pavel Roskin
In-Reply-To: <200605161648.57356.linux-arm@hrw.one.pl>
Marcin Juszkiewicz wrote:
> Dnia wtorek, 16 maja 2006 16:38, Jeff Garzik napisał:
>> Marcin Juszkiewicz wrote:
>>> One more Prism2 card which works with HostAP.
>> Please roll these into a single patch. There's no need to split it up
>> such that there is one ID per patch.
>
> Index: netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c
> ===================================================================
> --- netdev-2.6.orig/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:27.469628352 +0200
> +++ netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:48.882373120 +0200
Thanks, but you violated rules #6, #5, and #2 of
http://linux.yyz.us/patch-format.html
Also, make sure to CC John Linville, as he's the one who will actually
be applying your patch.
Regards,
Jeff
^ permalink raw reply
* Re: [RFC] changing value of NETDEV_ALIGN to cacheline size
From: Christian Borntraeger @ 2006-05-16 15:16 UTC (permalink / raw)
To: David S. Miller; +Cc: rick.jones2, rdunlap, netdev
In-Reply-To: <20060515.154955.114682456.davem@davemloft.net>
On Tuesday 16 May 2006 00:49, David S. Miller wrote:
> From: Rick Jones <rick.jones2@hp.com>
> Date: Mon, 15 May 2006 14:39:23 -0700
>
> > How about:
>
> How about, just leave it alone? :-)
Agreed. Currently it only makes a difference with slab debugging, which hurts
performance no matter what we do.
--
Mit freundlichen Grüßen / Best Regards
Christian Borntraeger
Linux Software Engineer zSeries Linux & Virtualization
^ permalink raw reply
* Re: [PATCH 3/6] new pcmcia IDs for hostap
From: Marcin Juszkiewicz @ 2006-05-16 15:24 UTC (permalink / raw)
To: netdev; +Cc: Jeff Garzik, Jouni Malinen, Pavel Roskin, John W. Linville
In-Reply-To: <4469E3F6.5070302@garzik.org>
Dnia wtorek, 16 maja 2006 16:38, Jeff Garzik napisał:
> Marcin Juszkiewicz wrote:
> > One more Prism2 card which works with HostAP.
> Please roll these into a single patch. There's no need to split it up
> such that there is one ID per patch.
Here's another card that would benefit from a hostap driver:
Platform: HP Ipaq hx4700 running 2.6.16-hh
root@ipaq-pxa270:~# pccardctl ident
Socket 0:
product info: "ASUS", "802_11B_CF_CARD_25", "Version 01.00", ""
manfid: 0x02aa, 0x0002
function: 6 (network)
==========================================================================
I use D-Link DCF-660W card with WPA protected network. By default
orinoco_cs was loaded for my card so I was not able to connect. This patch
make my card working with hostap_cs (like it was when I used pcmcia-cs).
Card was used with hostap_cs during last year in two Zaurus models (2.4.18
on one and 2.6.11 - 2.6.16 on another).
Platform: Sharp Zaurus C760 running 2.6.16 and pcmciautils 013.
root@c7x0:~# pccardctl ident
Socket 0:
product info: "D-Link", "DCF-660W", "", ""
manfid: 0xd601, 0x0005
function: 6 (network)
==========================================================================
One more Prism2 card which works with HostAP.
Platform: Sharp Zaurus SL-5500 running 2.4.18 + hostap_cs 0.4.7
root@collie:~# cardctl ident
Socket 0:
product info: "NETGEAR", "MA701 Wireless CF Card", ""
manfid: 0xd601, 0x0002
function: 6 (network)
==========================================================================
Platform: Sharp Zaurus SL-C3100 running 2.6.16 + pcmciautils 013
root@spitz:~# pccardctl ident
Socket 0:
product info: "HITACHI", "microdrive", "", ""
manfid: 0x0319, 0x0000
function: 4 (fixed disk)
Socket 1:
product info:"PLANEX COMMUNICATION INC","PLANEX GW-CF11X Wireless CF Card", "", ""
manfid: 0xd601, 0x0010
function: 6 ( network )
==========================================================================
From: Jochen Friedrich
Yet another card known to work OK with hostap_cs:
# pccardctl ident
Socket 0:
no product info available
Socket 1:
product info: "U.S. Robotics", "IEEE 802.11b PC-CARD", "Version 01.02", ""
manfid: 0x0156, 0x0002
function: 6 (network)
==========================================================================
Signed-off-by: Marcin Juszkiewicz <openembedded@hrw.one.pl>
drivers/net/wireless/hostap/hostap_cs.c | 15 +++++++++++++++
1 file changed, 15 insertions(+)
Index: netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c
===================================================================
--- netdev-2.6.orig/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:27.469628352 +0200
+++ netdev-2.6/drivers/net/wireless/hostap/hostap_cs.c 2006-05-16 16:47:48.882373120 +0200
@@ -881,6 +881,21 @@
PCMCIA_DEVICE_PROD_ID12(
"ZoomAir 11Mbps High", "Rate wireless Networking",
0x273fe3db, 0x32a1eaee),
+ PCMCIA_DEVICE_PROD_ID1234("ASUS", "802_11B_CF_CARD_25", "Version 01.00", "",
+ 0x78fc06ee, 0x45a50c1e, 0xa57adb8c, 0x00000000),
+ PCMCIA_DEVICE_PROD_ID12("D-Link", "DCF-660W",
+ 0x1a424a1c, 0xe78b6dcc),
+ PCMCIA_DEVICE_PROD_ID12("NETGEAR", "MA701 Wireless CF Card",
+ 0x9aa79dc3, 0xd9ec98e),
+ PCMCIA_DEVICE_PROD_ID12("PLANEX COMMUNICATION INC",
+ "PLANEX GW-CF11X Wireless CF Card",
+ 0x4703cf68, 0xfad7318d),
+ PCMCIA_DEVICE_PROD_ID123(
+ "Pretec", "CompactWLAN Card 802.11b", "2.5",
+ 0x1cadd3e5, 0xe697636c, 0x7a5bfcf1),
+ PCMCIA_DEVICE_PROD_ID1234(
+ "U.S. Robotics", "IEEE 802.11b PC-CARD", "Version 01.02", ""
+ 0xc7b8df9d, 0x1700d087, 0x4b74baa0, 0x00000000),
PCMCIA_DEVICE_NULL
};
MODULE_DEVICE_TABLE(pcmcia, hostap_cs_ids);
--
JID: hrw-jabber.org
Sharp Zaurus C-760 (OZ 3.5.x)
OpenEmbedded/OpenZaurus/OPIE developer
"To be or not to be that is the question.":
every programmer knows the answer $2b or (not $2b) is $ff.
^ permalink raw reply
* [-mm patch] drivers/net/s2io.c: make bus_speed[] static
From: Adrian Bunk @ 2006-05-16 15:30 UTC (permalink / raw)
To: Andrew Morton, Ananda Raju, jgarzik; +Cc: linux-kernel, netdev
In-Reply-To: <20060515005637.00b54560.akpm@osdl.org>
On Mon, May 15, 2006 at 12:56:37AM -0700, Andrew Morton wrote:
>...
> Changes since 2.6.17-rc3-mm1:
>...
> git-netdev-all.patch
>...
> git trees
>...
This patch makes the needlessly global bus_speed[] static.
Signed-off-by: Adrian Bunk <bunk@stusta.de>
--- linux-2.6.17-rc4-mm1-full/drivers/net/s2io.c.old 2006-05-16 13:06:58.000000000 +0200
+++ linux-2.6.17-rc4-mm1-full/drivers/net/s2io.c 2006-05-16 13:07:08.000000000 +0200
@@ -852,7 +852,7 @@
return 0;
}
-int bus_speed[8] = {33, 133, 133, 200, 266, 133, 200, 266};
+static int bus_speed[8] = {33, 133, 133, 200, 266, 133, 200, 266};
/**
* s2io_print_pci_mode -
*/
^ permalink raw reply
* Re: [-mm patch] drivers/net/s2io.c: make bus_speed[] static
From: Andreas Mohr @ 2006-05-16 15:36 UTC (permalink / raw)
To: Adrian Bunk; +Cc: Andrew Morton, Ananda Raju, jgarzik, linux-kernel, netdev
In-Reply-To: <20060516153050.GC5677@stusta.de>
Hi,
On Tue, May 16, 2006 at 05:30:50PM +0200, Adrian Bunk wrote:
> This patch makes the needlessly global bus_speed[] static.
Is there a reason why you don't also constify it while you are at it?
Or is it because you want to do a series of static-only patches for now?
Andreas Mohr
^ permalink raw reply
* Re: Setting TCP_NODELAY doesn't disable Nagle's alg. on loopback
From: Stephen Hemminger @ 2006-05-16 16:16 UTC (permalink / raw)
To: Radko Mihal; +Cc: netdev
In-Reply-To: <fc1d209cf91d41b5a5ff491732e52283@pobox.sk>
On Tue, 16 May 2006 10:50:30 +0200
"Radko Mihal" <rmihal@pobox.sk> wrote:
> Hi,
>
> We are facing strange problem with disabling the Nagle's algorithm via setting the TCP_NODELAY flag on server socket (setsockopt), where server is communication with client via loopback.
> After the first segment (of the response) is sent by server side, server is waiting for ACK instead of continuing sending next segments (as it should use sliding window principle). The client sends ACK after 40 ms, only then server sends the rest of responses packed into one segment. The 40 ms is a big delay and causes reponse processing to be 10 times slower.
>
> The thing doesn't happen, if we move client to another host. In that case the server don't wait for ACK, don't pack responses and also response processing is much faster.
>
> It seems, like on loopback the Nagle's alg. is still acting (citate from alg. description says:"a first segment is sent immediately, while further data on the sender side is buffered until either a full maximum segment can be sent or an acknowledgement for the first segment is received)
>
> I found some descriptions of the same problem, but with no solution!
> Is there a bug in setsockopt()? We are using 2.6.5 kernel.
If it is 2.6.5 that is over 2+ years old. Please try with something past the Pleistocene era...
More likely, you mean 2.6.15 and you are seeing the effect of TCP ABC. ABC is appropriate byte count
and it penalizes applications that do small sends. The correct fix is to change your application
to use TCP_CORK or do consolidation with writev(), sendmsg(), etc. This came up with the Java
debugger, see mailing list archives.
^ permalink raw reply
* Re: [PATCH] Enabling standard compliant behaviour in the Linux TCP implementation
From: Stephen Hemminger @ 2006-05-16 16:24 UTC (permalink / raw)
To: Angelo P. Castellani; +Cc: netdev, francesco, andrea.baiocchi
In-Reply-To: <8dd26e70605160724j784cf538v59631cf571646f36@mail.gmail.com>
On Tue, 16 May 2006 16:24:22 +0200
"Angelo P. Castellani" <angelo.castellani+lkml@gmail.com> wrote:
> Hi all,
> I'm a student doing a thesis about TCP performance over high BDP links
> and so about congestion control in TCP.
>
> To do this work I've built a testbed using the latest Linux release (2.6.16).
>
> Anyway I've came across the fact that Linux TCP implementation isn't
> fully standard compliant.
>
> Even if the choices made to be different from the standards have been
> wisely thought, I think that should be possible to disable these
> Linuxisms.
>
> Surely this can help all the people using Linux to evaluate a
> "standard" environment.
>
> Moreover it permits to compare the pros&cons of the Linux
> implementation against the standard one.
>
> So I've disabled the first two Linux-specific mechanisms I've found:
> - rate halving
> - dynamic reordering metric (dynamic DupThresh)
>
> These're disabled as long as net.ipv4.tcp_standard_compliant=1 (default: 0).
>
> However I don't exclude that there're more non-standard details, so I
> hope that somebody can point some more differences between Linux and
> the RFCs.
>
> Moreover NewReno is implemented in the Impatient variant (resets the
> retransmit timer only on the first partial ack), with
> net.ipv4.tcp_slow_but_steady=1 (default: 0) you can enable the
> Slow-but-Steady variant (resets the retransmit timer every partial
> ack).
>
> Hoping that this can be useful, I attach the patch.
>
> Regards,
> Angelo P. Castellani
Read Linus's comments on standards. We make software for users, not for
academic use.
http://kerneltrap.org/node/5725
If we added this then paranoid users would set it.
The Reno thing seems okay, if the default was the same as the original behavior
but it makes one more test case to try.
^ permalink raw reply
* Re: send(), sendmsg(), sendto() not thread-safe
From: Mike Stroyan @ 2006-05-16 16:24 UTC (permalink / raw)
To: Mark A Smith; +Cc: Rick Jones, Linux Network Development list, shemminger
In-Reply-To: <OF4D94549F.7BBB070C-ON85257170.0009219D-88257170.000A05E8@us.ibm.com>
On Mon, May 15, 2006 at 06:50:36PM -0700, Mark A Smith wrote:
>
> I cannot think of another possible definition for thread-safe in the
> context of these functions. Certainly they should not cause a "crash" when
> called from multiple threads, but that's a requirement independent of
> thread-safety.
...
> I think the question really boils down to: "What does thread-safe mean with
> respect to send()?" It might be more easily answered by asking, "How would
> a non-thread-safe send() behave?" I think it would behave the way we're
> seeing it behave.
A non-thread-safe send() could use a global buffer to hold copied
data or results. When called from multiple threads it could lose data
or mix data from send()s to different sockets. Or it could return a
result in one thread that reflects the result of an overlapping send()
in another thread. Or it could sometimes core dump. The behavior of
a non-thread-safe function called from multiple threads is undefined.
There is really no requirement "independent of thread-safety" on the
behavior of a function called from multiple unsyncronized threads.
As Rick noted, this is not really a threading test but a multiprocess
test. A requirement to be thread-safe shouldn't imply anything about
the behavior of functions in single-threaded processes. The posix
standard has a limit of PIPE_BUF bytes for atomic writes to a pipe.
That might extend to expecting sends of under PIPE_BUF bytes to be atomic
on a socket. But I don't actually find any guarantee of atomic writes
for sockets, even for sizes below PIPE_BUF.
--
Mike Stroyan, mike.stroyan@hp.com
^ permalink raw reply
* Re: ifIndex allocation
From: Stephen Hemminger @ 2006-05-16 16:38 UTC (permalink / raw)
To: Sven Schnelle; +Cc: netdev
In-Reply-To: <86r72uh53e.fsf@deprecated.bitebene.org>
On Tue, 16 May 2006 08:11:01 +0200
"Sven Schnelle" <svens@gmx.de> wrote:
> Hi List,
Redirecting to netdev
>
> investigating a problem with an snmp software for linux, i was wondering
> why the kernel allocates a new ifindex Number, even if the old one is still
> available. For example, if i unload a network driver module, and reload
> it, it has a different ifindex.
Because when you reload the driver it is effectively a completely new
object. ifindex is a basically and object id. Ifindices act as soft
references so user space can know about a particular network device
even if name changes or other operations happen. The reference is soft
because the device can disappear. If the application wants to know about
device removal it can catch the netlink event.
> Looking at the function dev_new_index (line 2620 in net/core/dev.c)
> there is a line 'static int ifindex'. Is there any special reason why
> this variable is static, and the list is not traversed from the
> beginning, so that the first free ifindex will be used?
>
>
> Best regards,
>
> Sven.
It is static because no other code should be looking at it.
It doesn't retraverse from the start because it doesn't want to reuse
an earlier index and confuse an application with a soft reference.
^ permalink raw reply
* Re: [-mm patch] drivers/net/s2io.c: make bus_speed[] static
From: Adrian Bunk @ 2006-05-16 16:42 UTC (permalink / raw)
To: Andreas Mohr; +Cc: Andrew Morton, Ananda Raju, jgarzik, linux-kernel, netdev
In-Reply-To: <20060516153611.GA13270@rhlx01.fht-esslingen.de>
On Tue, May 16, 2006 at 05:36:11PM +0200, Andreas Mohr wrote:
> Hi,
>
> On Tue, May 16, 2006 at 05:30:50PM +0200, Adrian Bunk wrote:
> > This patch makes the needlessly global bus_speed[] static.
>
> Is there a reason why you don't also constify it while you are at it?
> Or is it because you want to do a series of static-only patches for now?
The latter.
Feel free to send a patch that also makes it const.
> Andreas Mohr
cu
Adrian
--
"Is there not promise of rain?" Ling Tan asked suddenly out
of the darkness. There had been need of rain for many days.
"Only a promise," Lao Er said.
Pearl S. Buck - Dragon Seed
^ permalink raw reply
* [1/1] Netchannel subsyste.
From: Evgeniy Polyakov @ 2006-05-16 17:34 UTC (permalink / raw)
To: David S. Miller; +Cc: netdev, kelly, rusty
In-Reply-To: <20060515.235712.26771832.davem@davemloft.net>
Receiving support.
As proof-of-concept code I created simple copy_to_user() based getting
data callback. Next step is to implement netchannels data allocation
callbacks to get data from mapped userspace area and make get data
callback be similar to ->recvmsg() so all protocol processing happens in
userspace (TCP should start working, now only UDP case) if there is some
interest in it. Patch attached.
There are brief description of netchannel design and implementation,
patches and userspace utility at project's homepage [1].
Thank you.
1. Netchannel project homepage.
http://tservice.net.ru/~s0mbre/old/?section=projects&item=netchannel
Receiving netchannel implementation.
Signed-off-by: Evgeniy Polyakov <johnpol@2ka.mipt.ru>
diff --git a/arch/i386/kernel/syscall_table.S b/arch/i386/kernel/syscall_table.S
index f48bef1..7a4a758 100644
--- a/arch/i386/kernel/syscall_table.S
+++ b/arch/i386/kernel/syscall_table.S
@@ -315,3 +315,5 @@ ENTRY(sys_call_table)
.long sys_splice
.long sys_sync_file_range
.long sys_tee /* 315 */
+ .long sys_vmsplice
+ .long sys_netchannel_control
diff --git a/arch/x86_64/ia32/ia32entry.S b/arch/x86_64/ia32/ia32entry.S
index 5a92fed..fdfb997 100644
--- a/arch/x86_64/ia32/ia32entry.S
+++ b/arch/x86_64/ia32/ia32entry.S
@@ -696,4 +696,5 @@ ia32_sys_call_table:
.quad sys_sync_file_range
.quad sys_tee
.quad compat_sys_vmsplice
+ .quad sys_netchannel_control
ia32_syscall_end:
diff --git a/include/asm-i386/unistd.h b/include/asm-i386/unistd.h
index eb4b152..777cd85 100644
--- a/include/asm-i386/unistd.h
+++ b/include/asm-i386/unistd.h
@@ -322,8 +322,9 @@
#define __NR_sync_file_range 314
#define __NR_tee 315
#define __NR_vmsplice 316
+#define __NR_netchannel_control 317
-#define NR_syscalls 317
+#define NR_syscalls 318
/*
* user-visible error numbers are in the range -1 - -128: see
diff --git a/include/asm-x86_64/unistd.h b/include/asm-x86_64/unistd.h
index feb77cb..08c230e 100644
--- a/include/asm-x86_64/unistd.h
+++ b/include/asm-x86_64/unistd.h
@@ -617,8 +617,10 @@ __SYSCALL(__NR_tee, sys_tee)
__SYSCALL(__NR_sync_file_range, sys_sync_file_range)
#define __NR_vmsplice 278
__SYSCALL(__NR_vmsplice, sys_vmsplice)
+#define __NR_netchannel_control 279
+__SYSCALL(__NR_vmsplice, sys_netchannel_control)
-#define __NR_syscall_max __NR_vmsplice
+#define __NR_syscall_max __NR_netchannel_control
#ifndef __NO_STUBS
diff --git a/include/linux/netchannel.h b/include/linux/netchannel.h
new file mode 100644
index 0000000..e87a148
--- /dev/null
+++ b/include/linux/netchannel.h
@@ -0,0 +1,75 @@
+/*
+ * netchannel.h
+ *
+ * 2006 Copyright (c) Evgeniy Polyakov <johnpol@2ka.mipt.ru>
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef __NETCHANNEL_H
+#define __NETCHANNEL_H
+
+#include <linux/types.h>
+
+enum netchannel_commands {
+ NETCHANNEL_CREATE = 0,
+ NETCHANNEL_REMOVE,
+ NETCHANNEL_BIND,
+ NETCHANNEL_READ,
+ NETCHANNEL_DUMP,
+};
+
+struct unetchannel
+{
+ __u32 src, dst; /* source/destination hashes */
+ __u16 sport, dport; /* source/destination ports */
+ __u8 proto; /* IP protocol number */
+ __u8 listen;
+ __u8 reserved[2];
+};
+
+struct unetchannel_control
+{
+ struct unetchannel unc;
+ __u32 cmd;
+ __u32 len;
+};
+
+#ifdef __KERNEL__
+
+struct netchannel
+{
+ struct hlist_node node;
+ atomic_t refcnt;
+ struct rcu_head rcu_head;
+ struct unetchannel unc;
+ unsigned long hit;
+
+ struct page * (*nc_alloc_page)(unsigned int size);
+ void (*nc_free_page)(struct page *page);
+ int (*nc_read_data)(struct netchannel *, unsigned int *len, void __user *arg);
+
+ struct sk_buff_head list;
+};
+
+struct netchannel_cache_head
+{
+ struct hlist_head head;
+ struct mutex mutex;
+};
+
+#endif /* __KERNEL__ */
+#endif /* __NETCHANNEL_H */
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index a461b51..9924911 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -684,6 +684,15 @@ extern void dev_queue_xmit_nit(struct s
extern void dev_init(void);
+#ifdef CONFIG_NETCHANNEL
+extern int netchannel_recv(struct sk_buff *skb);
+#else
+static int netchannel_recv(struct sk_buff *skb)
+{
+ return -1;
+}
+#endif
+
extern int netdev_nit;
extern int netdev_budget;
diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h
index f8f2347..accd00b 100644
--- a/include/linux/skbuff.h
+++ b/include/linux/skbuff.h
@@ -301,6 +301,7 @@ struct sk_buff {
* Handling routines are only of interest to the kernel
*/
#include <linux/slab.h>
+#include <linux/netchannel.h>
#include <asm/system.h>
@@ -314,6 +315,17 @@ static inline struct sk_buff *alloc_skb(
return __alloc_skb(size, priority, 0);
}
+#ifdef CONFIG_NETCHANNEL
+extern struct sk_buff *netchannel_alloc(struct unetchannel *unc, unsigned int header_size,
+ unsigned int total_size, gfp_t gfp_mask);
+#else
+static struct sk_buff *netchannel_alloc(struct unetchannel *unc, unsigned int header_size,
+ unsigned int total_size, gfp_t gfp_mask)
+{
+ return NULL;
+}
+#endif
+
static inline struct sk_buff *alloc_skb_fclone(unsigned int size,
gfp_t priority)
{
diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h
index 3996960..8c22875 100644
--- a/include/linux/syscalls.h
+++ b/include/linux/syscalls.h
@@ -582,4 +582,6 @@ asmlinkage long sys_tee(int fdin, int fd
asmlinkage long sys_sync_file_range(int fd, loff_t offset, loff_t nbytes,
unsigned int flags);
+asmlinkage long sys_netchannel_control(void __user *arg);
+
#endif
diff --git a/kernel/sys_ni.c b/kernel/sys_ni.c
index 5433195..1747fc3 100644
--- a/kernel/sys_ni.c
+++ b/kernel/sys_ni.c
@@ -132,3 +132,5 @@ cond_syscall(sys_mincore);
cond_syscall(sys_madvise);
cond_syscall(sys_mremap);
cond_syscall(sys_remap_file_pages);
+
+cond_syscall(sys_netchannel_control);
diff --git a/net/Kconfig b/net/Kconfig
index 4193cdc..465e37b 100644
--- a/net/Kconfig
+++ b/net/Kconfig
@@ -66,6 +66,14 @@ source "net/ipv6/Kconfig"
endif # if INET
+config NETCHANNEL
+ bool "Network channels"
+ ---help---
+ Network channels are peer-to-peer abstraction, which allows to create
+ high performance communications.
+ Main advantages are unified address cache, protocol processing moved
+ to userspace, receiving zero-copy support and other interesting features.
+
menuconfig NETFILTER
bool "Network packet filtering (replaces ipchains)"
---help---
diff --git a/net/core/Makefile b/net/core/Makefile
index 79fe12c..7119812 100644
--- a/net/core/Makefile
+++ b/net/core/Makefile
@@ -16,3 +16,4 @@ obj-$(CONFIG_NET_DIVERT) += dv.o
obj-$(CONFIG_NET_PKTGEN) += pktgen.o
obj-$(CONFIG_WIRELESS_EXT) += wireless.o
obj-$(CONFIG_NETPOLL) += netpoll.o
+obj-$(CONFIG_NETCHANNEL) += netchannel.o
diff --git a/net/core/dev.c b/net/core/dev.c
index 9ab3cfa..2721111 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -1712,6 +1712,10 @@ int netif_receive_skb(struct sk_buff *sk
}
}
+ ret = netchannel_recv(skb);
+ if (!ret)
+ goto out;
+
#ifdef CONFIG_NET_CLS_ACT
if (pt_prev) {
ret = deliver_skb(skb, pt_prev, orig_dev);
diff --git a/net/core/netchannel.c b/net/core/netchannel.c
new file mode 100644
index 0000000..169a764
--- /dev/null
+++ b/net/core/netchannel.c
@@ -0,0 +1,691 @@
+/*
+ * netchannel.c
+ *
+ * 2006 Copyright (c) Evgeniy Polyakov <johnpol@2ka.mipt.ru>
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include <linux/types.h>
+#include <linux/unistd.h>
+#include <linux/linkage.h>
+#include <linux/notifier.h>
+#include <linux/list.h>
+#include <linux/slab.h>
+#include <linux/skbuff.h>
+#include <linux/errno.h>
+
+#include <linux/in.h>
+#include <linux/ip.h>
+#include <linux/tcp.h>
+#include <linux/udp.h>
+
+#include <linux/netdevice.h>
+#include <linux/inetdevice.h>
+#include <net/addrconf.h>
+
+#include <asm/uaccess.h>
+
+static unsigned int netchannel_hash_order = 8;
+static struct netchannel_cache_head ***netchannel_hash_table;
+static kmem_cache_t *netchannel_cache;
+
+static int netchannel_inetaddr_notifier_call(struct notifier_block *, unsigned long, void *);
+static struct notifier_block netchannel_inetaddr_notifier = {
+ .notifier_call = &netchannel_inetaddr_notifier_call
+};
+
+#ifdef CONFIG_IPV6
+static int netchannel_inet6addr_notifier_call(struct notifier_block *, unsigned long, void *);
+static struct notifier_block netchannel_inet6addr_notifier = {
+ .notifier_call = &netchannel_inet6addr_notifier_call
+};
+#endif
+
+static inline unsigned int netchannel_hash(struct unetchannel *unc)
+{
+ unsigned int h = (unc->dst ^ unc->dport) ^ (unc->src ^ unc->sport);
+ h ^= h >> 16;
+ h ^= h >> 8;
+ h ^= unc->proto;
+ return h & ((1 << 2*netchannel_hash_order) - 1);
+}
+
+static inline void netchannel_convert_hash(unsigned int hash, unsigned int *col, unsigned int *row)
+{
+ *row = hash & ((1 << netchannel_hash_order) - 1);
+ *col = (hash >> netchannel_hash_order) & ((1 << netchannel_hash_order) - 1);
+}
+
+static struct netchannel_cache_head *netchannel_bucket(struct unetchannel *unc)
+{
+ unsigned int hash = netchannel_hash(unc);
+ unsigned int col, row;
+
+ netchannel_convert_hash(hash, &col, &row);
+ return netchannel_hash_table[col][row];
+}
+
+static inline int netchannel_hash_equal_full(struct unetchannel *unc1, struct unetchannel *unc2)
+{
+ return (unc1->dport == unc2->dport) && (unc1->dst == unc2->dst) &&
+ (unc1->sport == unc2->sport) && (unc1->src == unc2->src) &&
+ (unc1->proto == unc2->proto);
+}
+
+static inline int netchannel_hash_equal_dest(struct unetchannel *unc1, struct unetchannel *unc2)
+{
+ return ((unc1->dport == unc2->dport) && (unc1->dst == unc2->dst) && (unc1->proto == unc2->proto));
+}
+
+static struct netchannel *netchannel_check_dest(struct unetchannel *unc, struct netchannel_cache_head *bucket)
+{
+ struct netchannel *nc;
+ struct hlist_node *node;
+ int found = 0;
+
+ hlist_for_each_entry_rcu(nc, node, &bucket->head, node) {
+ if (netchannel_hash_equal_dest(&nc->unc, unc)) {
+ found = 1;
+ break;
+ }
+ }
+
+ return (found)?nc:NULL;
+}
+
+static struct netchannel *netchannel_check_full(struct unetchannel *unc, struct netchannel_cache_head *bucket)
+{
+ struct netchannel *nc;
+ struct hlist_node *node;
+ int found = 0;
+
+ hlist_for_each_entry_rcu(nc, node, &bucket->head, node) {
+ if (netchannel_hash_equal_full(&nc->unc, unc)) {
+ found = 1;
+ break;
+ }
+ }
+
+ return (found)?nc:NULL;
+}
+
+static void netchannel_free_rcu(struct rcu_head *rcu)
+{
+ struct netchannel *nc = container_of(rcu, struct netchannel, rcu_head);
+
+ kmem_cache_free(netchannel_cache, nc);
+}
+
+static inline void netchannel_get(struct netchannel *nc)
+{
+ atomic_inc(&nc->refcnt);
+}
+
+static inline void netchannel_put(struct netchannel *nc)
+{
+ if (atomic_dec_and_test(&nc->refcnt))
+ call_rcu(&nc->rcu_head, &netchannel_free_rcu);
+}
+
+static inline void netchannel_dump_info_unc(struct unetchannel *unc, char *prefix, unsigned long hit, int err)
+{
+ u32 src, dst;
+ u16 sport, dport;
+
+ dst = unc->dst;
+ src = unc->src;
+ dport = ntohs(unc->dport);
+ sport = ntohs(unc->sport);
+
+ printk(KERN_INFO "netchannel: %s %u.%u.%u.%u:%u -> %u.%u.%u.%u:%u, proto: %u, hit: %lu, err: %d.\n",
+ prefix, NIPQUAD(src), sport, NIPQUAD(dst), dport, unc->proto, hit, err);
+}
+
+static int netchannel_convert_skb_ipv6(struct sk_buff *skb, struct unetchannel *unc)
+{
+ /*
+ * Hash IP addresses into src/dst. Setup TCP/UDP ports.
+ * Not supported yet.
+ */
+ return -1;
+}
+
+static int netchannel_convert_skb_ipv4(struct sk_buff *skb, struct unetchannel *unc)
+{
+ struct iphdr *iph;
+ u32 len;
+ struct tcphdr *th;
+ struct udphdr *uh;
+
+ if (!pskb_may_pull(skb, sizeof(struct iphdr)))
+ goto inhdr_error;
+
+ iph = skb->nh.iph;
+
+ if (iph->ihl < 5 || iph->version != 4)
+ goto inhdr_error;
+
+ if (!pskb_may_pull(skb, iph->ihl*4))
+ goto inhdr_error;
+
+ iph = skb->nh.iph;
+
+ if (unlikely(ip_fast_csum((u8 *)iph, iph->ihl)))
+ goto inhdr_error;
+
+ len = ntohs(iph->tot_len);
+ if (skb->len < len || len < (iph->ihl*4))
+ goto inhdr_error;
+
+ unc->dst = iph->daddr;
+ unc->src = iph->saddr;
+ unc->proto = iph->protocol;
+
+ len = skb->len;
+
+ skb->h.raw = skb->nh.iph + iph->ihl*4;
+
+ switch (unc->proto) {
+ case IPPROTO_TCP:
+ if (!pskb_may_pull(skb, sizeof(struct tcphdr)))
+ goto inhdr_error;
+ th = skb->h.th;
+
+ if (th->doff < sizeof(struct tcphdr) / 4)
+ goto inhdr_error;
+
+ unc->dport = th->dest;
+ unc->sport = th->source;
+ break;
+ case IPPROTO_UDP:
+ if (!pskb_may_pull(skb, sizeof(struct udphdr)))
+ goto inhdr_error;
+ uh = skb->h.uh;
+
+ if (ntohs(uh->len) < sizeof(struct udphdr))
+ goto inhdr_error;
+
+ unc->dport = uh->dest;
+ unc->sport = uh->source;
+ break;
+ default:
+ goto inhdr_error;
+ }
+
+ return 0;
+
+inhdr_error:
+ return -1;
+}
+
+static int netchannel_convert_skb(struct sk_buff *skb, struct unetchannel *unc)
+{
+ if (skb->pkt_type == PACKET_OTHERHOST)
+ return -1;
+
+ switch (ntohs(skb->protocol)) {
+ case ETH_P_IP:
+ return netchannel_convert_skb_ipv4(skb, unc);
+ case ETH_P_IPV6:
+ return netchannel_convert_skb_ipv6(skb, unc);
+ default:
+ return -1;
+ }
+}
+
+/*
+ * By design netchannels allow to "allocate" data
+ * not only from SLAB cache, but get it from mapped area
+ * or from VFS cache (requires process' context or preallocation).
+ */
+struct sk_buff *netchannel_alloc(struct unetchannel *unc, unsigned int header_size,
+ unsigned int total_size, gfp_t gfp_mask)
+{
+ struct netchannel *nc;
+ struct netchannel_cache_head *bucket;
+ int err;
+ struct sk_buff *skb = NULL;
+ unsigned int size, pnum, i;
+
+ skb = alloc_skb(header_size, gfp_mask);
+ if (!skb)
+ return NULL;
+
+ rcu_read_lock();
+ bucket = netchannel_bucket(unc);
+ nc = netchannel_check_full(unc, bucket);
+ if (!nc) {
+ err = -ENODEV;
+ goto err_out_free_skb;
+ }
+
+ if (!nc->nc_alloc_page || !nc->nc_free_page) {
+ err = -EINVAL;
+ goto err_out_free_skb;
+ }
+
+ netchannel_get(nc);
+
+ size = total_size - header_size;
+ pnum = PAGE_ALIGN(size) >> PAGE_SHIFT;
+
+ for (i=0; i<pnum; ++i) {
+ unsigned int cs = min_t(unsigned int, PAGE_SIZE, size);
+ struct page *page;
+
+ page = nc->nc_alloc_page(cs);
+ if (!page)
+ break;
+
+ skb_fill_page_desc(skb, skb_shinfo(skb)->nr_frags, page, 0, cs);
+
+ skb->len += cs;
+ skb->data_len += cs;
+ skb->truesize += cs;
+
+ size -= cs;
+ }
+
+ if (i < pnum) {
+ pnum = i;
+ err = -ENOMEM;
+ goto err_out_free_frags;
+ }
+
+ rcu_read_unlock();
+
+ return skb;
+
+err_out_free_frags:
+ for (i=0; i<pnum; ++i) {
+ unsigned int cs = skb_shinfo(skb)->frags[i].size;
+ struct page *page = skb_shinfo(skb)->frags[i].page;
+
+ nc->nc_free_page(page);
+
+ skb->len -= cs;
+ skb->data_len -= cs;
+ skb->truesize -= cs;
+ }
+
+err_out_free_skb:
+ kfree_skb(skb);
+ return NULL;
+}
+
+int netchannel_recv(struct sk_buff *skb)
+{
+ struct netchannel *nc;
+ struct unetchannel unc;
+ struct netchannel_cache_head *bucket;
+ int err;
+
+ if (!netchannel_hash_table)
+ return -ENODEV;
+
+ rcu_read_lock();
+
+ err = netchannel_convert_skb(skb, &unc);
+ if (err)
+ goto unlock;
+
+ bucket = netchannel_bucket(&unc);
+ nc = netchannel_check_full(&unc, bucket);
+ if (!nc) {
+ err = -ENODEV;
+ goto unlock;
+ }
+
+ nc->hit++;
+
+ skb_queue_tail(&nc->list, skb);
+
+unlock:
+ rcu_read_unlock();
+ return err;
+}
+
+/*
+ * Actually it should be something like recvmsg().
+ */
+static int netchannel_copy_to_user(struct netchannel *nc, unsigned int *len, void __user *arg)
+{
+ unsigned int copied;
+ struct sk_buff *skb;
+ struct iovec to;
+ int err = -EINVAL;
+
+ to.iov_base = arg;
+ to.iov_len = *len;
+
+ skb = skb_dequeue(&nc->list);
+ if (!skb)
+ return -EAGAIN;
+
+ copied = skb->len;
+ if (copied > *len)
+ copied = *len;
+
+ if (skb->ip_summed==CHECKSUM_UNNECESSARY) {
+ err = skb_copy_datagram_iovec(skb, 0, &to, copied);
+ } else {
+ err = skb_copy_and_csum_datagram_iovec(skb,0, &to);
+ }
+
+ *len = (err == 0)?copied:0;
+
+ kfree_skb(skb);
+
+ return err;
+}
+
+static int netchannel_create(struct unetchannel *unc)
+{
+ struct netchannel *nc;
+ int err = -ENOMEM;
+ struct netchannel_cache_head *bucket;
+
+ if (!netchannel_hash_table)
+ return -ENODEV;
+
+ bucket = netchannel_bucket(unc);
+
+ mutex_lock(&bucket->mutex);
+
+ if (netchannel_check_full(unc, bucket)) {
+ err = -EEXIST;
+ goto out_unlock;
+ }
+
+ if (unc->listen && netchannel_check_dest(unc, bucket)) {
+ err = -EEXIST;
+ goto out_unlock;
+ }
+
+ nc = kmem_cache_alloc(netchannel_cache, GFP_KERNEL);
+ if (!nc)
+ goto out_exit;
+
+ memset(nc, 0, sizeof(struct netchannel));
+
+ nc->hit = 0;
+ skb_queue_head_init(&nc->list);
+ atomic_set(&nc->refcnt, 1);
+ memcpy(&nc->unc, unc, sizeof(struct unetchannel));
+
+ nc->nc_read_data = &netchannel_copy_to_user;
+
+ hlist_add_head_rcu(&nc->node, &bucket->head);
+ err = 0;
+
+out_unlock:
+ mutex_unlock(&bucket->mutex);
+out_exit:
+ netchannel_dump_info_unc(unc, "create", 0, err);
+
+ return err;
+}
+
+static int netchannel_remove(struct unetchannel *unc)
+{
+ struct netchannel *nc;
+ int err = -ENODEV;
+ struct netchannel_cache_head *bucket;
+ unsigned long hit = 0;
+
+ if (!netchannel_hash_table)
+ return -ENODEV;
+
+ bucket = netchannel_bucket(unc);
+
+ mutex_lock(&bucket->mutex);
+
+ nc = netchannel_check_full(unc, bucket);
+ if (!nc)
+ nc = netchannel_check_dest(unc, bucket);
+
+ if (!nc)
+ goto out_unlock;
+
+ hlist_del_rcu(&nc->node);
+ hit = nc->hit;
+
+ netchannel_put(nc);
+ err = 0;
+
+out_unlock:
+ mutex_unlock(&bucket->mutex);
+ netchannel_dump_info_unc(unc, "remove", hit, err);
+ return err;
+}
+
+static int netchannel_recv_data(struct unetchannel_control *ctl, void __user *data)
+{
+ int ret = -ENODEV;
+ struct netchannel_cache_head *bucket;
+ struct netchannel *nc;
+
+ bucket = netchannel_bucket(&ctl->unc);
+
+ mutex_lock(&bucket->mutex);
+
+ nc = netchannel_check_full(&ctl->unc, bucket);
+ if (!nc)
+ nc = netchannel_check_dest(&ctl->unc, bucket);
+
+ if (!nc)
+ goto out_unlock;
+
+ ret = nc->nc_read_data(nc, &ctl->len, data);
+
+out_unlock:
+ mutex_unlock(&bucket->mutex);
+ return ret;
+}
+
+static int netchannel_dump_info(struct unetchannel *unc)
+{
+ struct netchannel_cache_head *bucket;
+ struct netchannel *nc;
+ char *ncs = "none";
+ unsigned long hit = 0;
+ int err;
+
+ bucket = netchannel_bucket(unc);
+
+ mutex_lock(&bucket->mutex);
+ nc = netchannel_check_full(unc, bucket);
+ if (!nc) {
+ nc = netchannel_check_dest(unc, bucket);
+ if (nc)
+ ncs = "dest";
+ } else
+ ncs = "full";
+ if (nc)
+ hit = nc->hit;
+ mutex_unlock(&bucket->mutex);
+ err = (nc)?0:-ENODEV;
+
+ netchannel_dump_info_unc(unc, ncs, hit, err);
+
+ return err;
+}
+
+asmlinkage long sys_netchannel_control(void __user *arg)
+{
+ struct unetchannel_control ctl;
+ int ret;
+
+ if (!netchannel_hash_table)
+ return -ENODEV;
+
+ if (copy_from_user(&ctl, arg, sizeof(struct unetchannel_control)))
+ return -ERESTARTSYS;
+
+ switch (ctl.cmd) {
+ case NETCHANNEL_CREATE:
+ case NETCHANNEL_BIND:
+ ret = netchannel_create(&ctl.unc);
+ break;
+ case NETCHANNEL_REMOVE:
+ ret = netchannel_remove(&ctl.unc);
+ break;
+ case NETCHANNEL_READ:
+ ret = netchannel_recv_data(&ctl, arg + sizeof(struct unetchannel_control));
+ break;
+ case NETCHANNEL_DUMP:
+ ret = netchannel_dump_info(&ctl.unc);
+ break;
+ default:
+ ret = -EINVAL;
+ break;
+ }
+
+ if (copy_to_user(arg, &ctl, sizeof(struct unetchannel_control)))
+ return -ERESTARTSYS;
+
+ return ret;
+}
+
+static inline void netchannel_dump_addr(struct in_ifaddr *ifa, char *str)
+{
+ printk("netchannel: %s %u.%u.%u.%u/%u.%u.%u.%u\n", str, NIPQUAD(ifa->ifa_local), NIPQUAD(ifa->ifa_mask));
+}
+
+static int netchannel_inetaddr_notifier_call(struct notifier_block *this, unsigned long event, void *ptr)
+{
+ struct in_ifaddr *ifa = ptr;
+
+ switch (event) {
+ case NETDEV_UP:
+ netchannel_dump_addr(ifa, "add");
+ break;
+ case NETDEV_DOWN:
+ netchannel_dump_addr(ifa, "del");
+ break;
+ default:
+ netchannel_dump_addr(ifa, "unk");
+ break;
+ }
+
+ return NOTIFY_DONE;
+}
+
+#ifdef CONFIG_IPV6
+static int netchannel_inet6addr_notifier_call(struct notifier_block *this, unsigned long event, void *ptr)
+{
+ struct inet6_ifaddr *ifa = ptr;
+
+ printk("netchannel: inet6 event=%lx, ifa=%p.\n", event, ifa);
+ return NOTIFY_DONE;
+}
+#endif
+
+static int __init netchannel_init(void)
+{
+ unsigned int i, j, size;
+ int err = -ENOMEM;
+
+ size = (1 << netchannel_hash_order);
+
+ netchannel_hash_table = kzalloc(size * sizeof(void *), GFP_KERNEL);
+ if (!netchannel_hash_table)
+ goto err_out_exit;
+
+ for (i=0; i<size; ++i) {
+ struct netchannel_cache_head **col;
+
+ col = kzalloc(size * sizeof(void *), GFP_KERNEL);
+ if (!col)
+ break;
+
+ for (j=0; j<size; ++j) {
+ struct netchannel_cache_head *head;
+
+ head = kzalloc(sizeof(struct netchannel_cache_head), GFP_KERNEL);
+ if (!head)
+ break;
+
+ INIT_HLIST_HEAD(&head->head);
+ mutex_init(&head->mutex);
+
+ col[j] = head;
+ }
+
+ if (j<size && j>0) {
+ while (j >= 0)
+ kfree(col[j--]);
+ kfree(col);
+ break;
+ }
+
+ netchannel_hash_table[i] = col;
+ }
+
+ if (i<size) {
+ size = i;
+ goto err_out_free;
+ }
+
+ netchannel_cache = kmem_cache_create("netchannel", sizeof(struct netchannel), 0, 0,
+ NULL, NULL);
+ if (!netchannel_cache)
+ goto err_out_free;
+
+ register_inetaddr_notifier(&netchannel_inetaddr_notifier);
+#ifdef CONFIG_IPV6
+ register_inet6addr_notifier(&netchannel_inet6addr_notifier);
+#endif
+
+ printk("netchannel: Created %u order two-dimensional hash table.\n",
+ netchannel_hash_order);
+
+ return 0;
+
+err_out_free:
+ for (i=0; i<size; ++i) {
+ for (j=0; j<(1 << netchannel_hash_order); ++j)
+ kfree(netchannel_hash_table[i][j]);
+ kfree(netchannel_hash_table[i]);
+ }
+ kfree(netchannel_hash_table);
+err_out_exit:
+
+ printk("netchannel: Failed to create %u order two-dimensional hash table.\n",
+ netchannel_hash_order);
+ return err;
+}
+
+static void __exit netchannel_exit(void)
+{
+ unsigned int i, j;
+
+ unregister_inetaddr_notifier(&netchannel_inetaddr_notifier);
+#ifdef CONFIG_IPV6
+ unregister_inet6addr_notifier(&netchannel_inet6addr_notifier);
+#endif
+ kmem_cache_destroy(netchannel_cache);
+
+ for (i=0; i<(1 << netchannel_hash_order); ++i) {
+ for (j=0; j<(1 << netchannel_hash_order); ++j)
+ kfree(netchannel_hash_table[i][j]);
+ kfree(netchannel_hash_table[i]);
+ }
+ kfree(netchannel_hash_table);
+}
+
+late_initcall(netchannel_init);
--
Evgeniy Polyakov
^ permalink raw reply related
* [RFC] new qla3xxx NIC Driver v2.02.00k19
From: Ron Mercer @ 2006-05-16 17:52 UTC (permalink / raw)
To: Ron Mercer, netdev; +Cc: linux-driver, Ying Ping Lok, Mike Metskas
All,
Second submission for the upstream inclusion of the qla3xxx Ethernet
driver. This is a complementary network driver for our ISP4XXX parts.
There is a concurrent effort underway to get the iSCSI driver (qla4xxx)
integrated upstream as well.
The following files are included and have been posted to the link below:
LICENSE.qla3xxx
qla3xxxsrc-v2.02.00k19.tgz
ftp://ftp.qlogic.com/outgoing/linux/network/upstream/2.02.00k19/
Original submission:
http://marc.theaimsgroup.com/?l=linux-netdev&m=114254712431781&w=2
Comments from original submission:
http://marc.theaimsgroup.com/?l=linux-netdev&m=114263130100996&w=2
Changes in this release:
-Removed double buffering on receives.
-Added NAPI support.
-Removed elements in device structure that were already in netdev.
-Changed to pci_xxx_consistent calls instead of dma_xxx_coherent.
-Added ethtool support.
-Changed debug printing to use netif_msg_xxx.
-Changed DPC thread to work queue.
-Inlined numerous functions.
-Changed all functions to statics.
-Combined all source files to a single file.
Work in progress:
-Removal of debug functions.
-Possible changes for big endian architecture.
The driver has been built and tested using kernel 2.6.16-rc5.
Looking forward to any and all feedback.
Regards,
Ron Mercer
Qlogic Corporation
^ permalink raw reply
* Re: Controlling TCP window size
From: John Heffner @ 2006-05-16 18:28 UTC (permalink / raw)
To: lists; +Cc: netdev
In-Reply-To: <4469B251.3050901@andyfurniss.entadsl.com>
Andy Furniss wrote:
>
> I've been doing some testing of my new wan connection and noticed that
> when I specify a window with ip route it still changes after a while.
Looks like this is occurring in net/ipv4/tcp_input.c:tcp_rcv_space_adjust().
The problem really is that the window_clamp variable is overloaded.
It's used as a kind of cache for rcvbuf -> window conversion, but also
as a user-settable bound in window size. On examination, it looks like
this is also broken (in that window size won't increase) if a user does
a setsockopt(SO_RCVBUF). Can we make window_clamp a true clamp? Then
we can get rid of the hack of raising it in tcp_rcv_space_adjust(). I
can cook up a patch if interested.
-John
^ permalink raw reply
* Re: Controlling TCP window size
From: Andy Furniss @ 2006-05-16 18:36 UTC (permalink / raw)
To: John Heffner; +Cc: netdev
In-Reply-To: <446A19C7.1000302@psc.edu>
John Heffner wrote:
> Andy Furniss wrote:
>
>>
>> I've been doing some testing of my new wan connection and noticed that
>> when I specify a window with ip route it still changes after a while.
>
>
> Looks like this is occurring in
> net/ipv4/tcp_input.c:tcp_rcv_space_adjust().
>
> The problem really is that the window_clamp variable is overloaded. It's
> used as a kind of cache for rcvbuf -> window conversion, but also as a
> user-settable bound in window size. On examination, it looks like this
> is also broken (in that window size won't increase) if a user does a
> setsockopt(SO_RCVBUF). Can we make window_clamp a true clamp? Then we
> can get rid of the hack of raising it in tcp_rcv_space_adjust(). I can
> cook up a patch if interested.
>
> -John
>
Thanks - I did get an answer off list (probably accidently?) to the
effect that I shouldn't rely on ip route to limit window as it's only a
hint and would make more sense if I wanted it to start really big.
Playing with r_mem etc is the way to go to hard limit.
Andy.
^ permalink raw reply
* [PATCH] ipv6: endian fix
From: Alexey Dobriyan @ 2006-05-16 18:36 UTC (permalink / raw)
To: Andrew Morton; +Cc: netdev
Signed-off-by: Alexey Dobriyan <adobriyan@gmail.com>
---
--- a/net/ipv6/netfilter/ip6t_eui64.c
+++ b/net/ipv6/netfilter/ip6t_eui64.c
@@ -38,11 +38,11 @@ match(const struct sk_buff *skb,
return 0;
}
memset(eui64, 0, sizeof(eui64));
- if (eth_hdr(skb)->h_proto == ntohs(ETH_P_IPV6)) {
+ if (eth_hdr(skb)->h_proto == htons(ETH_P_IPV6)) {
if (skb->nh.ipv6h->version == 0x6) {
memcpy(eui64, eth_hdr(skb)->h_source, 3);
memcpy(eui64 + 5, eth_hdr(skb)->h_source + 3, 3);
eui64[3] = 0xff;
eui64[4] = 0xfe;
^ permalink raw reply
* Re: Controlling TCP window size
From: John Heffner @ 2006-05-16 18:48 UTC (permalink / raw)
To: lists; +Cc: netdev
In-Reply-To: <446A1BC8.5060609@andyfurniss.entadsl.com>
Andy Furniss wrote:
> John Heffner wrote:
>> Andy Furniss wrote:
>>
>>>
>>> I've been doing some testing of my new wan connection and noticed
>>> that when I specify a window with ip route it still changes after a
>>> while.
>>
>>
>> Looks like this is occurring in
>> net/ipv4/tcp_input.c:tcp_rcv_space_adjust().
>>
>> The problem really is that the window_clamp variable is overloaded.
>> It's used as a kind of cache for rcvbuf -> window conversion, but also
>> as a user-settable bound in window size. On examination, it looks
>> like this is also broken (in that window size won't increase) if a
>> user does a setsockopt(SO_RCVBUF). Can we make window_clamp a true
>> clamp? Then we can get rid of the hack of raising it in
>> tcp_rcv_space_adjust(). I can cook up a patch if interested.
>>
>> -John
>>
>
> Thanks - I did get an answer off list (probably accidently?) to the
> effect that I shouldn't rely on ip route to limit window as it's only a
> hint and would make more sense if I wanted it to start really big.
I guess the other problem is that it's not well defined. :) As it
stands now though it's nearly useless if you have tcp_moderate_rcvbuf
turned on.
> Playing with r_mem etc is the way to go to hard limit.
This will work, but is not available per-route or per-socket. The
purpose is really different.
-John
^ permalink raw reply
* [2.6 patch] net/802/tr.c: remove an unused export
From: Adrian Bunk @ 2006-05-16 18:48 UTC (permalink / raw)
To: acme; +Cc: netdev
This patch removes the unused EXPORT_SYMBOL(tr_source_route).
(No, the usage in net/llc/llc_output.c can't be modular.)
Signed-off-by: Adrian Bunk <bunk@stusta.de>
---
This patch was already sent on:
- 20 Apr 2006
--- linux-2.6.17-rc1-mm3-full/net/802/tr.c.old 2006-04-20 22:45:07.000000000 +0200
+++ linux-2.6.17-rc1-mm3-full/net/802/tr.c 2006-04-20 22:45:18.000000000 +0200
@@ -643,6 +643,5 @@
module_init(rif_init);
-EXPORT_SYMBOL(tr_source_route);
EXPORT_SYMBOL(tr_type_trans);
EXPORT_SYMBOL(alloc_trdev);
^ permalink raw reply
* [PATCH] ipx: correct return type of ipx_map_frame_type
From: Alexey Dobriyan @ 2006-05-16 18:49 UTC (permalink / raw)
To: Andrew Morton; +Cc: Arnaldo Carvalho de Melo, netdev
Casting BE16 to int and back may or may not work. Correct, to be sure.
Signed-off-by: Alexey Dobriyan <adobriyan@gmail.com>
---
--- a/net/ipx/af_ipx.c
+++ b/net/ipx/af_ipx.c
@@ -944,9 +944,9 @@ out:
return rc;
}
-static int ipx_map_frame_type(unsigned char type)
+static __be16 ipx_map_frame_type(unsigned char type)
{
- int rc = 0;
+ __be16 rc = 0;
switch (type) {
case IPX_FRAME_ETHERII: rc = htons(ETH_P_IPX); break;
^ permalink raw reply
* Re: kernel panic (on DHCP discover?) in sky2 driver of 2.6.17-rc1
From: Stephen Hemminger @ 2006-05-16 19:11 UTC (permalink / raw)
To: Guenther Thomsen; +Cc: John W. Linville, netdev
In-Reply-To: <200604121442.56750.gthomsen@bluearc.com>
Could you try the 2.6.17-rc4 version with this patch. It turns out the board
seems to give out of order status responses.
Ignore the vendor sk98lin driver, when I try the stock version it spends it's
life resetting itself because it sets up PCI bus wrong. If I fix that, it spends
it's time getting confused because it can't handle intermixed status reports
properly (checksum et all is per port not per board).
drivers/net/sky2.c | 28 +++++++++++++++++++++-------
1 files changed, 21 insertions(+), 7 deletions(-)
792547bc5e8e4f7d5a1070a168056f429635c254
diff --git a/drivers/net/sky2.c b/drivers/net/sky2.c
index ffd267f..11e7914 100644
--- a/drivers/net/sky2.c
+++ b/drivers/net/sky2.c
@@ -1020,8 +1020,27 @@ static int sky2_up(struct net_device *de
struct sky2_hw *hw = sky2->hw;
unsigned port = sky2->port;
u32 ramsize, rxspace, imask;
- int err = -ENOMEM;
+ int cap, err;
+ struct net_device *otherdev = hw->dev[sky2->port^1];
+ /*
+ * Reduce split transactions (and turn off) rx checksums to
+ * prevent problems with dual ports.
+ */
+ if (otherdev && netif_running(otherdev) &&
+ (cap = pci_find_capability(hw->pdev, PCI_CAP_ID_PCIX))) {
+ struct sky2_port *osky2 = netdev_priv(otherdev);
+ u16 cmd;
+
+ cmd = sky2_pci_read16(hw, cap + PCI_X_CMD);
+ cmd &= ~PCI_X_CMD_MAX_SPLIT;
+ sky2_pci_write16(hw, cap + PCI_X_CMD, cmd);
+
+ sky2->rx_csum = 0;
+ osky2->rx_csum = 0;
+ }
+
+ err = -ENOMEM;
if (netif_msg_ifup(sky2))
printk(KERN_INFO PFX "%s: enabling interface\n", dev->name);
@@ -3067,12 +3086,7 @@ static __devinit struct net_device *sky2
sky2->duplex = -1;
sky2->speed = -1;
sky2->advertising = sky2_supported_modes(hw);
-
- /* Receive checksum disabled for Yukon XL
- * because of observed problems with incorrect
- * values when multiple packets are received in one interrupt
- */
- sky2->rx_csum = (hw->chip_id != CHIP_ID_YUKON_XL);
+ sky2->rx_csum = 1;
spin_lock_init(&sky2->phy_lock);
sky2->tx_pending = TX_DEF_PENDING;
--
1.2.4
^ permalink raw reply related
* [PATCH] ipx: correct return type of ipxrtr_delete
From: Alexey Dobriyan @ 2006-05-16 20:12 UTC (permalink / raw)
To: Andrew Morton; +Cc: Arnaldo Carvalho de Melo, netdev
A single caller passes __u32. Inside function "net" is compared with
__u32 (__be32 really, just wasn't annotated).
Signed-off-by: Alexey Dobriyan <adobriyan@gmail.com>
---
--- a/net/ipx/ipx_route.c
+++ b/net/ipx/ipx_route.c
@@ -119,7 +119,7 @@ out:
return rc;
}
-static int ipxrtr_delete(long net)
+static int ipxrtr_delete(__u32 net)
{
struct ipx_route *r, *tmp;
int rc;
^ permalink raw reply
* RE: kernel panic (on DHCP discover?) in sky2 driver of 2.6.17-rc1
From: Guenther Thomsen @ 2006-05-16 20:15 UTC (permalink / raw)
To: Stephen Hemminger; +Cc: John W. Linville, netdev
Thanks for your continued work on it. I will test the patch, as soon as I get access to the hardware again (probably next week).
best regards
Guenther
-----Original Message-----
From: Stephen Hemminger [mailto:shemminger@osdl.org]
Sent: Tuesday, May 16, 2006 12:12 PM
To: Guenther Thomsen
Cc: John W. Linville; netdev@vger.kernel.org
Subject: Re: kernel panic (on DHCP discover?) in sky2 driver of
2.6.17-rc1
Could you try the 2.6.17-rc4 version with this patch. It turns out the board
seems to give out of order status responses.
Ignore the vendor sk98lin driver, when I try the stock version it spends it's
life resetting itself because it sets up PCI bus wrong. If I fix that, it spends
it's time getting confused because it can't handle intermixed status reports
properly (checksum et all is per port not per board).
drivers/net/sky2.c | 28 +++++++++++++++++++++-------
1 files changed, 21 insertions(+), 7 deletions(-)
792547bc5e8e4f7d5a1070a168056f429635c254
diff --git a/drivers/net/sky2.c b/drivers/net/sky2.c
index ffd267f..11e7914 100644
--- a/drivers/net/sky2.c
+++ b/drivers/net/sky2.c
@@ -1020,8 +1020,27 @@ static int sky2_up(struct net_device *de
struct sky2_hw *hw = sky2->hw;
unsigned port = sky2->port;
u32 ramsize, rxspace, imask;
- int err = -ENOMEM;
+ int cap, err;
+ struct net_device *otherdev = hw->dev[sky2->port^1];
+ /*
+ * Reduce split transactions (and turn off) rx checksums to
+ * prevent problems with dual ports.
+ */
+ if (otherdev && netif_running(otherdev) &&
+ (cap = pci_find_capability(hw->pdev, PCI_CAP_ID_PCIX))) {
+ struct sky2_port *osky2 = netdev_priv(otherdev);
+ u16 cmd;
+
+ cmd = sky2_pci_read16(hw, cap + PCI_X_CMD);
+ cmd &= ~PCI_X_CMD_MAX_SPLIT;
+ sky2_pci_write16(hw, cap + PCI_X_CMD, cmd);
+
+ sky2->rx_csum = 0;
+ osky2->rx_csum = 0;
+ }
+
+ err = -ENOMEM;
if (netif_msg_ifup(sky2))
printk(KERN_INFO PFX "%s: enabling interface\n", dev->name);
@@ -3067,12 +3086,7 @@ static __devinit struct net_device *sky2
sky2->duplex = -1;
sky2->speed = -1;
sky2->advertising = sky2_supported_modes(hw);
-
- /* Receive checksum disabled for Yukon XL
- * because of observed problems with incorrect
- * values when multiple packets are received in one interrupt
- */
- sky2->rx_csum = (hw->chip_id != CHIP_ID_YUKON_XL);
+ sky2->rx_csum = 1;
spin_lock_init(&sky2->phy_lock);
sky2->tx_pending = TX_DEF_PENDING;
--
1.2.4
^ permalink raw reply related
* Re: [PATCH] Enabling standard compliant behaviour in the Linux TCP implementation
From: David S. Miller @ 2006-05-16 20:51 UTC (permalink / raw)
To: shemminger; +Cc: angelo.castellani+lkml, netdev, francesco, andrea.baiocchi
In-Reply-To: <20060516092407.68fbc205@localhost.localdomain>
From: Stephen Hemminger <shemminger@osdl.org>
Date: Tue, 16 May 2006 09:24:07 -0700
> Read Linus's comments on standards. We make software for users, not for
> academic use.
> http://kerneltrap.org/node/5725
>
> If we added this then paranoid users would set it.
I totally agree, and naming this thing "standard_compliant" really
gives the wrong impression about the situation.
Every TCP stack out there has behaviorisms, like these, which
while not mentioned specifically in any standard are entirely
within the spirit of the standards and that is what matters.
^ permalink raw reply
* Re: Setting TCP_NODELAY doesn't disable Nagle's alg. on loopback
From: David S. Miller @ 2006-05-16 20:53 UTC (permalink / raw)
To: shemminger; +Cc: rmihal, netdev
In-Reply-To: <20060516091606.39d0ecc3@localhost.localdomain>
From: Stephen Hemminger <shemminger@osdl.org>
Date: Tue, 16 May 2006 09:16:06 -0700
> If it is 2.6.5 that is over 2+ years old. Please try with something
> past the Pleistocene era...
R O F L!
If that doesn't belong in a quotes file, I don't know what
does :-)
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox