Re: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread Evgeniy Polyakov
On Thu, Apr 27, 2006 at 02:12:09PM -0700, Caitlin Bestler ([EMAIL PROTECTED]) 
wrote:
> So the real issue is when there is an intelligent device that
> uses hardware packet classification to place the packet in
> the correct ring. We don't want to bypass packet filtering,
> but it would be terribly wasteful to reclassify the packet.
> Intelligent NICs will have packet classification capabilities
> to support RDMA and iSCSI. Those capabilities should be available
> to benefit SOCK_STREAM and SOCK_DGRAM users as well without it
> being a choice of either turning all stack control over to
> the NIC or ignorign all NIC capabilities beyound pretending
> to be a dumb Ethernet NIC.

Btw, how is it supposed to work without header split capabale hardware?

-- 
Evgeniy Polyakov
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread Evgeniy Polyakov
On Thu, Apr 27, 2006 at 01:09:18PM -0700, David S. Miller ([EMAIL PROTECTED]) 
wrote:
> Evgeniy, the difference between this and your work is that you did not
> have an intelligent piece of hardware that could be told to recognize
> flows, and only put packets for a specific flow into that's flow's
> buffer pool.

There are the most "intellegent" NICs which use MMIO copy like Realtek 8139 :)
which were used in receiving zero-copy [1] project.

There was special alorithm researched for receiving zero-copy [1] to allow 
to put not page-aligned TCP frames into pages, but there was other
problem when page was committed, since no byte commit is allowed in VFS.

In this case we do not have that problem, but instead we must force userspace to
be very smart when dealing with mapped buffers, instead of simple recv().
And for sending it must be even smarter, since data must be properly
aligned. And what about crappy hardware which can DMA only into limited
memory area, or NIC that can not do sg? Or do we need remapping for NIC
that can not do checksum calculation?

> > If we want to dma data from nic into premapped userspace area, this will
> > strike with message sizes/misalignment/slow read and so on, so
> > preallocation has even more problems.
> 
> I do not really think this is an issue, we put the full packet into
> user space and teach it where the offset is to the actual data.
> We'll do the same things we do today to try and get the data area
> aligned.  User can do whatever is logical and relevant on his end
> to deal with strange cases.
> 
> In fact we can specify that card has to take some care to get data
> area of packet aligned on say an 8 byte boundary or something like
> that.  When we don't have hardware assist, we are going to be doing
> copies.

Userspace must be too smart, and as we saw with various java tests, it
can not be so even now.
And what if pages are shared and several threads are trying to write
into the same remapped area? Will we use COW and be blamed like Mach
and FreeBSD developers? :)

> > I do think that significant win in VJ's tests belongs not to remapping
> > and cache-oriented changes, but to move all protocol processing into
> > process' context.
> 
> I partly disagree.  The biggest win is eliminating all of the control
> overhead (all of "softint RX + protocol demux + IP route lookup +
> socket lookup" is turned into single flow demux), and the SMP safe
> data structure which makes it realistic enough to always move the bulk
> of the packet work to the socket's home cpu.
> 
> I do not think userspace protocol implementation buys enough to
> justify it.  We have to do the protection switch in and out of kernel
> space anyways, so why not still do the protected protocol processing
> work in the kernel?  It is still being done on the user's behalf,
> contributes to his time slice, and avoids all of the terrible issues
> of userspace protocol implementations.

After hard irq softirq is scheduled, then later userspace is scheduled,
at least 2 context switch just to move a packet, and "slow" userspace
code is interrupted by both irqs again...
I run some tests on ppc32 embedded boards which showed that rescheduling
latency tend to have milliseconds delay sometimes (about 4 running processes
on 200mhz cpu), although we do not have some real-time requirements here
it is not a good sign...

> And I also want to note that even if the whole idea explodes and
> cannot be made to work, there are good arguments for transitioning
> to SKB'less drivers for their own sake.  So work will really not
> be lost.
> 
> Let's have 100 different implementations of net channels! :-)

:)

-- 
Evgeniy Polyakov
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: E1000 stopped transmitting in rc3.

2006-04-27 Thread Auke Kok

Dave Jones wrote:

With 2.6.17-rc3, my E1000 won't get a dhcp lease.
Looking at tcpdump and ifconfig output, it's easy to see why.
It's recieving packets, but the packets transmitted field
of ifconfig never increases.

The last version I have built that worked ok was 2.6.17rc2-git3


*puzzled*

the only patch between 2.6.17rc2 and 2.6.17rc3 contains an rx-path patch, but 
nothing that affects tx. All the other patches sent earlier are queued for 
2.6.18 so they don't apply.


Auke
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [LARTC] how to change classful netem loss probability?

2006-04-27 Thread George P Nychis
And if its not possible to change the probability, is there another method I 
can use instead?

> Hi,
> 
> I am using netem to add loss and then adding another qdisc within netem 
> according to the wiki.  Then i want to change the netem drop probability 
> without having to delete the qdisc and recreate it.  I try it but I get 
> invalid argument:
> 
> thorium-ini hedpe # tc qdisc add dev ath0 root handle 1:0 netem drop 1% 
> thorium-ini hedpe # tc qdisc add dev ath0 parent 1:1 handle 10: xcp 
> capacity 54Mbit limit 500 thorium-ini hedpe # tc -s qdisc ls dev ath0 qdisc
> netem 1: limit 1000 loss 1% Sent 0 bytes 0 pkts (dropped 0, overlimits 0) 
> qdisc xcp 10: parent 1:1 capacity 52734Kbit limit 500p Sent 0 bytes 0 pkts
> (dropped 0, overlimits 0) thorium-ini hedpe # tc qdisc change dev ath0
> root handle 1:0 netem drop 1% RTNETLINK answers: Invalid argument 
> thorium-ini hedpe # tc qdisc change dev ath0 root netem drop 1% RTNETLINK
> answers: Invalid argument
> 
> any ideas?
> 
> Thanks! George ___ LARTC mailing
> list LARTC@mailman.ds9a.nl 
> http://mailman.ds9a.nl/cgi-bin/mailman/listinfo/lartc
> 
> 


-- 

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 20/24] NET: e1000: Update truesize with the length of the packet for packet split

2006-04-27 Thread Greg KH
-stable review patch.  If anyone has any objections, please let us know.

--

Update skb with the real packet size.


Signed-off-by: Jesse Brandeburg <[EMAIL PROTECTED]>
Signed-off-by: Auke Kok <[EMAIL PROTECTED]>
Signed-off-by: John Ronciak <[EMAIL PROTECTED]>
Signed-off-by: Greg Kroah-Hartman <[EMAIL PROTECTED]>

---
 drivers/net/e1000/e1000_main.c |1 +
 1 file changed, 1 insertion(+)

--- linux-2.6.16.11.orig/drivers/net/e1000/e1000_main.c
+++ linux-2.6.16.11/drivers/net/e1000/e1000_main.c
@@ -3851,6 +3851,7 @@ e1000_clean_rx_irq_ps(struct e1000_adapt
skb_shinfo(skb)->nr_frags++;
skb->len += length;
skb->data_len += length;
+   skb->truesize += length;
}
 
e1000_rx_checksum(adapter, staterr,

--
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


E1000 stopped transmitting in rc3.

2006-04-27 Thread Dave Jones
With 2.6.17-rc3, my E1000 won't get a dhcp lease.
Looking at tcpdump and ifconfig output, it's easy to see why.
It's recieving packets, but the packets transmitted field
of ifconfig never increases.

The last version I have built that worked ok was 2.6.17rc2-git3

NIC is ..
03:0e.0 Ethernet controller: Intel Corporation 82545GM Gigabit Ethernet 
Controller (rev 04)
(8086:1026)

Dave

-- 
http://www.codemonkey.org.uk
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 0/10] [IOAT] I/OAT patches repost

2006-04-27 Thread Rick Jones

Chris Leech wrote:

Netperf2 TOT now accesses the buffer that was just recv()'d rather than
the one that is about to be recv()'d.



We've posted netperf2 results with I/OAT enabled/disabled and the data
access option on/off at
http://kernel.org/pub/linux/kernel/people/grover/ioat/netperf-icb-1.5-postscaling-both.pdf



calling it netperf data verification is a quite overstated - all netperf 
does is read from or write to the buffer.  there is no check of data 
integrity or anything


rick jones
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 0/10] [IOAT] I/OAT patches repost

2006-04-27 Thread Chris Leech
> Netperf2 TOT now accesses the buffer that was just recv()'d rather than
> the one that is about to be recv()'d.

We've posted netperf2 results with I/OAT enabled/disabled and the data
access option on/off at
http://kernel.org/pub/linux/kernel/people/grover/ioat/netperf-icb-1.5-postscaling-both.pdf

This link has also been added to the I/OAT page on the LinuxNet wiki.

- Chris
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 0/10] [IOAT] I/OAT patches repost

2006-04-27 Thread Chris Leech
On 4/20/06, David S. Miller <[EMAIL PROTECTED]> wrote:
> Yes, and it means that the memory bandwidth costs are equivalent
> between I/O AT and cpu copy.

The following is a response from the I/OAT architects.  I only point
out that this is not coming directly from me because I have not seen
the data to verify the claims regarding the speed of a copy vs a load
and the cost of the rep mov instruction.  I'll encourage more direct
participation in this discussion from the architects moving forward.

- Chris

Let's talk about the caching benefits that is seemingly lost when
using the DMA engine. The intent of the DMA engine is to save CPU
cycles spent in copying data (rep mov). In cases where the destination
is already warm in cache (due to destination buffer re-use) and the
source is in memory, the cycles spent in a host copy is not just due
to the cache misses it encounters in the process of bringing in the
source but also due to the execution of rep move itself within the
host core. If you contrast this to simply touching (loading) the data
residing in memory, the cost of this load is primarily the cost of the
cache misses and not so much CPU execution time. Given this, some of
the following points are noteworthy:

1. While the DMA engine forces the destination to be in memory and
touching it may cause the same number of observable cache misses as a
host copy assuming a cache warmed destination, the cost of the host
copy (in terms of CPU cycles) is much more than the cost of the touch.

2. CPU hardware prefetchers do a pretty good job of staying ahead of
the fetch stream to minimize cache misses. So for loads of medium to
large buffers, cache misses form a much smaller component of the data
fetch time…most of it is dominated by front side bus (FSB) or Memory
bandwidth. For small buffers, we do not use the DMA engine but if we
had to, we would insert SW prefetches that do reasonably well.

3. If the destination wasn't already warm in cache i.e., it was in
memory or some CPU other cache, host copy will have to snoop and bring
the destination in and will encounter additional misses on the
destination buffer as well. These misses are the same as those
encountered in #1 above when using the DMA engine and touching the
data afterwards. So in effect it becomes a wash when compared to the
DMA engine's behavior. The case where the destination is already warm
in cache is common in benchmarks such as iperf, ttcp etc. where the
same buffer is reused over and over again. Real applications typically
will not exhibit this aggressive buffer re-use behavior.

4. It may take a large number of packets (and several interrupts) to
satisfy a large posted buffer (say 64KB). Even if you use host copy to
warm the cache with the destination, there is no guarantee that some
or all of the destination will stay in the cache before the
application has a chance to read the data.

5. The source data payload (skb ->data) is typically needed only once
for the copy and has no use later. The host copy brings it into the
cache and may end up polluting the cache, and consuming FSB bandwidth
whereas the DMA engine avoids this altogether.

The IxChariot data posted earlier that touches the data and yet shows
I/OAT benefit is due to some of the reasons above. Bottom line is that
I agree with the cache benefit argument of host copy for small buffers
(64B to 512B) but for larger buffers and certain application scenarios
(destination in memory), the DMA engine will show better performance
regardless of where the destination buffer resided to begin with and
where it is accessed from.
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: IP1000 gigabit nic driver

2006-04-27 Thread David Vrabel

Francois Romieu wrote:

David Gómez <[EMAIL PROTECTED]> :
[...]

Does anybody in this list know why the IP1000 driver is not
included in the kernel ?


Afaik the driver has never been submitted for inclusion.
At least not on netdev@vger.kernel.org (hint, hint).

[...]

The card in question is:

Sundance Technology Inc IC Plus IP1000

and the driver can be found in sundance web, sources 


URL please ?


included. I tried to contact the author but my email
bounced.

There's no LICENSE in the source, just copyrigth
sentences in the .c files, so i'm not sure under
which license it's distributed :-?.


/me goes to http://www.icplus.com.tw/driver-pp-IP1000A.html

$ unzip -c IP1000A-Linux-driver-v2.09f.zip | grep MODULE_LICENSE
MODULE_LICENSE("GPL");

It's a bit bloaty but it does not seem too bad (not mergeable "as
is" though). Do you volunteer to test random cra^W^W carefully
engineered code on your computer to help the rework/merging process ?


I finally got around to putting a 2nd NIC in my box that has one of this 
chips and was going to start fixing the driver up and preparing it for 
submission this weekend.  Or I might try rewriting from scratch based on 
the datasheet depending on how horrific the code looks on closer inspection.


Not got a whole lot of time to do this so no timescale for completion...

David Vrabel

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 20/32] rt2x00: byte ordering correctness

2006-04-27 Thread Christoph Hellwig
On Fri, Apr 28, 2006 at 12:03:12AM +0200, Ivo van Doorn wrote:
> From: Ivo van Doorn <[EMAIL PROTECTED]>
> 
> Fix various little/big endian conversions.
> rt2500pci should use cpu_to_le32 and rt2500usb should not.

While you're at it can you add __be* annotations to the hardware
datastructures so the endianess handling can be verified using sparse?
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 3/32] rt2x00: use pci_*_consistent for DMA mapping

2006-04-27 Thread Christoph Hellwig
On Fri, Apr 28, 2006 at 12:02:52AM +0200, Ivo van Doorn wrote:
> From: Ivo van Doorn <[EMAIL PROTECTED]>
> 
> Instead of dma_*_coherent
> use pci_*consistent functions.

No point in doing that, quite reverse as you use the gfp_mask argument
which is a (small) pessimation here.

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH 11/32] rt2x00: Add more register defines

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

During the work on rt2x00 several new registers could be defined.
This will add all those new registers, and will in the next
couple of patches be used.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h  
2006-04-27 21:36:19.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
2006-04-27 21:43:27.0 +0200
@@ -43,6 +43,13 @@
 #define RF5222 0x0010
 
 /*
+ * RT2560 version
+ */
+#define RT2560_VERSION_B   2
+#define RT2560_VERSION_C   3
+#define RT2560_VERSION_D   4
+
+/*
  * Control/Status Registers(CSR).
  * Some values are set in TU, whereas 1 TU == 1024 us.
  */
@@ -558,15 +565,23 @@
  * Statistic Register.
  * CNT1: PLCP error count.
  * CNT2: Long error count.
- * CNT3: CCA false alarm count.
- * CNT4: Rx FIFO overflow count.
- * CNT5: Tx FIFO underrun count.
  */
 #define TIMECSR2   0x00a8
 #define CNT1   0x00ac
 #define CNT2   0x00b0
 #define TIMECSR3   0x00b4
+
+/*
+ * CNT3: CCA false alarm count.
+ */
 #define CNT3   0x00b8
+#define CNT3_FALSE_CCA FIELD32(0x)
+
+/*
+ * Statistic Register.
+ * CNT4: Rx FIFO overflow count.
+ * CNT5: Tx FIFO underrun count.
+ */
 #define CNT4   0x00bc
 #define CNT5   0x00c0
 
@@ -840,6 +855,10 @@
  * BBPCSR1: BBP TX configuration.
  */
 #define BBPCSR10x015c
+#define BBPCSR1_CCKFIELD32(0x0003)
+#define BBPCSR1_CCK_FLIP   FIELD32(0x0004)
+#define BBPCSR1_OFDM   FIELD32(0x0003)
+#define BBPCSR1_OFDM_FLIP  FIELD32(0x0004)
 
 /*
  * Dual band configuration registers.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.h  
2006-04-27 21:42:29.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.h
2006-04-27 21:43:27.0 +0200
@@ -160,10 +160,28 @@
 #define MAC_CSR19  0x0426
 
 /*
- * LED control registers.
+ * MAC_CSR20: LED control register.
+ * ACTIVITY: 0: idle, 1: active.
+ * LINK: 0: linkoff, 1: linkup.
+ * ACTIVITY_POLARITY: 0: active low, 1: active high.
  */
 #define MAC_CSR20  0x0428
+#define MAC_CSR20_ACTIVITY FIELD16(0x0001)
+#define MAC_CSR20_LINK FIELD16(0x0002)
+#define MAC_CSR20_ACTIVITY_POLARITYFIELD16(0x0004)
+
+/*
+ * MAC_CSR21: LED control register.
+ * ON_PERIOD: On period, default 70ms.
+ * OFF_PERIOD: Off period, default 30ms.
+ */
 #define MAC_CSR21  0x042a
+#define MAC_CSR21_ON_PERIODFIELD16(0x00ff)
+#define MAC_CSR21_OFF_PERIOD   FIELD16(0xff00)
+
+/*
+ * Collision window control register.
+ */
 #define MAC_CSR22  0x042c
 
 /*
@@ -373,10 +391,18 @@
 /*
  * BBP pre-TX registers.
  * PHY_CSR5: BBP pre-TX CCK.
- * PHY_CSR6: BBP pre-TX OFDM.
  */
 #define PHY_CSR5   0x04ca
+#define PHY_CSR5_CCK   FIELD16(0x0003)
+#define PHY_CSR5_CCK_FLIP  FIELD16(0x0004)
+
+/*
+ * BBP pre-TX registers.
+ * PHY_CSR6: BBP pre-TX OFDM.
+ */
 #define PHY_CSR6   0x04cc
+#define PHY_CSR6_OFDM  FIELD16(0x0003)
+#define PHY_CSR6_OFDM_FLIP FIELD16(0x0004)
 
 /*
  * PHY_CSR7: BBP access register 0.
@@ -459,6 +485,12 @@
  * HW MAC address.
  */
 #define EEPROM_MAC_ADDR0x0004
+#define EEPROM_MAC_ADDR_BYTE0  FIELD16(0x00ff)
+#define EEPROM_MAC_ADDR_BYTE1  FIELD16(0xff00)
+#define EEPROM_MAC_ADDR_BYTE2  FIELD16(0x00ff)
+#define EEPROM_MAC_ADDR_BYTE3  FIELD16(0xff00)
+#define EEPROM_MAC_ADDR_BYTE4  FIELD16(0x00ff)
+#define EEPROM_MAC_ADDR_BYTE5  FIELD16(0xff00)
 
 /*
  * EEPROM antenna.


pgpJBQTAX9fIU.pgp
Description: PGP signature


[PATCH 13/32] rt2x00: Tune link depending on link quality

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Add link tuning capabilities, and call this function
every time the rxdone handler has finished.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:42:29.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:45:08.0 +0200
@@ -618,6 +618,41 @@ rt2400pci_config_rate(struct rt2x00_pci 
 }
 
 /*
+ * Link tuning
+ */
+static void
+rt2400pci_link_tuner(struct rt2x00_pci *rt2x00pci)
+{
+   u8  reg;
+   charfalse_cca_delta;
+
+   /*
+* Read false CCA counter.
+*/
+   rt2x00_bbp_read(rt2x00pci, 39, ®);
+
+   /*
+* Determine difference with previous CCA counter.
+*/
+   false_cca_delta = reg - rt2x00pci->false_cca;
+   rt2x00pci->false_cca = reg;
+
+   /*
+* Check if the difference is higher than the
+* threshold and if so, tune the link.
+*/
+   if (false_cca_delta >= 8) {
+   /*
+* Read and update RX AGC VGC.
+*/
+   rt2x00_bbp_read(rt2x00pci, 13, ®);
+   reg += 2;
+   if (reg < 0x20)
+   rt2x00_bbp_write(rt2x00pci, 13, reg);
+   }
+}
+
+/*
  * TX descriptor initialization
  */
 static void
@@ -779,6 +814,9 @@ rt2400pci_rxdone(void *data)
 
memcpy(skb_put(skb, size), entry->data_addr, size);
 
+   ring->params.rx.ssi =
+   rt2x00_get_field32(rxd->word2, RXD_W2_RSSI);
+
__ieee80211_rx(net_dev, skb, &ring->params.rx);
}
 
@@ -786,6 +824,11 @@ rt2400pci_rxdone(void *data)
 
rt2x00_ring_index_inc(&rt2x00pci->rx);
}
+
+   /*
+* Tune link for optimal performance.
+*/
+   rt2400pci_link_tuner(rt2x00pci);
 }
 
 static void
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-04-27 21:36:19.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
2006-04-27 21:45:08.0 +0200
@@ -926,6 +926,11 @@ struct rt2x00_pci{
struct workqueue_struct *workqueue;
 
/*
+* False CCA count.
+*/
+   int false_cca;
+
+   /*
 * EEPROM bus width.
 */
u8  eeprom_width;
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:42:29.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:45:08.0 +0200
@@ -661,6 +661,51 @@ rt2500pci_config_rate(struct rt2x00_pci 
 }
 
 /*
+ * Link tuning
+ */
+static void
+rt2500pci_link_tuner(struct rt2x00_pci *rt2x00pci, char rssi)
+{
+   u32 reg;
+   u8  reg_r17;
+
+   /*
+* Don't perform any tuning during scan.
+*/
+   if (rt2x00pci->scan)
+   return;
+
+   rt2x00_register_read(rt2x00pci, CSR0, ®);
+   rt2x00_bbp_read(rt2x00pci, 17, ®_r17);
+
+   if (reg < RT2560_VERSION_D)
+   goto dynamic_cca_tune;
+
+   if (rssi < 40) {
+   if (reg_r17 >= 0x41)
+   rt2x00_bbp_write(rt2x00pci, 17, reg_r17);
+   return;
+   } else if (rssi >= 62) {
+   if (reg_r17 != 0x50)
+   rt2x00_bbp_write(rt2x00pci, 17, 0x50);
+   return;
+   } else if (reg_r17 >= 0x41) {
+   rt2x00_bbp_write(rt2x00pci, 17, reg_r17);
+   return;
+   }
+
+dynamic_cca_tune:
+   rt2x00_register_read(rt2x00pci, CNT3, ®);
+
+   reg = rt2x00_get_field32(reg, CNT3_FALSE_CCA);
+
+   if (reg > 512 && reg_r17 < 0x40)
+   rt2x00_bbp_write(rt2x00pci, 17, ++reg_r17);
+   else if (reg < 100 && reg_r17 > 0x32)
+   rt2x00_bbp_write(rt2x00pci, 17, --reg_r17);
+}
+
+/*
  * TX descriptor initialization
  */
 static void
@@ -819,6 +864,14 @@ rt2500pci_rxdone(void *data)
struct sk_buff  *skb;
struct rxd  *rxd;
u16 size;
+   u8  rssi_count;
+   chartotal_rssi;
+
+   /*
+* Initialize variable for average RSSI calculation.
+*/
+   rssi_count = 0;

[PATCH 24/32] rt2x00: Use correct desc_addr and data_addr

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

USB buffer don't have a seperate descriptor ring and data ring.
The location of the descriptor area and data area depends
on the type of ring. Add functions to determine the correct
location and use these instead of the invalid desc_addr and data_addr
pointers.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:54:33.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:55:14.0 +0200
@@ -740,7 +740,7 @@ rt2500usb_rxdone(void *data)
 
while (1) {
entry = rt2x00_get_data_entry(ring);
-   rxd = entry->desc_addr;
+   rxd = rt2x00usb_rxdesc_addr(entry);
 
/*
* There has been a problem. Ignore packet.
@@ -769,7 +769,8 @@ rt2500usb_rxdone(void *data)
 
skb_reserve(skb, NET_IP_ALIGN);
 
-   memcpy(skb_put(skb, size), entry->data_addr, size);
+   memcpy(skb_put(skb, size),
+   rt2x00usb_rxdata_addr(entry), size);
 
rt2x00usb->rx_params.ssi =
rt2x00_get_field32(rxd->word1, RXD_W1_RSSI);
@@ -805,7 +806,7 @@ rt2500usb_txdone(void *data)
 
 while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
-   txd = entry->desc_addr;
+   txd = rt2x00usb_txdesc_addr(entry);
 
ack = rt2x00_get_field32(txd->word0, TXD_W0_ACK);

@@ -937,16 +938,14 @@ rt2500usb_alloc_ring(
entry[counter].urb = usb_alloc_urb(0, GFP_KERNEL);
else
entry[counter].urb = NULL;
-   if (entry[counter].urb == NULL)
+   if (!entry[counter].urb)
status = -ENOMEM;
entry[counter].skb = NULL;
-   entry[counter].desc_addr = ring->data_addr
-   + (counter * ring->desc_size);
entry[counter].data_addr = ring->data_addr
-   + (ring->stats.limit * ring->desc_size)
+   + (counter * ring->desc_size)
+ (counter * ring->data_size);
entry[counter].data_dma = ring->data_dma
-   + (ring->stats.limit * ring->desc_size)
+   + (counter * ring->desc_size)
+ (counter * ring->data_size);
}
 
@@ -959,7 +958,7 @@ rt2500usb_free_ring(struct rt2x00_usb *r
struct  data_entry  *entry;
u8  counter;
 
-   if (ring->entry)
+   if (!ring->entry)
goto exit;
 
entry = (struct data_entry*)ring->entry;
@@ -1091,9 +1090,9 @@ rt2500usb_init_registers(struct rt2x00_u
return -EBUSY;
 
rt2x00_vendor_request(rt2x00usb, USB_DEVICE_MODE,
-   USB_VENDOR_REQUEST_OUT, USB_MODE_TEST, 0x00, NULL, 0);
+   USB_VENDOR_REQUEST_OUT, 0x00, USB_MODE_TEST, NULL, 0);
rt2x00_vendor_request(rt2x00usb, USB_SINGLE_WRITE,
-   USB_VENDOR_REQUEST_OUT, 0x0308, 0x00f0, NULL, 0);
+   USB_VENDOR_REQUEST_OUT, 0x0308, 0xf0, NULL, 0);
 
rt2x00_register_write(rt2x00usb, TXRX_CSR2, 0x0001);
rt2x00_register_write(rt2x00usb, MAC_CSR13, 0x);
@@ -1242,9 +1241,9 @@ rt2500usb_tx(struct net_device *net_dev,
return NET_RX_DROP;
 
entry = rt2x00_get_data_entry(ring);
-   txd = entry->desc_addr;
+   txd = rt2x00usb_txdesc_addr(entry);
 
-   memcpy(entry->data_addr, skb->data, skb->len);
+   memcpy(rt2x00usb_txdata_addr(entry), skb->data, skb->len);
rt2500usb_write_tx_desc(rt2x00usb, txd, skb, control);
entry->skb = skb;
 
@@ -1621,8 +1620,9 @@ rt2500usb_beacon_update(struct net_devic
 */
control->queue = IEEE80211_TX_QUEUE_BEACON;
 
-   memcpy(entry->data_addr, skb->data, skb->len);
-   rt2500usb_write_tx_desc(rt2x00usb, entry->desc_addr, skb, control);
+   memcpy(rt2x00usb_txdata_addr(entry), skb->data, skb->len);
+   rt2500usb_write_tx_desc(rt2x00usb,
+   rt2x00usb_txdesc_addr(entry), skb, control);
 
usb_fill_bulk_urb(
entry->urb,
@@ -1658,6 +1658,14 @@ rt2500usb_init_eeprom(struct rt2x00_usb 
rt2x00_set_chip(&rt2x00usb->chip, RT2570,
rt2x00_get_field16(eeprom, EEPROM_ANTENNA_RF_TYPE));
 
+   if (!rt2x00_rf(&rt2x00usb->chip, RF2522)
+   && !rt2x00_rf(&rt2x00usb->chip, RF2523)
+   && !rt2x00_rf(&rt2x00usb->chip, RF2524)
+   && !rt2x00_rf(&rt2x00usb->chip, RF2525)
+   && !rt2x00_rf(&rt2x00usb->chip, RF2525E)
+   && !rt2x00_rf(&rt2x

[PATCH 15/32] rt2x00: Move rx_params to correct location

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Store rx_params seperately outside the ring structure.
This is more safer and required because of some changes
in the way the rings are stored in the structure in the following
patches.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:47:22.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:47:52.0 +0200
@@ -475,8 +475,8 @@ rt2400pci_config_channel(struct rt2x00_p
/*
 * Update active info for RX.
 */
-   rt2x00pci->rx.params.rx.freq = freq;
-   rt2x00pci->rx.params.rx.channel = channel;
+   rt2x00pci->rx_params.freq = freq;
+   rt2x00pci->rx_params.channel = channel;
 
/*
 * Clear false CRC during channel switch.
@@ -534,7 +534,7 @@ rt2400pci_config_antenna(struct rt2x00_p
/*
 * Update active info for RX.
 */
-   rt2x00pci->rx.params.rx.antenna = antenna;
+   rt2x00pci->rx_params.antenna = antenna;
 }
 
 static void
@@ -814,10 +814,10 @@ rt2400pci_rxdone(void *data)
 
memcpy(skb_put(skb, size), entry->data_addr, size);
 
-   ring->params.rx.ssi =
+   rt2x00pci->rx_params.ssi =
rt2x00_get_field32(rxd->word2, RXD_W2_RSSI);
 
-   __ieee80211_rx(net_dev, skb, &ring->params.rx);
+   __ieee80211_rx(net_dev, skb, &rt2x00pci->rx_params);
}
 
rt2x00_set_field32(&rxd->word0, RXD_W0_OWNER_NIC, 1);
@@ -981,8 +981,8 @@ rt2400pci_alloc_ring(
/*
 * Initialize ring parameters.
 */
-   ring->params.tx.cw_min = 5; /* cw_min: 2^5 = 32. */
-   ring->params.tx.cw_max = 10;/* cw_max: 2^10 = 1024. */
+   ring->tx_params.cw_min = 5; /* cw_min: 2^5 = 32. */
+   ring->tx_params.cw_max = 10;/* cw_max: 2^10 = 1024. */
 
rt2x00_ring_index_clear(ring);
 
@@ -1374,7 +1374,7 @@ rt2400pci_tx(struct net_device *net_dev,
 * queue. This is the alternative since we cannot
 * set the CWmin and CWmax per descriptor.
 */
-   rt2400pci_config_cw(rt2x00pci, &ring->params.tx);
+   rt2400pci_config_cw(rt2x00pci, &ring->tx_params);
rt2x00_register_write(rt2x00pci, TXCSR0, reg);
 
return 0;
@@ -1544,7 +1544,7 @@ rt2400pci_config_update(void *data)
/*
 * Update active info for RX.
 */
-   rt2x00pci->rx.params.rx.phymode = conf->phymode;
+   rt2x00pci->rx_params.phymode = conf->phymode;
 }
 
 static int
@@ -1599,7 +1599,7 @@ rt2400pci_scan(void *data)
 * Switch channel and update active info for RX.
 */
if (rt2x00pci->scan->state == IEEE80211_SCAN_START) {
-   rt2x00pci->rx.params.rx.phymode =
+   rt2x00pci->rx_params.phymode =
rt2x00pci->scan->conf.scan_phymode;
 
rt2400pci_config_channel(rt2x00pci,
@@ -1610,7 +1610,7 @@ rt2400pci_scan(void *data)
rt2400pci_config_txpower(rt2x00pci,
rt2x00pci->scan->conf.scan_power_level);
} else {
-   rt2x00pci->rx.params.rx.phymode =
+   rt2x00pci->rx_params.phymode =
rt2x00pci->scan->conf.running_phymode;
 
rt2400pci_config_channel(rt2x00pci,
@@ -1726,7 +1726,7 @@ rt2400pci_conf_tx(struct net_device *net
else
return -EINVAL;
 
-   memcpy(&ring->params, params, sizeof(*params));
+   memcpy(&ring->tx_params, params, sizeof(*params));
 
/*
 * TODO: We can't use different cw_min and cw_max variables
@@ -1737,14 +1737,14 @@ rt2400pci_conf_tx(struct net_device *net
 * RT2400 registers require to know the bit number 'n'.
 */
if (params->cw_min)
-   ring->params.tx.cw_min = HIGHEST_BIT16(params->cw_min) + 1;
+   ring->tx_params.cw_min = HIGHEST_BIT16(params->cw_min) + 1;
else
-   ring->params.tx.cw_min = 5; /* cw_min: 2^5 = 32. */
+   ring->tx_params.cw_min = 5; /* cw_min: 2^5 = 32. */
 
if (params->cw_max)
-   ring->params.tx.cw_max = HIGHEST_BIT16(params->cw_max) + 1;
+   ring->tx_params.cw_max = HIGHEST_BIT16(params->cw_max) + 1;
else
-   ring->params.tx.cw_max = 10; /* cw_min: 2^10 = 1024. */
+   ring->tx_params.cw_max = 10; /* cw_min: 2^10 = 1024. */
 
return 0;
 }
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-

[PATCH 32/32] rt2x00: misc fixes

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Misc. small fixes. Add small comments,
remove unwanted whitespaces etc.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 22:05:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 22:06:22.0 +0200
@@ -1003,7 +1003,7 @@ rt2400pci_txdone(void *data)
int tx_status;
int ack;
 
-while (!rt2x00_ring_empty(ring)) {
+   while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
txd = entry->desc_addr;
 
@@ -1212,7 +1212,7 @@ rt2400pci_free_ring(struct rt2x00_pci *r
ring->data_addr, ring->data_dma);
ring->data_addr = NULL;
 
-   kfree(ring->entry);
+   kfree(ring->entry);
ring->entry = NULL;
 }
 
@@ -1318,6 +1318,9 @@ rt2400pci_init_rings(struct rt2x00_pci *
 {
u32 reg;
 
+   /*
+* Initialize rings.
+*/
rt2400pci_init_rxdesc(rt2x00pci, &rt2x00pci->ring[RING_RX]);
rt2400pci_init_txdesc(rt2x00pci, &rt2x00pci->ring[RING_TX]);
rt2400pci_init_txdesc(rt2x00pci, &rt2x00pci->ring[RING_ATIM]);
@@ -1847,7 +1850,7 @@ rt2400pci_config_interface(struct net_de
rt2400pci_config_bssid(rt2x00pci, conf->bssid);
 
return 0;
- }
+}
 
 static void
 rt2400pci_set_multicast_list(struct net_device *net_dev,
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 22:05:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 22:06:22.0 +0200
@@ -487,7 +487,7 @@ rt2500pci_config_channel(struct rt2x00_p
 
if (rt2x00_rf(&rt2x00pci->chip, RF5222)) {
if (channel < 14) {
-   rf1 = cpu_to_le32(0x00022020);
+   rf1 = cpu_to_le32(0x00022020);
rf4 = cpu_to_le32(0x0a0b);
} else if (channel == 14) {
rf1 = cpu_to_le32(0x00022010);
@@ -501,7 +501,7 @@ rt2500pci_config_channel(struct rt2x00_p
} else if (channel < 161) {
rf1 = cpu_to_le32(0x00022020);
rf4 = cpu_to_le32(0x0a07);
-   }
+   }
}
 
INFO("Switching channel. RF1: 0x%08x, RF2: 0x%08x, RF3: 0x%08x, "
@@ -1091,7 +1091,7 @@ rt2500pci_txdone(void *data)
int tx_status;
int ack;
 
-while (!rt2x00_ring_empty(ring)) {
+   while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
txd = entry->desc_addr;
 
@@ -1301,7 +1301,7 @@ rt2500pci_free_ring(struct rt2x00_pci *r
ring->data_addr, ring->data_dma);
ring->data_addr = NULL;
 
-   kfree(ring->entry);
+   kfree(ring->entry);
ring->entry = NULL;
 }
 
@@ -2438,7 +2438,7 @@ rt2500pci_init_hw_channels(struct rt2x00
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
channels[counter].val =
cpu_to_le32(vals[counter] | rf2_base);
-   }
+   }
if (rt2x00_rf(&rt2x00pci->chip, RF5222)) {
static u32 vals[] = {
0x00018896, 0x0001889a, 0x0001889e, 0x000188a2,
@@ -2453,7 +2453,7 @@ rt2500pci_init_hw_channels(struct rt2x00

for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
(chan++)->val = cpu_to_le32(vals[counter]);
-   }
+   }
 
/*
 * Set TX power, each EEPROM TXpower entry
@@ -2472,7 +2472,7 @@ rt2500pci_init_hw_channels(struct rt2x00
rt2x00_get_field16(eeprom, EEPROM_TXPOWER_2);
if (channels[(counter * 2) + 1].power_level > 0x20)
channels[(counter * 2) + 1].power_level = 0x18;
-   }
+   }
 
/*
 * Set device specific, but channel independent RF values.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 22:05:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 22:08:38.0 +0200
@@ -335,7 +335,7 @@ rt2500usb_config_channel(struct rt2x00_u
|| rt2x00_rf(&rt2x00usb->chip, RF2524)
   

[PATCH 12/32] rt2x00: Add USB ID's

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Remove the rt73usb ID that accidently sneaked into
rt2500usb. And add new rt2500usb ID's.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:42:29.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:44:33.0 +0200
@@ -2192,6 +2192,7 @@ static struct usb_device_id rt2500usb_de
{ USB_DEVICE(0x0b05, 0x1707), .driver_info = RT2570},
/* Belkin */
{ USB_DEVICE(0x050d, 0x7050), .driver_info = RT2570},
+   { USB_DEVICE(0x050d, 0x7051), .driver_info = RT2570},
{ USB_DEVICE(0x050d, 0x705a), .driver_info = RT2570},
/* Cisco Systems */
{ USB_DEVICE(0x13b1, 0x000d), .driver_info = RT2570},
@@ -2201,7 +2202,6 @@ static struct usb_device_id rt2500usb_de
{ USB_DEVICE(0x14b2, 0x3c02), .driver_info = RT2570},
/* D-LINK */
{ USB_DEVICE(0x2001, 0x3c00), .driver_info = RT2570},
-   { USB_DEVICE(0x07d1, 0x3c03), .driver_info = RT2570},
/* Gigabyte */
{ USB_DEVICE(0x1044, 0x8001), .driver_info = RT2570},
{ USB_DEVICE(0x1044, 0x8007), .driver_info = RT2570},
@@ -2224,6 +2224,10 @@ static struct usb_device_id rt2500usb_de
{ USB_DEVICE(0x0707, 0xee13), .driver_info = RT2570},
/* Spairon */
{ USB_DEVICE(0x114b, 0x0110), .driver_info = RT2570},
+   /* Trust */
+   { USB_DEVICE(0x0eb0, 0x9020), .driver_info = RT2570},
+   /* Zinwell */
+   { USB_DEVICE(0x5a57, 0x0260), .driver_info = RT2570},
{0,}
 };
 


pgpUozaXKP7GJ.pgp
Description: PGP signature


[PATCH 3/32] rt2x00: use pci_*_consistent for DMA mapping

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Add linux/dma-mapping.h header to allow compilation
on some architectures. Instead of dma_*_coherent
use pci_*consistent functions.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:36:17.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:37:02.0 +0200
@@ -29,6 +29,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -928,8 +929,8 @@ rt2400pci_alloc_ring(
/*
 * Allocate DMA memory for descriptor and buffer.
 */
-   ring->data_addr = dma_alloc_coherent(&rt2x00pci->pci_dev->dev,
-   rt2x00_get_ring_size(ring), &ring->data_dma, GFP_KERNEL);
+   ring->data_addr = pci_alloc_consistent(rt2x00pci->pci_dev,
+   rt2x00_get_ring_size(ring), &ring->data_dma);
if (!ring->data_addr) {
kfree(ring->entry);
return -ENOMEM;
@@ -959,7 +960,7 @@ static void
 rt2400pci_free_ring(struct rt2x00_pci *rt2x00pci, struct data_ring *ring)
 {
if (ring->data_addr)
-   dma_free_coherent(&rt2x00pci->pci_dev->dev,
+   pci_free_consistent(rt2x00pci->pci_dev,
rt2x00_get_ring_size(ring),
ring->data_addr, ring->data_dma);
ring->data_addr = NULL;
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:36:17.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:37:02.0 +0200
@@ -29,6 +29,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -964,8 +965,8 @@ rt2500pci_alloc_ring(
/*
 * Allocate DMA memory for descriptor and buffer.
 */
-   ring->data_addr = dma_alloc_coherent(&rt2x00pci->pci_dev->dev,
-   rt2x00_get_ring_size(ring), &ring->data_dma, GFP_KERNEL);
+   ring->data_addr = pci_alloc_consistent(rt2x00pci->pci_dev,
+   rt2x00_get_ring_size(ring), &ring->data_dma);
if (!ring->data_addr) {
kfree(ring->entry);
return -ENOMEM;
@@ -995,7 +996,7 @@ static void
 rt2500pci_free_ring(struct rt2x00_pci *rt2x00pci, struct data_ring *ring)
 {
if (ring->data_addr)
-   dma_free_coherent(&rt2x00pci->pci_dev->dev,
+   pci_free_consistent(rt2x00pci->pci_dev,
rt2x00_get_ring_size(ring),
ring->data_addr, ring->data_dma);
ring->data_addr = NULL;


pgpJFezwDatSd.pgp
Description: PGP signature


[PATCH 17/32] rt2x00: Put net_device structure in data_ring

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Change the structure stored in the data_ring structure
from the rt2x00_pci or rt2x00_usb to net_device.
This allows for better type checking, and the net_dev
is more often used in the interrupt handlers.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:48:21.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:49:08.0 +0200
@@ -760,10 +760,8 @@ rt2400pci_write_tx_desc(
 static void
 rt2400pci_beacondone(void *data)
 {
-   struct data_ring*ring = (struct data_ring*)data;
-   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)ring->dev;
-   struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
-   struct sk_buff  *skb;
+   struct data_ring*ring = (struct data_ring*)data;
+   struct sk_buff  *skb;
struct ieee80211_tx_control beacon;
 
memset(&beacon, 0x00, sizeof(beacon));
@@ -771,11 +769,11 @@ rt2400pci_beacondone(void *data)
/*
 * TODO: What value should be passed as bss_idx?
 */
-   skb = ieee80211_beacon_get(net_dev, 0, &beacon);
+   skb = ieee80211_beacon_get(ring->net_dev, 0, &beacon);
if (!skb)
return;
 
-   rt2400pci_beacon_update(net_dev, skb, &beacon);
+   rt2400pci_beacon_update(ring->net_dev, skb, &beacon);
 
dev_kfree_skb_any(skb);
 }
@@ -784,8 +782,8 @@ static void
 rt2400pci_rxdone(void *data)
 {
struct data_ring*ring = (struct data_ring*)data;
-   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)ring->dev;
-   struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
+   struct rt2x00_pci   *rt2x00pci =
+   ieee80211_dev_hw_data(ring->net_dev);
struct data_entry   *entry;
struct sk_buff  *skb;
struct rxd  *rxd;
@@ -817,7 +815,8 @@ rt2400pci_rxdone(void *data)
rt2x00pci->rx_params.ssi =
rt2x00_get_field32(rxd->word2, RXD_W2_RSSI);
 
-   __ieee80211_rx(net_dev, skb, &rt2x00pci->rx_params);
+   __ieee80211_rx(ring->net_dev,
+   skb, &rt2x00pci->rx_params);
}
 
rt2x00_set_field32(&rxd->word0, RXD_W0_OWNER_NIC, 1);
@@ -835,8 +834,8 @@ static void
 rt2400pci_txdone(void *data)
 {
struct data_ring*ring = (struct data_ring*)data;
-   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)ring->dev;
-   struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
+   struct rt2x00_pci   *rt2x00pci =
+   ieee80211_dev_hw_data(ring->net_dev);
struct data_entry   *entry;
struct txd  *txd;
int tx_status;
@@ -881,7 +880,8 @@ rt2400pci_txdone(void *data)
entry->tx_status.retry_count = rt2x00_get_field32(
txd->word0, TXD_W0_RETRY_COUNT);
 
-   ieee80211_tx_status(net_dev, entry->skb, &entry->tx_status);
+   ieee80211_tx_status(ring->net_dev,
+   entry->skb, &entry->tx_status);
 
rt2x00_set_field32(&txd->word0, TXD_W0_VALID, 0);
entry->skb = NULL;
@@ -975,7 +975,7 @@ rt2400pci_alloc_ring(
/*
 *Set device structure.
 */
-   ring->dev = rt2x00pci;
+   ring->net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
 
/*
 * Initialize work structure for deferred work.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:48:21.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:49:08.0 +0200
@@ -834,10 +834,8 @@ rt2500pci_write_tx_desc(
 static void
 rt2500pci_beacondone(void *data)
 {
-   struct data_ring*ring = (struct data_ring*)data;
-   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)ring->dev;
-   struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
-   struct sk_buff  *skb;
+   struct data_ring*ring = (struct data_ring*)data;
+   struct sk_buff  *skb;
struct ieee80211_tx_control beacon;
 
memset(&beacon, 0x00, sizeof(beacon));
@@ -845,11 +843,11 @@ rt2500pci_beacondone(void *data)
/*
 * TODO: What value should be passed as bss_idx?
 */
-   skb = ieee80211_beac

[PATCH 26/32] rt2x00: Move all USB and PCI common data into seperate headers

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Now that rt2x00_pci and rt2x00_usb structures in the various
headers are generic enough, add 2 header files rt2x00pci and rt2x00usb
and make them contain all common information of the PCI or USB modules.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

Available on server:

http://mendiosus.nl/rt2x00/rt2x00-26-dev.diff


pgp2HdaloG1JW.pgp
Description: PGP signature


[PATCH 19/32] rt2x00: Fix panics in interrupt handlers

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Fix panics when the interrupt handlers are being
run while the ring is empty.
During the interrupt handling break the loop
correctly when an error has been detected,
more work is being done after the loop.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:49:59.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:50:36.0 +0200
@@ -844,7 +844,7 @@ rt2400pci_rxdone(void *data)
&& !rt2x00_get_field32(rxd->word0, RXD_W0_PHYSICAL_ERROR)) {
skb = dev_alloc_skb(size + NET_IP_ALIGN);
if (!skb)
-   return;
+   break;
 
skb_reserve(skb, NET_IP_ALIGN);
 
@@ -859,7 +859,7 @@ rt2400pci_rxdone(void *data)
 
rt2x00_set_field32(&rxd->word0, RXD_W0_OWNER_NIC, 1);
 
-   rt2x00_ring_index_inc(&rt2x00pci->rx);
+   rt2x00_ring_index_inc(ring);
}
 
/*
@@ -879,7 +879,7 @@ rt2400pci_txdone(void *data)
int tx_status;
int ack;
 
-   do {
+while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
txd = entry->desc_addr;
 
@@ -925,7 +925,7 @@ rt2400pci_txdone(void *data)
entry->skb = NULL;
 
rt2x00_ring_index_done_inc(ring);
-   } while (!rt2x00_ring_empty(ring));
+   }
 
/*
 * Check if we are waiting on an empty queue
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:49:59.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:50:36.0 +0200
@@ -926,7 +926,7 @@ rt2500pci_rxdone(void *data)
&& !rt2x00_get_field32(rxd->word0, RXD_W0_PHYSICAL_ERROR)) {
skb = dev_alloc_skb(size + NET_IP_ALIGN);
if (!skb)
-   return;
+   break;
 
skb_reserve(skb, NET_IP_ALIGN);
 
@@ -943,7 +943,7 @@ rt2500pci_rxdone(void *data)
}
rt2x00_set_field32(&rxd->word0, RXD_W0_OWNER_NIC, 1);
 
-   rt2x00_ring_index_inc(&rt2x00pci->rx);
+   rt2x00_ring_index_inc(ring);
}
 
/*
@@ -964,7 +964,7 @@ rt2500pci_txdone(void *data)
int tx_status;
int ack;
 
-   do {
+while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
txd = entry->desc_addr;
 
@@ -1010,7 +1010,7 @@ rt2500pci_txdone(void *data)
entry->skb = NULL;
 
rt2x00_ring_index_done_inc(ring);
-   } while (!rt2x00_ring_empty(ring));
+   }
 
/*
 * Check if we are waiting on an empty queue
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:49:59.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:50:36.0 +0200
@@ -808,7 +808,7 @@ rt2500usb_txdone(void *data)
struct txd  *txd;
int ack;
 
-   do {
+while (!rt2x00_ring_empty(ring)) {
entry = rt2x00_get_data_entry_done(ring);
txd = entry->desc_addr;
 
@@ -843,7 +843,7 @@ rt2500usb_txdone(void *data)
entry->skb = NULL;

rt2x00_ring_index_done_inc(entry->ring);
-   } while (!rt2x00_ring_empty(ring));
+   }
 
/*
 * Check if we are waiting on an empty queue


pgprpPT39wqU1.pgp
Description: PGP signature


[PATCH 28/32] rt2x00: Support TXRX led handling

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Create more advanced led handling, enable txrx activity
by switching on and off the led at interrupt time.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 22:03:48.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 22:04:19.0 +0200
@@ -669,6 +669,57 @@ rt2400pci_link_tuner(struct rt2x00_pci *
 }
 
 /*
+ * LED functions.
+ */
+static void
+rt2400pci_enable_led(struct rt2x00_pci *rt2x00pci)
+{
+   u32 reg;
+
+   rt2x00_register_read(rt2x00pci, LEDCSR, ®);
+
+   rt2x00_set_field32(®, LEDCSR_ON_PERIOD, 30);
+   rt2x00_set_field32(®, LEDCSR_OFF_PERIOD, 70);
+
+   if (rt2x00pci->led_mode == LED_MODE_TXRX_ACTIVITY) {
+   rt2x00_set_field32(®, LEDCSR_LINK, 1);
+   rt2x00_set_field32(®, LEDCSR_ACTIVITY, 0);
+   } else if (rt2x00pci->led_mode == LED_MODE_ASUS) {
+   rt2x00_set_field32(®, LEDCSR_LINK, 0);
+   rt2x00_set_field32(®, LEDCSR_ACTIVITY, 1);
+   } else {
+   rt2x00_set_field32(®, LEDCSR_LINK, 1);
+   rt2x00_set_field32(®, LEDCSR_ACTIVITY, 1);
+   }
+
+   rt2x00_register_write(rt2x00pci, LEDCSR, reg);
+}
+
+static void
+rt2400pci_disable_led(struct rt2x00_pci *rt2x00pci)
+{
+   u32 reg;
+
+   rt2x00_register_read(rt2x00pci, LEDCSR, ®);
+   rt2x00_set_field32(®, LEDCSR_LINK, 0);
+   rt2x00_set_field32(®, LEDCSR_ACTIVITY, 0);
+   rt2x00_register_write(rt2x00pci, LEDCSR, reg);
+}
+
+static void
+rt2400pci_activity_led(struct rt2x00_pci *rt2x00pci, char activity)
+{
+   u32 reg;
+
+   if (rt2x00pci->led_mode != LED_MODE_TXRX_ACTIVITY)
+   return;
+
+   rt2x00_register_read(rt2x00pci, LEDCSR, ®);
+   rt2x00_set_field32(®, LEDCSR_ACTIVITY, activity);
+   rt2x00_register_write(rt2x00pci, LEDCSR, reg);
+}
+
+/*
  * Device state switch.
  * This will put the device to sleep, or awake it.
  */
@@ -882,6 +933,11 @@ rt2400pci_rxdone(void *data)
 * Tune link for optimal performance.
 */
rt2400pci_link_tuner(rt2x00pci);
+
+   /*
+* Update LED.
+*/
+   rt2400pci_activity_led(rt2x00pci, 0);
 }
 
 static void
@@ -987,10 +1043,13 @@ rt2400pci_interrupt(int irq, void *dev_i
 
/*
 * 2 - Rx ring done interrupt.
+* Enable the TXRX activity led.
 */
-   if (rt2x00_get_field32(reg, CSR7_RXDONE))
+   if (rt2x00_get_field32(reg, CSR7_RXDONE)) {
queue_work(rt2x00pci->workqueue,
&rt2x00pci->ring[RING_RX].irq_work);
+   rt2400pci_activity_led(rt2x00pci, 1);
+   }
 
/*
 * 3 - Atim ring transmit done interrupt.
@@ -1333,13 +1392,6 @@ rt2400pci_init_registers(struct rt2x00_p
rt2x00_set_field32(®, RALINKCSR_AR_BBP_ID1, 154);
rt2x00_register_write(rt2x00pci, RALINKCSR, reg);
 
-   rt2x00_register_read(rt2x00pci, LEDCSR, ®);
-   rt2x00_set_field32(®, LEDCSR_ON_PERIOD, 30);
-   rt2x00_set_field32(®, LEDCSR_OFF_PERIOD, 70);
-   rt2x00_set_field32(®, LEDCSR_LINK, 0);
-   rt2x00_set_field32(®, LEDCSR_ACTIVITY, 0);
-   rt2x00_register_write(rt2x00pci, LEDCSR, reg);
-
rt2x00_register_read(rt2x00pci, CSR1, ®);
rt2x00_set_field32(®, CSR1_SOFT_RESET, 1);
rt2x00_set_field32(®, CSR1_BBP_RESET, 0);
@@ -1555,6 +1607,11 @@ rt2400pci_open(struct net_device *net_de
}
 
/*
+* Enable LED
+*/
+   rt2400pci_enable_led(rt2x00pci);
+
+   /*
 * Enable interrupts.
 */
rt2x00_register_read(rt2x00pci, CSR8, ®);
@@ -1597,11 +1654,9 @@ rt2400pci_stop(struct net_device *net_de
rt2x00_register_write(rt2x00pci, RXCSR0, reg);
 
/*
-* Switch off LED.
+* Disable LED
 */
-   rt2x00_register_read(rt2x00pci, LEDCSR, ®);
-   rt2x00_set_field32(®, LEDCSR_LINK, 0);
-   rt2x00_register_write(rt2x00pci, LEDCSR, reg);
+   rt2400pci_disable_led(rt2x00pci);
 
/*
 * Disable interrupts.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 22:03:48.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 22:04:19.0 +0200
@@ -722,6 +722,57 @@ dynamic_cca_tune:
 }
 
 /*
+ * LED functions.
+ */
+static void
+rt2500pci_enable_led(struct rt2x00_pci *rt2x00pci)
+{
+   u32 reg;
+
+   rt2x00_register_read(rt2x00pci, LEDCSR, ®

[PATCH 14/32] rt2x00: Allocate eeprom memory

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Make the EEPROM array in rt2x00_pci and rt2x00_usb a pointer,
and allocate the memory seperately. This is needed for make
the structures more generic for all rt2x00 pci or usb modules.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:45:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:47:22.0 +0200
@@ -1831,7 +1831,6 @@ rt2400pci_init_eeprom(struct rt2x00_pci 
u32 reg;
u16 value;
u16 eeprom;
-   int counter;
 
/*
 * 1 - Detect EEPROM width.
@@ -1886,8 +1885,12 @@ rt2400pci_init_eeprom(struct rt2x00_pci 
/*
 * 7 - Read BBP data from EEPROM and store in private structure.
 */
+   rt2x00pci->eeprom = kzalloc(EEPROM_BBP_SIZE * sizeof(u16), GFP_KERNEL);
+   if (!rt2x00pci->eeprom) 
+   return -ENOMEM;
+
rt2x00_eeprom_multiread(rt2x00pci, EEPROM_BBP_START,
-   &rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
+   rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
 
return 0;
 }
@@ -2197,6 +2200,8 @@ rt2400pci_uninitialize(struct net_device
del_timer_sync(&rt2x00pci->poll_timer);
 #endif /* CONFIG_RT2400PCI_BUTTON */
 
+   kfree(rt2x00pci->eeprom);
+
if (likely(rt2x00pci->csr_addr)) {
iounmap(rt2x00pci->csr_addr);
rt2x00pci->csr_addr = NULL;
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-04-27 21:45:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
2006-04-27 21:47:22.0 +0200
@@ -945,7 +945,7 @@ struct rt2x00_pci{
/*
 * EEPROM BBP data.
 */
-   u16 eeprom[EEPROM_BBP_SIZE];
+   u16 *eeprom;
 
/*
 * Low level statistics which will have
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:45:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:47:22.0 +0200
@@ -1939,7 +1939,6 @@ rt2500pci_init_eeprom(struct rt2x00_pci 
u32 reg;
u16 value;
u16 eeprom;
-   int counter;
 
/*
 * 1 - Detect EEPROM width.
@@ -1998,8 +1997,12 @@ rt2500pci_init_eeprom(struct rt2x00_pci 
/*
 * 7 - Read BBP data from EEPROM and store in private structure.
 */
+   rt2x00pci->eeprom = kzalloc(EEPROM_BBP_SIZE * sizeof(u16), GFP_KERNEL);
+   if (!rt2x00pci->eeprom)
+   return -ENOMEM;
+
rt2x00_eeprom_multiread(rt2x00pci, EEPROM_BBP_START,
-   &rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
+   rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
 
return 0;
 }
@@ -2495,6 +2498,8 @@ rt2500pci_uninitialize(struct net_device
del_timer_sync(&rt2x00pci->poll_timer);
 #endif /* CONFIG_RT2500PCI_BUTTON */
 
+   kfree(rt2x00pci->eeprom);
+
if (likely(rt2x00pci->csr_addr)) {
iounmap(rt2x00pci->csr_addr);
rt2x00pci->csr_addr = NULL;
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h  
2006-04-27 21:43:27.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
2006-04-27 21:47:22.0 +0200
@@ -1215,7 +1215,7 @@ struct rt2x00_pci{
/*
 * EEPROM BBP data.
 */
-   u16 eeprom[EEPROM_BBP_SIZE];
+   u16 *eeprom;
 
/*
 * Low level statistics which will have
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:45:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:47:22.0 +0200
@@ -1657,9 +1657,12 @@ rt2500usb_init_e

[PATCH 29/32] rt2x00: dscape compatibilitiy

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Latest dscape patches have broken rt2x00,
fix compile issues, and support the new features.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

Available on server:

http://mendiosus.nl/rt2x00/rt2x00-29-compat.diff


pgpdvt1YheaxX.pgp
Description: PGP signature


[PATCH 0/32] rt2x00

2006-04-27 Thread Ivo van Doorn
Hi,

Here follows quite a large series of patches
for rt2x00 for the wireless-dev tree.

This will bring rt2x00 in wireless-dev up to date with
our CVS tree except that rt61pci and rt73usb are not
yet send along. They will follow within a week.

Apologies for the long delay but due to time limitations
the highest priority was put on the CVS tree and not
on the regularly sending of patches. We will do our best
to send more frequent updates, so next time other developers
of rt2x00 will also be sending the patches.

A short summary of all patches the are following:
[PATCH 1/32] rt2x00: code style fix
[PATCH 2/32] rt2x00: use enumerations
[PATCH 3/32] rt2x00: use pci_*_consistent for DMA mapping
[PATCH 4/32] rt2x00: Add eeprom_multiread function
[PATCH 5/32] rt2x00: Optimize RATE flag handling
[PATCH 6/32] rt2x00: Use arraylike accessors for entries in DMA ring
[PATCH 7/32] rt2x00: make vals static
[PATCH 8/32] rt2x00: Invalid memory allocation check
[PATCH 9/32] rt2x00: Fix antenna configuration
[PATCH 10/32] rt2x00: Move TSF counting activation to correct funtion
[PATCH 11/32] rt2x00: Add more register defines
[PATCH 12/32] rt2x00: Add USB ID's
[PATCH 13/32] rt2x00: Tune link depending on link quality
[PATCH 14/32] rt2x00: Allocate eeprom memory
[PATCH 15/32] rt2x00: Move rx_params to correct location
[PATCH 16/32] rt2x00: Make sure TX rings are empty when scanning
[PATCH 17/32] rt2x00: Put net_device structure in data_ring
[PATCH 18/32] rt2x00: Make sure device has reached requested state while 
suspend/resume
[PATCH 19/32] rt2x00: Fix panics in interrupt handlers
[PATCH 20/32] rt2x00: byte ordering correctness
[PATCH 21/32] rt2x00: PRIO ring should be treated as regular TX ring
[PATCH 22/32] rt2x00: Allocate ring structures in single array
[PATCH 23/32] rt2x00: Make correct cast in USB interrupt
[PATCH 24/32] rt2x00: Use correct desc_addr and data_addr
[PATCH 25/32] rt2x00: Add flag handlers
[PATCH 26/32] rt2x00: Move all USB and PCI common data into seperate headers
[PATCH 27/32] rt2x00: Put Hardware button in generic header
[PATCH 28/32] rt2x00: Support TXRX led handling
[PATCH 29/32] rt2x00: dscape compatibilitiy
[PATCH 30/32] rt2x00: Correctly initialize TX power in registers
[PATCH 31/32] rt2x00: Correctly initialization and uninitialization of device
[PATCH 32/32] rt2x00: misc fixes

Some of the patches are quite big and placed on an external server,
the link for that patch will be placed in that particular mail.
All other patches are inlined but are also available on the same server:
http://mendiosus.nl/rt2x00/rt2x00-01-code-style.diff
http://mendiosus.nl/rt2x00/rt2x00-02-enum.diff
http://mendiosus.nl/rt2x00/rt2x00-03-dma-mapping.diff
http://mendiosus.nl/rt2x00/rt2x00-04-eeprom-multiread.diff
http://mendiosus.nl/rt2x00/rt2x00-05-txrate.diff
http://mendiosus.nl/rt2x00/rt2x00-06-array.diff
http://mendiosus.nl/rt2x00/rt2x00-07-static.diff
http://mendiosus.nl/rt2x00/rt2x00-08-rate-check.diff
http://mendiosus.nl/rt2x00/rt2x00-09-antenna.diff
http://mendiosus.nl/rt2x00/rt2x00-10-tsf-counting.diff
http://mendiosus.nl/rt2x00/rt2x00-11-register.diff
http://mendiosus.nl/rt2x00/rt2x00-12-usb-ids.diff
http://mendiosus.nl/rt2x00/rt2x00-13-link-tuner.diff
http://mendiosus.nl/rt2x00/rt2x00-14-eeprom.diff
http://mendiosus.nl/rt2x00/rt2x00-15-txrx-params.diff
http://mendiosus.nl/rt2x00/rt2x00-16-scan-params.diff
http://mendiosus.nl/rt2x00/rt2x00-17-ringdev.diff
http://mendiosus.nl/rt2x00/rt2x00-18-suspend.diff
http://mendiosus.nl/rt2x00/rt2x00-19-ring.diff
http://mendiosus.nl/rt2x00/rt2x00-20-endian.diff
http://mendiosus.nl/rt2x00/rt2x00-21-prio.diff
http://mendiosus.nl/rt2x00/rt2x00-22-rings.diff
http://mendiosus.nl/rt2x00/rt2x00-23-usbhandler.diff
http://mendiosus.nl/rt2x00/rt2x00-24-usbfixes.diff
http://mendiosus.nl/rt2x00/rt2x00-25-flags.diff
http://mendiosus.nl/rt2x00/rt2x00-26-dev.diff
http://mendiosus.nl/rt2x00/rt2x00-27-button.diff
http://mendiosus.nl/rt2x00/rt2x00-28-led.diff
http://mendiosus.nl/rt2x00/rt2x00-29-compat.diff
http://mendiosus.nl/rt2x00/rt2x00-30-config.diff
http://mendiosus.nl/rt2x00/rt2x00-31-init.diff
http://mendiosus.nl/rt2x00/rt2x00-32-misc.diff

IvD


pgpzoTJPlHGw1.pgp
Description: PGP signature


[PATCH 1/32] rt2x00: code style fix

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Coding style fix for all rt2x00 drivers.
This change was requested on the netdev list some time ago,
but the patch send then didn't contain all requested changes.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

Available on server:

http://mendiosus.nl/rt2x00/rt2x00-01-code-style.diff


pgprZQNrY8QfI.pgp
Description: PGP signature


[PATCH 2/32] rt2x00: use enumerations

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

The led_mode defines are equal in all drivers,
and should be placed in the common rt2x00.h header.
Make the led_mode, tx_status and dev_state defines
into enumerations.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-04-27 00:52:56.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
2006-04-27 21:25:33.0 +0200
@@ -936,11 +936,6 @@ struct rt2x00_pci{
 * Led status
 */
u8  led_mode;
-#define LED_MODE_DEFAULT   0
-#define LED_MODE_TXRX_ACTIVITY 1
-#define LED_MODE_SINGLE2
-#define LED_MODE_ASUS  3
-#define LED_MODE_ALPHA 4
 
/*
 * EEPROM BBP data.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.h  
2006-04-27 00:52:56.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.h
2006-04-27 21:25:33.0 +0200
@@ -1192,11 +1192,6 @@ struct rt2x00_pci{
 * Led status
 */
u8  led_mode;
-#define LED_MODE_DEFAULT   0
-#define LED_MODE_TXRX_ACTIVITY 1
-#define LED_MODE_SINGLE2
-#define LED_MODE_ASUS  3
-#define LED_MODE_ALPHA 4
 
/*
 * EEPROM BBP data.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.h  
2006-04-27 00:52:56.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.h
2006-04-27 21:25:33.0 +0200
@@ -691,11 +691,6 @@ struct rt2x00_usb{
 * Led status
 */
u8  led_mode;
-#define LED_MODE_DEFAULT   0
-#define LED_MODE_TXRX_ACTIVITY 1
-#define LED_MODE_SINGLE2
-#define LED_MODE_ASUS  3
-#define LED_MODE_ALPHA 4
 
/*
 * EEPROM BBP data.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
2006-04-27 21:23:26.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h   
2006-04-27 21:25:33.0 +0200
@@ -96,11 +96,34 @@ static int rt2x00_debug_level = 0;
 /*
  * TX result flags.
  */
-#define TX_SUCCESS 0
-#define TX_SUCCESS_RETRY   1
-#define TX_FAIL_RETRY  2
-#define TX_FAIL_INVALID3
-#define TX_FAIL_OTHER  4
+enum TX_STATUS {
+   TX_SUCCESS  = 0,
+   TX_SUCCESS_RETRY= 1,
+   TX_FAIL_RETRY   = 2,
+   TX_FAIL_INVALID = 3,
+   TX_FAIL_OTHER   = 4,
+};
+
+/*
+ * Led mode values.
+ */
+enum led_mode {
+   LED_MODE_DEFAULT= 0,
+   LED_MODE_TXRX_ACTIVITY  = 1,
+   LED_MODE_SIGNAL_STRENGTH= 2,
+   LED_MODE_ASUS   = 3,
+   LED_MODE_ALPHA  = 4,
+};
+
+/*
+ * Device states
+ */
+enum dev_state {
+   STATE_DEEP_SLEEP= 0,
+   STATE_SLEEP = 1,
+   STATE_STANDBY   = 2,
+   STATE_AWAKE = 3,
+};
 
 /*
  * Macros for determining which is the lowest or highest bit


pgpGba0MaNdiB.pgp
Description: PGP signature


[PATCH 27/32] rt2x00: Put Hardware button in generic header

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Put the hardware button handling as much as possible
in the new generic header for PCI.
The individial .c files should now only contain
the polling function to check the state of the hardware button.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:57:18.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 22:03:48.0 +0200
@@ -38,10 +38,6 @@
 #include 
 #include 
 
-#ifdef CONFIG_RT2400PCI_BUTTON
-#include 
-#endif /* CONFIG_RT2400PCI_BUTTON */
-
 #include 
 
 /*
@@ -364,6 +360,24 @@ rt2x00_eeprom_multiread(
rt2x00_eeprom_read(rt2x00pci, word + counter, data++);
 }
 
+#ifdef CONFIG_RT2400PCI_BUTTON
+/*
+ * Hardware button poll handler.
+ */
+static void
+rt2400pci_button_poll(unsigned long data)
+{
+   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)data;
+   u32 reg;
+
+   rt2x00_register_read(rt2x00pci, GPIOCSR, ®);
+   rt2x00pci_button_status(
+   rt2x00pci, rt2x00_get_field32(reg, GPIOCSR_BIT0));
+}
+#else /* CONFIG_RT2400PCI_BUTTON */
+static void rt2400pci_button_poll(struct rt2x00_pci *rt2x00pci){}
+#endif /* CONFIG_RT2400PCI_BUTTON */
+
 /*
  * Configuration handlers.
  */
@@ -2258,24 +2272,10 @@ rt2400pci_initialize(struct pci_dev *pci
|| rt2400pci_init_hw(rt2x00pci))
goto exit_destroy_workqueue;
 
-#ifdef CONFIG_RT2400PCI_BUTTON
-   strcpy(acpi_device_class(&rt2x00pci->acpi_dev), DRV_NAME "_button");
-   strcpy(acpi_device_bid(&rt2x00pci->acpi_dev), DRV_NAME);
-   strcpy(acpi_device_name(&rt2x00pci->acpi_dev), DRV_NAME);
-
-   init_timer(&rt2x00pci->poll_timer);
-
-   if (rt2x00_poll_delay
-   && rt2x00pci->button_status != BUTTON_STATUS_UNAVAILABLE) {
-   rt2x00pci->button_status = rt2400pci_poll(rt2x00pci);
-   rt2x00pci->poll_delay = rt2x00_poll_delay * (HZ / 10);
-   rt2x00pci->poll_timer.function = rt2400pci_poll_expire;
-   rt2x00pci->poll_timer.data = (unsigned long)rt2x00pci;
-   rt2x00pci->poll_timer.expires =
-   jiffies + rt2x00pci->poll_delay;
-   add_timer(&rt2x00pci->poll_timer);
-   };
-#endif /* CONFIG_RT2400PCI_BUTTON */
+   /*
+* If required start hardware button polling.
+*/
+   rt2x00pci_button_start(rt2x00pci, rt2400pci_button_poll);
 
return 0;
 
@@ -2294,13 +2294,10 @@ rt2400pci_uninitialize(struct net_device
 {
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
 
-#ifdef CONFIG_RT2400PCI_BUTTON
/*
 * Shutdown poll_timer for hardware button.
 */
-   rt2x00pci->button_status = BUTTON_STATUS_UNAVAILABLE;
-   del_timer_sync(&rt2x00pci->poll_timer);
-#endif /* CONFIG_RT2400PCI_BUTTON */
+   rt2x00pci_button_stop(rt2x00pci);
 
kfree(rt2x00pci->eeprom);
 
@@ -2506,40 +2503,6 @@ rt2400pci_resume(struct pci_dev *pci_dev
 }
 #endif /* CONFIG_PM */
 
-#ifdef CONFIG_RT2400PCI_BUTTON
-static int
-rt2400pci_poll(struct rt2x00_pci *rt2x00pci)
-{
-   u32 reg;
-
-   rt2x00_register_read(rt2x00pci, GPIOCSR, ®);
-   return rt2x00_get_field32(reg, GPIOCSR_BIT0);
-}
-
-static void
-rt2400pci_poll_expire(unsigned long data)
-{
-   struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)data;
-   u16 status;
-
-   status = rt2400pci_poll(rt2x00pci);
-
-   if (rt2x00pci->button_status != BUTTON_STATUS_UNAVAILABLE)
-   return;
-
-   if (status != rt2x00pci->button_status) {
-   rt2x00pci->button_status = status;
-   acpi_bus_generate_event(&rt2x00pci->acpi_dev,
-   ACPI_TYPE_EVENT, rt2x00pci->button_status);
-   }
-
-   rt2x00pci->poll_timer.expires = jiffies + rt2x00pci->poll_delay;
-
-   if (rt2x00pci->button_status != BUTTON_STATUS_UNAVAILABLE)
-   add_timer(&rt2x00pci->poll_timer);
-}
-#endif /* CONFIG_RT2400PCI_BUTTON */
-
 /*
  * RT2400pci module information.
  */
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-04-27 21:57:18.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
2006-04-27 22:03:48.0 +0200
@@ -863,21 +863,4 @@ static int rt2400pci_beacon_update(struc
struct sk_buff *skb, struct ieee80211_tx_control *control);
 static int rt2400pci_tx_last_beacon(struct net_device *net_dev);
 
-/*
- * HW button support structures and variables.
- * The de

[PATCH 22/32] rt2x00: Allocate ring structures in single array

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Allocate all ring structures seperately and
as an array of rings. This will make the
rt2x00_pci and rt2x00_usb structures more generic
for all rt2x00 modules.
Use seperate function to convert a dscape ring ID
to the address of the actual ring.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

Available on server:

http://mendiosus.nl/rt2x00/rt2x00-22-rings.diff


pgp37E3iQh6EF.pgp
Description: PGP signature


[PATCH 30/32] rt2x00: Correctly initialize TX power in registers

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

The rate does not need to be configured for each
TX packet. The actual rate for sending is determined
in the PLCP, the rate configuration is only capable
of setting the supported rates, which is dependent
of the physical mode we are in.
When we the configuration function is called,
disable the RX for proper behaviour.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 22:04:47.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 22:05:21.0 +0200
@@ -660,6 +660,22 @@ rt2400pci_config_rate(struct rt2x00_pci 
 }
 
 static void
+rt2400pci_config_phymode(struct rt2x00_pci *rt2x00pci, const int phymode)
+{
+   struct ieee80211_rate   *rate;
+
+   rate = &rt2x00pci->hw.modes[0].rates[
+   rt2x00pci->hw.modes[0].num_rates - 1];
+
+   rt2400pci_config_rate(rt2x00pci, rate->val2);
+
+   /*
+* Update physical mode for rx ring.
+*/
+   rt2x00pci->rx_params.phymode = phymode;
+}
+
+static void
 rt2400pci_config_mac_address(struct rt2x00_pci *rt2x00pci, void *addr)
 {
u32 reg[2] = {0, 0};
@@ -815,11 +831,6 @@ rt2400pci_write_tx_desc(
u16 signal;
u16 service;
 
-   /*
-* Update rate control register.
-*/
-   rt2400pci_config_rate(rt2x00pci, control->tx_rate);
-
rt2x00_set_field32(&txd->word0, TXD_W0_VALID, 1);
rt2x00_set_field32(&txd->word0, TXD_W0_ACK, !control->no_ack);
 
@@ -1545,14 +1556,6 @@ rt2400pci_tx(struct net_device *net_dev,
 
rt2x00_ring_index_inc(ring);
 
-   /*
-* We are going to cheat now, we update the register
-* with the CWmin and CWmax values for the current
-* queue. This is the alternative since we cannot
-* set the CWmin and CWmax per descriptor.
-*/
-   rt2400pci_config_cw(rt2x00pci, &ring->tx_params);
-
rt2x00_register_read(rt2x00pci, TXCSR0, ®);
if (control->queue == IEEE80211_TX_QUEUE_DATA0)
rt2x00_set_field32(®, TXCSR0_KICK_PRIO, 1);
@@ -1769,19 +1772,46 @@ rt2400pci_config_update(void *data)
struct rt2x00_pci   *rt2x00pci = data;
struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
struct ieee80211_conf   *conf = ieee80211_get_hw_conf(net_dev);
+   u32 reg;
+
+   /*
+* Some configuration changes require the RX to be disabled.
+*/
+   if (GET_FLAG(rt2x00pci, RADIO_ENABLED)) {
+   rt2x00_register_read(rt2x00pci, RXCSR0, ®);
+   rt2x00_set_field32(®, RXCSR0_DISABLE_RX, 1);
+   rt2x00_register_write(rt2x00pci, RXCSR0, reg);
+   }
 
-   rt2400pci_config_bssid(rt2x00pci, conf->client_bssid);
-   rt2400pci_config_type(rt2x00pci, conf->mode);
rt2400pci_config_channel(rt2x00pci,
conf->channel_val, conf->channel, conf->freq);
rt2400pci_config_txpower(rt2x00pci, conf->power_level);
rt2400pci_config_antenna(rt2x00pci, conf->antenna_sel);
rt2400pci_config_duration(rt2x00pci, conf->short_slot_time);
+   rt2400pci_config_phymode(rt2x00pci, conf->phymode);
 
/*
-* Update active info for RX.
+* Reenable RX only if the radio should be on.
 */
-   rt2x00pci->rx_params.phymode = conf->phymode;
+   if (conf->radio_enabled) {
+   if (!GET_FLAG(rt2x00pci, RADIO_ENABLED)) {
+   if (rt2400pci_open(net_dev)) {
+   ERROR("Failed to enabled radio.\n");
+   return;
+   }
+   } else {
+   rt2x00_register_read(rt2x00pci, RXCSR0, ®);
+   rt2x00_set_field32(®, RXCSR0_DISABLE_RX, 0);
+   rt2x00_register_write(rt2x00pci, RXCSR0, reg);
+   }
+   } else {
+   if (GET_FLAG(rt2x00pci, RADIO_ENABLED)) {
+   if (rt2400pci_stop(net_dev)) {
+   ERROR("Failed to disable radio.\n");
+   return;
+   }
+   }
+   }
 }
 
 static int
@@ -1863,8 +1893,8 @@ rt2400pci_scan(void *data)
 * Switch channel and update active info for RX.
 */
if (rt2x00pci->scan->state == IEEE80211_SCAN_START) {
-   rt2x00pci->rx_params.phymode =
-   rt2x00pci->scan->conf.scan_phymode;
+   rt2400pci_config_phymode(rt2x00pci,
+   rt2x00pci->scan->conf.scan_phymode);
 
rt2400pci_config_channel(rt2x00pci,
rt2x00

[PATCH 31/32] rt2x00: Correctly initialization and uninitialization of device

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Fix several hardware initialization and uninitalization
problems by incorrectly flushing workqueues.
Fix the memory leak when freeing the ieee80211_hw structure.
Allow device to connect to 802.11g networks by default
instead of 802.11b.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 22:05:21.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 22:05:52.0 +0200
@@ -1719,6 +1719,11 @@ rt2400pci_stop(struct net_device *net_de
}
 
/*
+* Flush out all pending work.
+*/
+   flush_workqueue(rt2x00pci->workqueue);
+
+   /*
 * Free DMA rings.
 */
rt2400pci_free_rings(rt2x00pci);
@@ -2441,7 +2446,7 @@ rt2400pci_initialize(struct pci_dev *pci
 
rt2x00pci->workqueue = create_singlethread_workqueue(DRV_NAME);
if (!rt2x00pci->workqueue)
-   goto exit_iounmap;
+   goto exit;
 
/*
 * Initialize cofniguration work.
@@ -2457,21 +2462,25 @@ rt2400pci_initialize(struct pci_dev *pci
if (rt2400pci_init_eeprom(rt2x00pci)
|| rt2400pci_init_mac(rt2x00pci)
|| rt2400pci_init_hw(rt2x00pci))
-   goto exit_destroy_workqueue;
+   goto exit;
 
/*
 * If required start hardware button polling.
 */
rt2x00pci_button_start(rt2x00pci, rt2400pci_button_poll);
 
-   return 0;
+   /*
+* Register hardware.
+*/
+   if (ieee80211_register_hw(net_dev, &rt2x00pci->hw)) {
+   ERROR("Failed to register device.\n");
+   goto exit;
+   }
 
-exit_destroy_workqueue:
-   destroy_workqueue(rt2x00pci->workqueue);
+   return 0;
 
-exit_iounmap:
-   iounmap(rt2x00pci->csr_addr);
-   rt2x00pci->csr_addr = NULL;
+exit:
+   rt2400pci_uninitialize(net_dev);
 
return -ENODEV;
 }
@@ -2482,26 +2491,39 @@ rt2400pci_uninitialize(struct net_device
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
 
/*
+* Unregister hardware.
+*/
+   ieee80211_unregister_hw(net_dev);
+
+   /*
 * Shutdown poll_timer for hardware button.
 */
rt2x00pci_button_stop(rt2x00pci);
 
kfree(rt2x00pci->eeprom);
 
+   /*
+* Release CSR memory.
+*/
if (likely(rt2x00pci->csr_addr)) {
iounmap(rt2x00pci->csr_addr);
rt2x00pci->csr_addr = NULL;
}
 
+   /*
+* Free workqueue.
+*/
if (likely(rt2x00pci->workqueue)) {
-   flush_workqueue(rt2x00pci->workqueue);
destroy_workqueue(rt2x00pci->workqueue);
rt2x00pci->workqueue = NULL;
}
 
+   /*
+* Free ieee80211_hw memory.
+*/
if (likely(rt2x00pci->hw.modes)) {
-   kfree(rt2x00pci->hw.modes->channels);
-   kfree(rt2x00pci->hw.modes->rates);
+   kfree(rt2x00pci->hw.modes->channels);
+   kfree(rt2x00pci->hw.modes->rates);
kfree(rt2x00pci->hw.modes);
rt2x00pci->hw.modes = NULL;
}
@@ -2514,7 +2536,6 @@ static int
 rt2400pci_probe(struct pci_dev *pci_dev, const struct pci_device_id *id)
 {
struct net_device   *net_dev;
-   struct rt2x00_pci   *rt2x00pci;
int status;
 
if (unlikely(id->driver_data != RT2460)) {
@@ -2559,19 +2580,9 @@ rt2400pci_probe(struct pci_dev *pci_dev,
ERROR("Failed to initialize device.\n");
goto exit_free_device;
}
-   rt2x00pci = ieee80211_dev_hw_data(net_dev);
-
-   status = ieee80211_register_hw(net_dev, &rt2x00pci->hw);
-   if (status) {
-   ERROR("Failed to register device.\n");
-   goto exit_uninitialize_device;
-   }
 
return 0;
 
-exit_uninitialize_device:
-   rt2400pci_uninitialize(net_dev);
-
 exit_free_device:
ieee80211_free_hw(net_dev);
 
@@ -2592,7 +2603,7 @@ rt2400pci_remove(struct pci_dev *pci_dev
 {
struct net_device   *net_dev = pci_get_drvdata(pci_dev);
 
-   ieee80211_unregister_hw(net_dev);
+   net_dev->stop(net_dev);
 
rt2400pci_uninitialize(net_dev);
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 22:05:21.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 22:05:52.0 +0200
@@ -1845,6 +1845,11 @@ rt2500pci_stop(struct 

[PATCH 6/32] rt2x00: Use arraylike accessors for entries in DMA ring

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Make the code a bit more readable by using
array like accessors for pointers in a loop.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:39:24.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:40:06.0 +0200
@@ -951,15 +951,15 @@ rt2400pci_alloc_ring(
 * Initialize all ring entries to contain valid
 * addresses.
 */
+   entry = (struct data_entry*)ring->entry;
for (counter = 0; counter < ring->stats.limit; counter++) {
-   entry = ring->entry + (counter * ring->entry_size);
-   entry->skb = NULL;
-   entry->desc_addr = ring->data_addr
+   entry[counter].skb = NULL;
+   entry[counter].desc_addr = ring->data_addr
+ (counter * ring->desc_size);
-   entry->data_addr = ring->data_addr
+   entry[counter].data_addr = ring->data_addr
+ (ring->stats.limit * ring->desc_size)
+ (counter * ring->data_size);
-   entry->data_dma = ring->data_dma
+   entry[counter].data_dma = ring->data_dma
+ (ring->stats.limit * ring->desc_size)
+ (counter * ring->data_size);
}
@@ -989,14 +989,14 @@ rt2400pci_init_rxdesc(struct rt2x00_pci 
 
memset(ring->data_addr, 0x00, rt2x00_get_ring_size(ring));
 
+   entry = (struct data_entry*)ring->entry;
for (counter = 0; counter < ring->stats.limit; counter++) {
-   entry = ring->entry + (counter * ring->entry_size);
-   rxd = entry->desc_addr;
+   rxd = entry[counter].desc_addr;
 
rt2x00_set_field32(&rxd->word2, RXD_W2_BUFFER_LENGTH,
ring->data_size);
rt2x00_set_field32(&rxd->word1, RXD_W1_BUFFER_ADDRESS,
-   entry->data_dma);
+   entry[counter].data_dma);
rt2x00_set_field32(&rxd->word0, RXD_W0_OWNER_NIC, 1);
}
 
@@ -1012,14 +1012,14 @@ rt2400pci_init_txdesc(struct rt2x00_pci 
 
memset(ring->data_addr, 0x00, rt2x00_get_ring_size(ring));
 
+   entry = (struct data_entry*)ring->entry;
for (counter = 0; counter < ring->stats.limit; counter++) {
-   entry = ring->entry + (counter * ring->entry_size);
-   txd = entry->desc_addr;
+   txd = entry[counter].desc_addr;
 
rt2x00_set_field32(&txd->word2, TXD_W2_BUFFER_LENGTH,
ring->data_size);
rt2x00_set_field32(&txd->word1, TXD_W1_BUFFER_ADDRESS,
-   entry->data_dma);
+   entry[counter].data_dma);
rt2x00_set_field32(&txd->word0, TXD_W0_VALID, 0);
rt2x00_set_field32(&txd->word0, TXD_W0_OWNER_NIC, 0);
}
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:39:24.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:40:06.0 +0200
@@ -987,15 +987,15 @@ rt2500pci_alloc_ring(
 * Initialize all ring entries to contain valid
 * addresses.
 */
+   entry = (struct data_entry*)ring->entry;
for (counter = 0; counter < ring->stats.limit; counter++) {
-   entry = ring->entry + (counter * ring->entry_size);
-   entry->skb = NULL;
-   entry->desc_addr = ring->data_addr
+   entry[counter].skb = NULL;
+   entry[counter].desc_addr = ring->data_addr
+ (counter * ring->desc_size);
-   entry->data_addr = ring->data_addr
+   entry[counter].data_addr = ring->data_addr
+ (ring->stats.limit * ring->desc_size)
+ (counter * ring->data_size);
-   entry->data_dma = ring->data_dma
+   entry[counter].data_dma = ring->data_dma
+ (ring->stats.limit * ring->desc_size)
+ (counter * ring->data_size);
}
@@ -1025,12 +1025,12 @@ rt2500pci_init_rxdesc(struct rt2x00_pci 
 
memset(ring->data_addr, 0x00, rt2x00_get_ring_size(ring));
 
+   entry = (struct data_entry*)ring->entry;
for (counter = 0; counter < ring->stats.limit; counter++) {
-   entry = ring->entry + (counter * ring->entry_size);
-   rxd = entry->desc_addr;
+   rxd = entry[counter].desc_addr;
 
  

[PATCH 21/32] rt2x00: PRIO ring should be treated as regular TX ring

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Remove PRIO_ENTRIES define, the prio ring
should be treated as a regular TX ring.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:50:36.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:52:01.0 +0200
@@ -1145,7 +1145,7 @@ rt2400pci_allocate_rings(struct rt2x00_p
ATIM_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))
|| rt2400pci_alloc_ring(
rt2x00pci, &rt2x00pci->prio, rt2400pci_txdone,
-   PRIO_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
+   TX_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
|| rt2400pci_alloc_ring(
rt2x00pci, &rt2x00pci->beacon, rt2400pci_beacondone,
BEACON_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))) {
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:51:11.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:52:01.0 +0200
@@ -1227,7 +1227,7 @@ rt2500pci_allocate_rings(struct rt2x00_p
ATIM_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))
|| rt2500pci_alloc_ring(
rt2x00pci, &rt2x00pci->prio, rt2500pci_txdone,
-   PRIO_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
+   TX_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
|| rt2500pci_alloc_ring(
rt2x00pci, &rt2x00pci->beacon, rt2500pci_beacondone,
BEACON_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))) {
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:51:11.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:52:01.0 +0200
@@ -996,7 +996,7 @@ rt2500usb_allocate_rings(struct rt2x00_u
ATIM_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))
|| rt2500usb_alloc_ring(
rt2x00usb, &rt2x00usb->prio, &rt2500usb_txdone,
-   PRIO_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
+   TX_ENTRIES, DATA_FRAME_SIZE, sizeof(struct txd))
|| rt2500usb_alloc_ring(
rt2x00usb, &rt2x00usb->beacon, &rt2500usb_beacondone,
BEACON_ENTRIES, MGMT_FRAME_SIZE, sizeof(struct txd))) {
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
2006-04-27 21:49:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h   
2006-04-27 21:52:01.0 +0200
@@ -90,7 +90,6 @@ static int rt2x00_debug_level = 0;
 #define RX_ENTRIES 12
 #define TX_ENTRIES 12
 #define ATIM_ENTRIES   1
-#define PRIO_ENTRIES   6
 #define BEACON_ENTRIES 1
 
 /*


pgpMtc6npJUhB.pgp
Description: PGP signature


[PATCH 10/32] rt2x00: Move TSF counting activation to correct funtion

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Move the enabling of TSF counting into *_config_mode
where it actually belongs.
For rt2500usb this means that the rt2500usb_reset_tsf function
is now removed since it is still unknown in what registers the
TSF counters are stored in.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:41:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:42:29.0 +0200
@@ -385,6 +385,9 @@ rt2400pci_config_mode(struct rt2x00_pci 
 {
u32 reg;
 
+   /*
+* Apply hardware packet filter.
+*/
rt2x00_register_read(rt2x00pci, RXCSR0, ®);
 
if (mode == IW_MODE_ADHOC
@@ -408,6 +411,19 @@ rt2400pci_config_mode(struct rt2x00_pci 
}
 
rt2x00_register_write(rt2x00pci, RXCSR0, reg);
+
+   /*
+* Enable TSF counter.
+*/
+   rt2x00_register_read(rt2x00pci, CSR14, ®);
+   rt2x00_set_field32(®, CSR14_TSF_COUNT, 1);
+   if (mode == IW_MODE_ADHOC)
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 2);
+   else if (mode == IW_MODE_INFRA)
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 1);
+   else
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 0);
+   rt2x00_register_write(rt2x00pci, CSR14, reg);
 }
 
 static void
@@ -1723,21 +1739,10 @@ static void
 rt2400pci_reset_tsf(struct net_device *net_dev)
 {
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
-   struct ieee80211_conf   *conf = ieee80211_get_hw_conf(net_dev);
u32 reg = 0;
 
rt2x00_register_write(rt2x00pci, CSR16, reg);
rt2x00_register_write(rt2x00pci, CSR17, reg);
-
-   rt2x00_register_read(rt2x00pci, CSR14, ®);
-   rt2x00_set_field32(®, CSR14_TSF_COUNT, 1);
-   if (conf->mode == IW_MODE_ADHOC)
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 2);
-   else if (conf->mode == IW_MODE_INFRA)
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 1);
-   else
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 0);
-   rt2x00_register_write(rt2x00pci, CSR14, reg);
 }
 
 static int
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:41:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:42:29.0 +0200
@@ -385,6 +385,9 @@ rt2500pci_config_mode(struct rt2x00_pci 
 {
u32 reg;
 
+   /*
+* Apply hardware packet filter.
+*/
rt2x00_register_read(rt2x00pci, RXCSR0, ®);
 
if (mode == IW_MODE_ADHOC
@@ -411,6 +414,19 @@ rt2500pci_config_mode(struct rt2x00_pci 
rt2x00_set_field32(®, RXCSR0_DROP_BCAST, 0);
 
rt2x00_register_write(rt2x00pci, RXCSR0, reg);
+
+   /*
+* Enable TSF counter.
+*/
+   rt2x00_register_read(rt2x00pci, CSR14, ®);
+   rt2x00_set_field32(®, CSR14_TSF_COUNT, 1);
+   if (mode == IW_MODE_ADHOC)
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 2);
+   else if (mode == IW_MODE_INFRA)
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 1);
+   else
+   rt2x00_set_field32(®, CSR14_TSF_SYNC, 0);
+   rt2x00_register_write(rt2x00pci, CSR14, reg);
 }
 
 static void
@@ -1809,21 +1825,10 @@ static void
 rt2500pci_reset_tsf(struct net_device *net_dev)
 {
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
-   struct ieee80211_conf   *conf = ieee80211_get_hw_conf(net_dev);
u32 reg = 0;
 
rt2x00_register_write(rt2x00pci, CSR16, reg);
rt2x00_register_write(rt2x00pci, CSR17, reg);
-
-   rt2x00_register_read(rt2x00pci, CSR14, ®);
-   rt2x00_set_field32(®, CSR14_TSF_COUNT, 1);
-   if (conf->mode == IW_MODE_ADHOC)
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 2);
-   else if (conf->mode == IW_MODE_INFRA)
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 1);
-   else
-   rt2x00_set_field32(®, CSR14_TSF_SYNC, 0);
-   rt2x00_register_write(rt2x00pci, CSR14, reg);
 }
 
 static int
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:41:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:42:29.0 +0200
@@ -268,6 +268,9 @@ rt2500usb_config_mode(struct rt2x00_usb 
 {
  

[PATCH 16/32] rt2x00: Make sure TX rings are empty when scanning

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Improve the waiting when a skb buffer needs to be send
before the channel switch. This also makes sure no
pending packets are still on the TX ring while making the
channel switch.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:47:52.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:48:21.0 +0200
@@ -838,7 +838,6 @@ rt2400pci_txdone(void *data)
struct rt2x00_pci   *rt2x00pci = (struct rt2x00_pci*)ring->dev;
struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
struct data_entry   *entry;
-   struct skb_cb   *cb;
struct txd  *txd;
int tx_status;
int ack;
@@ -851,13 +850,6 @@ rt2400pci_txdone(void *data)
|| !rt2x00_get_field32(txd->word0, TXD_W0_VALID))
break;
 
-   /*
-* Check if this frame was send for the scan routine.
-*/
-   cb = (struct skb_cb*)&entry->skb->cb;
-   if (rt2x00pci->scan && cb->scan_complete)
-   complete(&rt2x00pci->scan->completion);
-
ack = rt2x00_get_field32(txd->word0, TXD_W0_ACK);
 
/*
@@ -896,6 +888,18 @@ rt2400pci_txdone(void *data)
 
rt2x00_ring_index_done_inc(ring);
} while (!rt2x00_ring_empty(ring));
+
+   /*
+* Check if we are waiting on an empty queue
+* to start scanning.
+*/
+   if (rt2x00pci->scan
+   && rt2x00_ring_empty(&rt2x00pci->tx)
+   && rt2x00_ring_empty(&rt2x00pci->atim)
+   && rt2x00_ring_empty(&rt2x00pci->prio)) {
+   rt2x00pci->scan->status = SCANNING_READY;
+   complete(&rt2x00pci->scan->completion);
+   }
 }
 
 static irqreturn_t
@@ -1517,6 +1521,14 @@ rt2400pci_stop(struct net_device *net_de
rt2x00_register_write(rt2x00pci, CSR8, reg);
 
/*
+* Cancel scanning.
+*/
+   if (rt2x00pci->scan) {
+   rt2x00pci->scan->status = SCANNING_CANCELLED;
+   complete_all(&rt2x00pci->scan->completion);
+   }
+
+   /*
 * Free DMA rings.
 */
rt2400pci_free_rings(rt2x00pci);
@@ -1564,35 +1576,23 @@ static void
 rt2400pci_scan(void *data)
 {
struct rt2x00_pci   *rt2x00pci = data;
-   struct net_device   *net_dev = pci_get_drvdata(rt2x00pci->pci_dev);
-   struct skb_cb   *cb;
 
if (unlikely(!rt2x00pci->scan))
return;
 
/*
-* Check if we have to send a packet before the
-* channel switch.
+* Before we can start switch the channel for scanning
+* we need to wait untill all TX rings are empty to
+* guarentee that all frames are send on the correct channel.
 */
-   if (rt2x00pci->scan->conf.skb) {
-   cb = (struct skb_cb*)&rt2x00pci->scan->conf.skb->cb;
-   cb->scan_complete = 1;
-
-   if (rt2400pci_tx(net_dev, rt2x00pci->scan->conf.skb,
-   rt2x00pci->scan->conf.tx_control))
-   goto exit;
-
-   /*
-* Wait for the frame to be correctly transmitted.
-*/
+   if (rt2x00pci->scan->status != SCANNING_READY)
wait_for_completion(&rt2x00pci->scan->completion);
-   }
 
/*
 * Check if this scan has been cancelled while
 * work was still scheduled.
 */
-   if (rt2x00pci->scan->cancelled)
+   if (rt2x00pci->scan->status == SCANNING_CANCELLED)
goto exit;
 
/*
@@ -1633,9 +1633,24 @@ rt2400pci_passive_scan(struct net_device
 {
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
 
+   if (rt2x00pci->scan)
+   return -EBUSY;
+
+   /*
+* Allocate scanning structure to store scanning info.
+*/
rt2x00pci->scan = kmalloc(sizeof(struct scanning), GFP_ATOMIC);
if (!rt2x00pci->scan)
-   return 0;
+   return -ENOMEM;
+
+   /*
+* Check if we have to send a packet before the
+* channel switch.
+*/
+   if (conf->skb) {
+   if (rt2400pci_tx(net_dev, conf->skb, conf->tx_control))
+   goto exit;
+   }
 
/*
 * Initialize Scanning structure.
@@ -1646,14 +1661,21 @@ rt2400pci_passive_scan(struct net_device
 
rt2x00pci->scan->state = state;
 
-   rt2x00pci->scan->cancelled = 0;
+   rt2x00pci->scan->status = 0;
 
/*
 * Queue work.
 */
-   queue_work(rt2

[PATCH 5/32] rt2x00: Optimize RATE flag handling

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Optimize RATE flags by using the FIELD32() macro's,
also make the unit in which the rate is handled the
same as is used in the dscape stack.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:38:23.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:39:24.0 +0200
@@ -550,7 +550,7 @@ rt2400pci_config_duration(struct rt2x00_
rt2x00_register_read(rt2x00pci, CSR19, ®);
value = SIFS + (2 * short_slot_time);
rt2x00_set_field32(®, CSR19_DIFS, value);
-   value = SIFS + get_duration(IEEE80211_HEADER + ACK_SIZE, 2);
+   value = SIFS + get_duration(IEEE80211_HEADER + ACK_SIZE, 10);
rt2x00_set_field32(®, CSR19_EIFS, value);
rt2x00_register_write(rt2x00pci, CSR19, reg);
 
@@ -580,11 +580,11 @@ rt2400pci_config_rate(struct rt2x00_pci 
value = SIFS + PLCP
+ (2 * (conf->short_slot_time ? SHORT_SLOT_TIME : SLOT_TIME))
+ preamble
-   + get_duration(ACK_SIZE, 2);
+   + get_duration(ACK_SIZE, 10);
rt2x00_set_field32(®[0], TXCSR1_ACK_TIMEOUT, value);
value = SIFS + PLCP
+ preamble
-   + get_duration(ACK_SIZE, 2);
+   + get_duration(ACK_SIZE, 10);
rt2x00_set_field32(®[0], TXCSR1_ACK_CONSUME_TIME, value);
rt2x00_register_write(rt2x00pci, TXCSR1, reg[0]);
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:38:23.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:39:24.0 +0200
@@ -565,7 +565,7 @@ rt2500pci_config_duration(struct rt2x00_
rt2x00_register_read(rt2x00pci, CSR19, ®);
value = SIFS + (2 * short_slot_time);
rt2x00_set_field32(®, CSR19_DIFS, value);
-   value = SIFS + get_duration(IEEE80211_HEADER + ACK_SIZE, 2);
+   value = SIFS + get_duration(IEEE80211_HEADER + ACK_SIZE, 10);
rt2x00_set_field32(®, CSR19_EIFS, value);
rt2x00_register_write(rt2x00pci, CSR19, reg);
 
@@ -595,11 +595,11 @@ rt2500pci_config_rate(struct rt2x00_pci 
value = SIFS + PLCP
+ (2 * (conf->short_slot_time ? SHORT_SLOT_TIME : SLOT_TIME))
+ preamble
-   + get_duration(ACK_SIZE, 2);
+   + get_duration(ACK_SIZE, 10);
rt2x00_set_field32(®[0], TXCSR1_ACK_TIMEOUT, value);
value = SIFS + PLCP
+ preamble
-   + get_duration(ACK_SIZE, 2);
+   + get_duration(ACK_SIZE, 10);
rt2x00_set_field32(®[0], TXCSR1_ACK_CONSUME_TIME, value);
rt2x00_register_write(rt2x00pci, TXCSR1, reg[0]);
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:38:23.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:39:24.0 +0200
@@ -467,7 +467,7 @@ rt2500usb_config_rate(struct rt2x00_usb 
value = SIFS + PLCP
+ (2 * (conf->short_slot_time ? SHORT_SLOT_TIME : SLOT_TIME))
+ preamble
-   + get_duration(ACK_SIZE, 2);
+   + get_duration(ACK_SIZE, 10);
rt2x00_set_field16_nb(®, TXRX_CSR1_ACK_TIMEOUT, value);
rt2x00_register_write(rt2x00usb, TXRX_CSR1, reg);
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2x00.h 
2006-04-27 21:36:19.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2x00.h   
2006-04-27 21:39:24.0 +0200
@@ -609,71 +609,69 @@ struct scanning{
  * passed to the ieee80211 kernel. We need to make it a consist of
  * multiple fields because we want to store more then 1 device specific
  * values inside the value.
- * 1 - rate, stored as 0.5Mbit/s.
- * 2 - MASK_RATE, which rates are enabled in this mode, this mask
+ * 1 - rate, stored as 100 kbit/s.
+ * 2 - preamble, short_preamble enabled flag.
+ * 3 - MASK_RATE, which rates are enabled in this mode, this mask
  * corresponds with the TX register format for the current device.
- * 3 - plcp, 802.11b rates are device specific,
+ * 4 - plcp, 802.11b rates are device specific,
  * 802.11g rates are set according to the

[PATCH 23/32] rt2x00: Make correct cast in USB interrupt

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

The USB interrupt handler receives the entry
in the ring and not the ring itself.
Also check if the status indicates an error
before queueing the work.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:53:13.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:54:33.0 +0200
@@ -856,11 +856,14 @@ rt2500usb_txdone(void *data)
 static void
 rt2500usb_interrupt(struct urb *urb, struct pt_regs *regs)
 {
-   struct data_ring*ring = (struct data_ring*)urb->context;
+   struct data_entry   *entry = (struct data_entry*)urb->context;
struct rt2x00_usb   *rt2x00usb =
-   ieee80211_dev_hw_data(ring->net_dev);
+   ieee80211_dev_hw_data(entry->ring->net_dev);
 
-   queue_work(rt2x00usb->workqueue, &ring->irq_work);
+   if (urb->status)
+   return;
+
+   queue_work(rt2x00usb->workqueue, &entry->ring->irq_work);
 }
 
 /*
@@ -1064,7 +1067,6 @@ rt2500usb_init_txring(struct rt2x00_usb 
}
 }
 
-
 static int
 rt2500usb_init_rings(struct rt2x00_usb *rt2x00usb)
 {
@@ -1798,7 +1800,7 @@ rt2500usb_init_hw_channels(struct rt2x00
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
channels[counter].val = vals[counter] | rf2_base;
} else if (rt2x00_rf(&rt2x00usb->chip, RF2525E)) {
-   u32 vals[] = {
+   static u32 vals[] = {
0x089a, 0x089e, 0x089e, 0x08a2,
0x08a2, 0x08a6, 0x08a6, 0x08aa,
0x08aa, 0x08ae, 0x08ae, 0x08b2,


pgpbQxcfC8dzs.pgp
Description: PGP signature


[PATCH 7/32] rt2x00: make vals static

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

The vals[] arrays in *_init_hw_channels can be made
static to optimize memory and reduce stack size.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:40:06.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:40:43.0 +0200
@@ -1868,7 +1868,7 @@ rt2400pci_init_hw_channels(struct rt2x00
 {
int counter;
u16 eeprom;
-   u32 vals[] = {
+   static u32 vals[] = {
0x000c1fda, 0x000c1fee, 0x000c2002, 0x000c2016,
0x000c202a, 0x000c203e, 0x000c2052, 0x000c2066,
0x000c207a, 0x000c208e, 0x000c20a2, 0x000c20b6,
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:40:06.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:40:43.0 +0200
@@ -1929,9 +1929,9 @@ rt2500pci_init_hw_channels(struct rt2x00
struct ieee80211_channel *channels)
 {
int counter;
-   u16 eeprom;
u32 rf2_base;
-   struct {
+   u16 eeprom;
+   static struct {
unsigned int chip;
u32 val[3];
} rf[] = {
@@ -1947,16 +1947,16 @@ rt2500pci_init_hw_channels(struct rt2x00
 * Channel initialization.
 * First we set the basic variables.
 */
-   for (counter = 0; counter < 13; counter++) {
-   channels[counter].chan = counter + 1;
+   for (counter = 0; counter < 13; counter++) {
+   channels[counter].chan = counter + 1;
channels[counter].freq = 2407 + ((counter + 1) * 5);
channels[counter].flag = IEEE80211_CHAN_W_IBSS
| IEEE80211_CHAN_W_ACTIVE_SCAN | IEEE80211_CHAN_W_SCAN;
channels[counter].antenna_max = 0xff;
-   }
+   }
 
-   channels[13].chan = 14;
-   channels[13].freq = 2484;
+   channels[13].chan = 14;
+   channels[13].freq = 2484;
channels[13].flag = IEEE80211_CHAN_W_IBSS
| IEEE80211_CHAN_W_ACTIVE_SCAN | IEEE80211_CHAN_W_SCAN;
channels[13].antenna_max = 0xff;
@@ -1988,7 +1988,7 @@ rt2500pci_init_hw_channels(struct rt2x00
rf2_base = 0x0008;
 
if (rt2x00_rf(&rt2x00pci->chip, RF2522)) {
-   u32 vals[] = {
+   static u32 vals[] = {
0x000c1fda, 0x000c1fee, 0x000c2002, 0x000c2016,
0x000c202a, 0x000c203e, 0x000c2052, 0x000c2066,
0x000c207a, 0x000c208e, 0x000c20a2, 0x000c20b6,
@@ -2000,7 +2000,7 @@ rt2500pci_init_hw_channels(struct rt2x00
} else if (rt2x00_rf(&rt2x00pci->chip, RF2523)
|| rt2x00_rf(&rt2x00pci->chip, RF2524)
|| rt2x00_rf(&rt2x00pci->chip, RF2525)) {
-   u32 vals[] = {
+   static u32 vals[] = {
0x0c9e, 0x0ca2, 0x0ca6, 0x0caa,
0x0cae, 0x0cb2, 0x0cb6, 0x0cba,
0x0cbe, 0x0d02, 0x0d06, 0x0d0a,
@@ -2012,7 +2012,7 @@ rt2500pci_init_hw_channels(struct rt2x00
cpu_to_le32(vals[counter] | rf2_base);
} else if (rt2x00_rf(&rt2x00pci->chip, RF2525E)
|| rt2x00_rf(&rt2x00pci->chip, RF5222)) {
-   u32 vals[] = {
+   static u32 vals[] = {
0x1136, 0x113a, 0x113e, 0x1182,
0x1186, 0x118a, 0x118e, 0x1192,
0x1196, 0x119a, 0x119e, 0x11a2,
@@ -2024,7 +2024,7 @@ rt2500pci_init_hw_channels(struct rt2x00
cpu_to_le32(vals[counter] | rf2_base);
}
if (rt2x00_rf(&rt2x00pci->chip, RF5222)) {
-   u32 vals[] = {
+   static u32 vals[] = {
0x00018896, 0x0001889a, 0x0001889e, 0x000188a2,
0x000188a6, 0x000188aa, 0x000188ae, 0x000188b2,
0x8802, 0x8806, 0x880a, 0x880e,
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:40:06.0 +0200
+++ wi

[PATCH 20/32] rt2x00: byte ordering correctness

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Fix various little/big endian conversions.
rt2500pci should use cpu_to_le32 and rt2500usb should not.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:50:36.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:51:11.0 +0200
@@ -441,7 +441,7 @@ rt2500pci_config_channel(struct rt2x00_p
txpower = (txpower > 31) ? 31 : txpower;
 
if (rt2x00_rf(&rt2x00pci->chip, RF2525E) && channel == 14)
-   rf4 |= 0x0010;
+   rf4 |= cpu_to_le32(0x0010);
 
if (rt2x00_rf(&rt2x00pci->chip, RF5222)) {
if (channel < 14) {
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:50:36.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:51:11.0 +0200
@@ -324,20 +324,20 @@ rt2500usb_config_channel(struct rt2x00_u
 
if (rt2x00_rf(&rt2x00usb->chip, RF5222)) {
if (channel < 14) {
-   rf1 = cpu_to_le32(0x00022020);
-   rf4 = cpu_to_le32(0x0a0b);
+   rf1 = 0x00022020;
+   rf4 = 0x0a0b;
} else if (channel == 14) {
-   rf1 = cpu_to_le32(0x00022010);
-   rf4 = cpu_to_le32(0x0a1b);
+   rf1 = 0x00022010;
+   rf4 = 0x0a1b;
} else if (channel < 64) {
-   rf1 = cpu_to_le32(0x00022010);
-   rf4 = cpu_to_le32(0x0a1f);
+   rf1 = 0x00022010;
+   rf4 = 0x0a1f;
} else if (channel < 140) {
-   rf1 = cpu_to_le32(0x00022010);
-   rf4 = cpu_to_le32(0x0a0f);
+   rf1 = 0x00022010;
+   rf4 = 0x0a0f;
} else if (channel < 161) {
-   rf1 = cpu_to_le32(0x00022020);
-   rf4 = cpu_to_le32(0x0a07);
+   rf1 = 0x00022020;
+   rf4 = 0x0a07;
}
}
 
@@ -1829,7 +1829,7 @@ rt2500usb_init_hw_channels(struct rt2x00
};
 
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
-   channels[counter].val = cpu_to_le32(vals[counter]);
+   channels[counter].val = vals[counter];
} else if (rt2x00_rf(&rt2x00usb->chip, RF2523)
|| rt2x00_rf(&rt2x00usb->chip, RF2524)
|| rt2x00_rf(&rt2x00usb->chip, RF2525)) {
@@ -1841,8 +1841,7 @@ rt2500usb_init_hw_channels(struct rt2x00
};
 
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
-   channels[counter].val =
-   cpu_to_le32(vals[counter] | rf2_base);
+   channels[counter].val = vals[counter] | rf2_base;
} else if (rt2x00_rf(&rt2x00usb->chip, RF2525E)) {
u32 vals[] = {
0x089a, 0x089e, 0x089e, 0x08a2,
@@ -1852,7 +1851,7 @@ rt2500usb_init_hw_channels(struct rt2x00
};
 
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
-   channels[counter].val = cpu_to_le32(vals[counter]);
+   channels[counter].val = vals[counter];
} else if (rt2x00_rf(&rt2x00usb->chip, RF5222)) {
static u32 vals[] = {
0x1136, 0x113a, 0x113e, 0x1182,
@@ -1868,7 +1867,7 @@ rt2500usb_init_hw_channels(struct rt2x00
};
 
for (counter = 0; counter < ARRAY_SIZE(vals); counter++)
-   channels[counter].val = cpu_to_le32(vals[counter]);
+   channels[counter].val = vals[counter];
}
 
/*
@@ -1895,9 +1894,9 @@ rt2500usb_init_hw_channels(struct rt2x00
 */
for (counter = 0; counter < ARRAY_SIZE(rf); counter++) {
if (rt2x00_rf(&rt2x00usb->chip, rf[counter].chip)) {
-   rt2x00usb->rf1 = cpu_to_le32(rf[counter].val[0]);
-   rt2x00usb->rf3 = cpu_to_le32(rf[counter].val[1]);
-   rt2x00usb->rf4 = cpu_to_le32(rf[counter].val[2]);
+   rt2x00usb->rf1 = rf[counter].val[0];
+   rt2x00usb->rf3 = rf[counter].val[1];
+   rt2x00usb->rf4 = rf[counter

[PATCH 8/32] rt2x00: Invalid memory allocation check

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Fix invalid check when allocating the memory for
the rate structures. Instead of the channel pointer
the rates pointer should be verified.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:40:43.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:41:20.0 +0200
@@ -2036,7 +2036,7 @@ rt2400pci_init_hw(struct rt2x00_pci *rt2
hw->modes->num_rates = 4;
hw->modes->rates =
kzalloc(sizeof(struct ieee80211_rate) * 4, GFP_KERNEL);
-   if (!hw->modes->channels)
+   if (!hw->modes->rates)
goto exit_free_channels;
 
/*
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:40:43.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:41:20.0 +0200
@@ -2236,7 +2236,7 @@ rt2500pci_init_hw(struct rt2x00_pci *rt2
hw->modes->rates =
kzalloc((sizeof(struct ieee80211_rate) * 12),
GFP_KERNEL);
-   if (!hw->modes->channels)
+   if (!hw->modes->rates)
goto exit_free_channels;
} else {
hw->num_modes = 3;
@@ -2255,7 +2255,7 @@ rt2500pci_init_hw(struct rt2x00_pci *rt2
hw->modes->rates =
kzalloc((sizeof(struct ieee80211_rate) * 12),
GFP_KERNEL);
-   if (!hw->modes->channels)
+   if (!hw->modes->rates)
goto exit_free_channels;
}
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:40:43.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:41:20.0 +0200
@@ -1931,7 +1931,7 @@ rt2500usb_init_hw(struct rt2x00_usb *rt2
hw->modes->rates =
kzalloc((sizeof(struct ieee80211_rate) * 12),
GFP_KERNEL);
-   if (!hw->modes->channels)
+   if (!hw->modes->rates)
goto exit_free_channels;
} else {
hw->num_modes = 3;
@@ -1950,7 +1950,7 @@ rt2500usb_init_hw(struct rt2x00_usb *rt2
hw->modes->rates =
kzalloc((sizeof(struct ieee80211_rate) * 12),
GFP_KERNEL);
-   if (!hw->modes->channels)
+   if (!hw->modes->rates)
goto exit_free_channels;
}
 


pgp2KiQ7ZKxrx.pgp
Description: PGP signature


[PATCH 9/32] rt2x00: Fix antenna configuration

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

The handling of the antenna configuration was not
completely correct. For all modules the double clearing
of some bits can be reduced, and for rt2500pci and rt2500usb
some registers were not corretly changed.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:41:20.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:41:52.0 +0200
@@ -485,6 +485,9 @@ rt2400pci_config_antenna(struct rt2x00_p
rt2x00_bbp_read(rt2x00pci, 4, ®_rx);
rt2x00_bbp_read(rt2x00pci, 1, ®_tx);
 
+   /*
+* Clear current config antenna bits.
+*/
reg_rx &= ~0x06;
reg_tx &= ~0x03;
 
@@ -495,18 +498,18 @@ rt2400pci_config_antenna(struct rt2x00_p
 */
if (antenna == 0) {
/* Diversity. */
-   reg_rx = (reg_rx & 0xf9) | 0x02;
-   reg_tx = (reg_tx & 0xfc) | 0x01;
+   reg_rx |= 0x02;
+   reg_tx |= 0x01;
} else if (antenna == 1) {
/* RX: Antenna B */
-   reg_rx = (reg_rx & 0xf9) | 0x04;
+   reg_rx |= 0x04;
/* TX: Antenna A */
-   reg_tx = (reg_tx & 0xfc) | 0x00;
+   reg_tx |= 0x00;
} else if (antenna == 2) {
/* RX: Antenna A */
-   reg_rx = (reg_rx & 0xf9) | 0x00;
+   reg_rx |= 0x00;
/* TX: Antenna B */
-   reg_tx = (reg_tx & 0xfc) | 0x02;
+   reg_tx |= 0x02;
}
 
rt2x00_bbp_write(rt2x00pci, 4, reg_rx);
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:41:20.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:41:52.0 +0200
@@ -506,12 +506,17 @@ rt2500pci_config_channel(struct rt2x00_p
 static void
 rt2500pci_config_antenna(struct rt2x00_pci *rt2x00pci, int antenna)
 {
+   u32 reg;
u8  reg_rx;
u8  reg_tx;
 
+   rt2x00_register_read(rt2x00pci, BBPCSR1, ®);
rt2x00_bbp_read(rt2x00pci, 14, ®_rx);
rt2x00_bbp_read(rt2x00pci, 2, ®_tx);
 
+   /*
+* Clear current config antenna bits.
+*/
reg_rx &= ~0x06;
reg_tx &= ~0x03;
 
@@ -522,20 +527,46 @@ rt2500pci_config_antenna(struct rt2x00_p
 */
if (antenna == 0) {
/* Diversity. */
-   reg_rx = (reg_rx & 0xf9) | 0x02;
-   reg_tx = (reg_tx & 0xfc) | 0x01;
+   reg_rx |= 0x02;
+   reg_tx |= 0x01;
+   rt2x00_set_field32(®, BBPCSR1_CCK, 2);
+   rt2x00_set_field32(®, BBPCSR1_OFDM, 2);
} else if (antenna == 1) {
/* RX: Antenna B */
-   reg_rx = (reg_rx & 0xf9) | 0x04;
+   reg_rx |= 0x04;
/* TX: Antenna A */
-   reg_tx = (reg_tx & 0xfc) | 0x00;
+   reg_tx |= 0x00;
+   rt2x00_set_field32(®, BBPCSR1_CCK, 0);
+   rt2x00_set_field32(®, BBPCSR1_OFDM, 0);
} else if (antenna == 2) {
/* RX: Antenna A */
-   reg_rx = (reg_rx & 0xf9) | 0x00;
+   reg_rx |= 0x00;
/* TX: Antenna B */
-   reg_tx = (reg_tx & 0xfc) | 0x02;
+   reg_tx |= 0x02;
+   rt2x00_set_field32(®, BBPCSR1_CCK, 2);
+   rt2x00_set_field32(®, BBPCSR1_OFDM, 2);
+   }
+
+   /*
+* RT2525E and RT5222 need to flip TX I/Q
+*/
+   if (rt2x00_rf(&rt2x00pci->chip, RF2525E)
+   || rt2x00_rf(&rt2x00pci->chip, RF5222)) {
+   reg_tx |= 0x04;
+   rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 1);
+   rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 1);
+
+   /*
+* RT2525E does not need RX I/Q Flip.
+*/
+   if (rt2x00_rf(&rt2x00pci->chip, RF2525E))
+   reg_rx &= ~0x04;
+   } else {
+   rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 0);
+   rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 0);
}
 
+   rt2x00_register_write(rt2x00pci, BBPCSR1, reg);
rt2x00_bbp_write(rt2x00pci, 14, reg_rx);
rt2x00_bbp_write(rt2x00pci, 2, reg_tx);
 
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-

[PATCH 25/32] rt2x00: Add flag handlers

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Add flag handlers to set the state and capabilities of
the driver.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:53:13.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:56:05.0 +0200
@@ -1099,7 +1099,7 @@ rt2400pci_allocate_rings(struct rt2x00_p
return -ENOMEM;
}
 
-   rt2x00pci->atim_available = 1;
+   SET_FLAG(rt2x00pci, ATIM_AVAILABLE);
 
if (rt2400pci_alloc_ring(
rt2x00pci, &rt2x00pci->ring[RING_RX], rt2400pci_rxdone,
@@ -1549,6 +1549,8 @@ rt2400pci_open(struct net_device *net_de
rt2x00_set_field32(®, CSR8_RXDONE, 0);
rt2x00_register_write(rt2x00pci, CSR8, reg);
 
+   SET_FLAG(rt2x00pci, RADIO_ENABLED);
+
return 0;
 
 exit_fail:
@@ -1563,6 +1565,8 @@ rt2400pci_stop(struct net_device *net_de
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
u32 reg;
 
+   CLEAR_FLAG(rt2x00pci, RADIO_ENABLED);
+
rt2x00_register_write(rt2x00pci, PWRCSR0, 0);
 
/*
@@ -1972,16 +1976,11 @@ rt2400pci_init_eeprom(struct rt2x00_pci 
rt2x00pci->led_mode = rt2x00_get_field16(eeprom,
EEPROM_ANTENNA_LED_MODE);
 
-#ifdef CONFIG_RT2400PCI_BUTTON
/*
 * 6 - Detect if this device has an hardware controlled radio.
-* If this device is not hardware controlled, disable polling timer.
 */
if (rt2x00_get_field16(eeprom, EEPROM_ANTENNA_HARDWARE_RADIO))
-   rt2x00pci->button_status = BUTTON_STATUS_OFF;
-   else
-   rt2x00pci->button_status = BUTTON_STATUS_UNAVAILABLE;
-#endif /* CONFIG_RT2400PCI_BUTTON */
+   SET_FLAG(rt2x00pci, HARDWARE_BUTTON);
 
/*
 * 7 - Read BBP data from EEPROM and store in private structure.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.h  
2006-04-27 21:53:13.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.h
2006-04-27 21:56:05.0 +0200
@@ -868,6 +868,11 @@ struct data_entry{
  * Device specific structure.
  */
 struct rt2x00_pci{
+   /*
+* Device flags.
+*/
+   unsigned intflags;
+
 #ifdef CONFIG_RT2400PCI_BUTTON
/*
 * ACPI device for generation of ACPI events.
@@ -935,8 +940,6 @@ struct rt2x00_pci{
 */
int false_cca;
 
-   int atim_available;
-
/*
 * EEPROM bus width.
 */
@@ -987,7 +990,7 @@ rt2x00pci_get_ring(struct rt2x00_pci *rt
 {
u8  atim;
 
-   atim = rt2x00pci->atim_available;
+   atim = GET_FLAG(rt2x00pci, ATIM_AVAILABLE);
 
/*
 * Check if the rings have been allocated.
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:53:13.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:56:05.0 +0200
@@ -1180,7 +1180,7 @@ rt2500pci_allocate_rings(struct rt2x00_p
return -ENOMEM;
}
 
-   rt2x00pci->atim_available = 1;
+   SET_FLAG(rt2x00pci, ATIM_AVAILABLE);
 
if (rt2500pci_alloc_ring(
rt2x00pci, &rt2x00pci->ring[RING_RX], rt2500pci_rxdone,
@@ -1657,6 +1657,8 @@ rt2500pci_open(struct net_device *net_de
rt2x00_set_field32(®, CSR8_RXDONE, 0);
rt2x00_register_write(rt2x00pci, CSR8, reg);
 
+   SET_FLAG(rt2x00pci, RADIO_ENABLED);
+
return 0;
 
 exit_fail:
@@ -1671,6 +1673,8 @@ rt2500pci_stop(struct net_device *net_de
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
u32 reg;
 
+   CLEAR_FLAG(rt2x00pci, RADIO_ENABLED);
+
rt2x00_register_write(rt2x00pci, PWRCSR0, 0);
 
/*
@@ -1929,7 +1933,7 @@ rt2500pci_conf_tx(struct net_device *net
 
/*
 * The passed variables are stored as real value ((2^n)-1).
-* RT2400 registers require to know the bit number 'n'.
+* RT2500 registers require to know the bit number 'n'.
 */
if (params->cw_min)
ring->tx_params.cw_min = HIGHEST_BIT16(params->cw_min) + 1;
@@ -2075,16 +2079,11 @@ rt2500pci_init_eeprom(struct rt2x00_p

[PATCH 4/32] rt2x00: Add eeprom_multiread function

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Add the eeprom_multiread function and clean up the code
a bit by using it as well. ;)

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:37:02.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:38:23.0 +0200
@@ -351,6 +351,17 @@ rt2x00_eeprom_read(
rt2x00_eeprom_pulse_low(rt2x00pci, &flags);
 }
 
+static void
+rt2x00_eeprom_multiread(
+   const struct rt2x00_pci *rt2x00pci,
+   const u8 word, u16 *data, const u16 length)
+{
+   int counter;
+
+   for (counter = 0; counter < (length / sizeof(u16)); counter++)
+   rt2x00_eeprom_read(rt2x00pci, word + counter, data++);
+}
+
 /*
  * Configuration handlers.
  */
@@ -1824,9 +1835,8 @@ rt2400pci_init_eeprom(struct rt2x00_pci 
/*
 * 7 - Read BBP data from EEPROM and store in private structure.
 */
-   for (counter = 0; counter < EEPROM_BBP_SIZE; counter++)
-   rt2x00_eeprom_read(rt2x00pci, EEPROM_BBP_START + counter,
-   &rt2x00pci->eeprom[counter]);
+   rt2x00_eeprom_multiread(rt2x00pci, EEPROM_BBP_START,
+   &rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
 
return 0;
 }
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500pci.c  
2006-04-27 21:37:02.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500pci.c
2006-04-27 21:38:23.0 +0200
@@ -351,6 +351,17 @@ rt2x00_eeprom_read(
rt2x00_eeprom_pulse_low(rt2x00pci, &flags);
 }
 
+static void
+rt2x00_eeprom_multiread(
+   const struct rt2x00_pci *rt2x00pci,
+   const u8 word, u16 *data, const u16 length)
+{
+   int counter;
+
+   for (counter = 0; counter < (length / sizeof(u16)); counter++)
+   rt2x00_eeprom_read(rt2x00pci, word + counter, data++);
+}
+
 /*
  * Configuration handlers.
  */
@@ -1886,9 +1897,8 @@ rt2500pci_init_eeprom(struct rt2x00_pci 
/*
 * 7 - Read BBP data from EEPROM and store in private structure.
 */
-   for (counter = 0; counter < EEPROM_BBP_SIZE; counter++)
-   rt2x00_eeprom_read(rt2x00pci, EEPROM_BBP_START + counter,
-   &rt2x00pci->eeprom[counter]);
+   rt2x00_eeprom_multiread(rt2x00pci, EEPROM_BBP_START,
+   &rt2x00pci->eeprom, EEPROM_BBP_SIZE * sizeof(u16));
 
return 0;
 }
diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2500usb.c  
2006-04-27 21:36:17.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2500usb.c
2006-04-27 21:38:23.0 +0200
@@ -228,11 +228,21 @@ rf_write:
 static inline void
 rt2x00_eeprom_read(
const struct rt2x00_usb *rt2x00usb,
-   const u16 offset, u16 *value, const u16 length)
+   const u16 word, u16 *data)
 {
rt2x00_vendor_request(
rt2x00usb, USB_EEPROM_READ, USB_VENDOR_REQUEST_IN,
-   offset, 0x00, value, length);
+   word, 0x00, data, 2);
+}
+
+static void
+rt2x00_eeprom_multiread(
+   const struct rt2x00_usb *rt2x00usb,
+   const u8 word, u16 *data, const u16 length)
+{
+   rt2x00_vendor_request(
+   rt2x00usb, USB_EEPROM_READ, USB_VENDOR_REQUEST_IN,
+   word, 0x00, data, length);
 }
 
 /*
@@ -1552,7 +1562,7 @@ rt2500usb_init_eeprom(struct rt2x00_usb 
/*
 * 1 - Read EEPROM word for configuration.
 */
-   rt2x00_eeprom_read(rt2x00usb, EEPROM_ANTENNA, &eeprom, 2);
+   rt2x00_eeprom_read(rt2x00usb, EEPROM_ANTENNA, &eeprom);
 
/*
 * 2 - Identify RF chipset.
@@ -1579,7 +1589,7 @@ rt2500usb_init_eeprom(struct rt2x00_usb 
 * 5 - Read BBP data from EEPROM and store in private structure.
 */
memset(&rt2x00usb->eeprom, 0x00, sizeof(rt2x00usb->eeprom));
-   rt2x00_eeprom_read(rt2x00usb, EEPROM_BBP_START,
+   rt2x00_eeprom_multiread(rt2x00usb, EEPROM_BBP_START,
&rt2x00usb->eeprom[0], EEPROM_BBP_SIZE);
 
return 0;
@@ -1595,7 +1605,7 @@ rt2500usb_init_mac(struct rt2x00_usb *rt
/*
 * Read MAC address from EEPROM.
 */
-   rt2x00_eeprom_read(rt2x00usb, EEPROM_MAC_ADDR, ®[0], 6);
+   rt2x00_eeprom_multiread(rt2x00usb, EEPROM_MAC_ADDR, ®[0], 6);
 
net_dev->dev_addr[0] = rt2x00_get_field16(reg[0], MAC_CSR2_BYTE0);
  

[PATCH 18/32] rt2x00: Make sure device has reached requested state while suspend/resume

2006-04-27 Thread Ivo van Doorn
From: Ivo van Doorn <[EMAIL PROTECTED]>

Add the *_set_state functions which makes sure
the device is switching state to awake or sleep.
Fix bad behaviour in the suspend routine,
and disable the radio before suspending.

Signed-off-by: Ivo van Doorn <[EMAIL PROTECTED]>

diff -uprN wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c 
wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
--- wireless-dev-rt2x00/drivers/net/wireless/d80211/rt2x00/rt2400pci.c  
2006-04-27 21:49:08.0 +0200
+++ wireless-dev-rt2x00-patch/drivers/net/wireless/d80211/rt2x00/rt2400pci.c
2006-04-27 21:49:59.0 +0200
@@ -653,6 +653,44 @@ rt2400pci_link_tuner(struct rt2x00_pci *
 }
 
 /*
+ * Device state switch.
+ * This will put the device to sleep, or awake it.
+ */
+static int
+rt2400pci_set_state(struct rt2x00_pci *rt2x00pci, enum dev_state state)
+{
+   u32 reg;
+   int counter;
+   charput_to_sleep;
+
+   put_to_sleep = (state != STATE_AWAKE);
+
+   rt2x00_register_read(rt2x00pci, PWRCSR1, ®);
+   rt2x00_set_field32(®, PWRCSR1_SET_STATE, 1);
+   rt2x00_set_field32(®, PWRCSR1_BBP_DESIRE_STATE, state);
+   rt2x00_set_field32(®, PWRCSR1_RF_DESIRE_STATE, state);
+   rt2x00_set_field32(®, PWRCSR1_PUT_TO_SLEEP, put_to_sleep);
+   rt2x00_register_write(rt2x00pci, PWRCSR1, reg);
+
+   /*
+* Device is not guarenteed to be in the requested state yet.
+* We must wait untill the register indicates that the
+* device has entered the correct state.
+*/
+   for (counter = 0; counter < REGISTER_BUSY_COUNT; counter++) {
+   rt2x00_register_read(rt2x00pci, PWRCSR1, ®);
+   if ((rt2x00_get_field32(reg, PWRCSR1_BBP_CURR_STATE) == state)
+   && (rt2x00_get_field32(reg, PWRCSR1_RF_CURR_STATE) == state))
+   return 0;
+   msleep(10);
+   }
+
+   NOTICE("Device failed to %s.\n" , put_to_sleep ? "suspend" : "resume");
+
+   return -EBUSY;
+}
+
+/*
  * TX descriptor initialization
  */
 static void
@@ -1190,6 +1228,9 @@ rt2400pci_init_registers(struct rt2x00_p
 {
u32 reg;
 
+   if (rt2400pci_set_state(rt2x00pci, STATE_AWAKE))
+   return -EBUSY;
+
rt2x00_register_write(rt2x00pci, PWRCSR0, cpu_to_le32(0x3f3b3100));
 
rt2x00_register_write(rt2x00pci, PSCSR0, cpu_to_le32(0x00020002));
@@ -2342,57 +2383,42 @@ rt2400pci_remove(struct pci_dev *pci_dev
 }
 
 #ifdef CONFIG_PM
-static int rt2400pci_resume(struct pci_dev *pci_dev);
-
 static int
 rt2400pci_suspend(struct pci_dev *pci_dev, pm_message_t state)
 {
struct net_device   *net_dev = pci_get_drvdata(pci_dev);
struct rt2x00_pci   *rt2x00pci = ieee80211_dev_hw_data(net_dev);
-   int counter;
-   u32 reg;
 
NOTICE("Going to sleep.\n");
 
-   if (ieee80211_netif_oper(net_dev, NETIF_DETACH))
-   return -EBUSY;
-
-   rt2x00_register_read(rt2x00pci, PWRCSR1, ®);
-   rt2x00_set_field32(®, PWRCSR1_SET_STATE, 1);
-   rt2x00_set_field32(®, PWRCSR1_BBP_DESIRE_STATE, 1);
-   rt2x00_set_field32(®, PWRCSR1_RF_DESIRE_STATE, 1);
-   rt2x00_set_field32(®, PWRCSR1_PUT_TO_SLEEP, 1);
-   rt2x00_register_write(rt2x00pci, PWRCSR1, reg);
-
/*
-* Device is not guarenteed to be asleep yet.
-* We must wait untill the register indicates
-* device has been correctly put to sleep.
+* If radio was enabled, stop radio and
+* set the resume flag to the radio will be enabled
+* when resuming.
 */
-   for (counter = 0; counter < REGISTER_BUSY_COUNT; counter++) {
-   rt2x00_register_read(rt2x00pci, PWRCSR1, ®);
-   if ((rt2x00_get_field32(reg, PWRCSR1_BBP_CURR_STATE) == 1)
-   && (rt2x00_get_field32(reg, PWRCSR1_RF_CURR_STATE) == 1))
-   break;
-   NOTICE("Waiting for device to sleep.\n");
-   msleep(10);
+   if (GET_FLAG(rt2x00pci, RADIO_ENABLED)) {
+   if (net_dev->stop(net_dev))
+   return -EBUSY;
+   SET_FLAG(rt2x00pci, RADIO_RESUME);
}
 
-   if (counter == REGISTER_BUSY_COUNT)
-   goto exit;
-
-   if (pci_enable_wake(pci_dev, pci_choose_state(pci_dev, state), 1)
-   || pci_save_state(pci_dev)
-   || pci_set_power_state(pci_dev, pci_choose_state(pci_dev, state)))
-   goto exit;
-
-   return 0;
+   /*
+* Set device mode to sleep for power management.
+*/
+   if (rt2400pci_set_state(rt2x00pci, STATE_SLEEP))
+   return -EBUSY;
 
-exit:
-   ERROR("Failed to suspend device.\n");
+   /*
+* Uninitialize hardware.
+*/
+   rt2400pci_uninitialize(net_dev);
 
-   rt2400pci_resume(pci_dev);
-   return

Re: Netpoll checksum issue

2006-04-27 Thread Herbert Xu
On Thu, Apr 27, 2006 at 08:57:33PM +0800, Aubrey wrote:
> 
> Is there any update of this issue?

Assuming that the CHECKSUM_UNNECESSARY line wasn't there, then the
problem is simply that your packet has the wrong UDP checksum.
So I suggest that you print the packet out and compare it with
the original to see where the corruption is.

I don't see how the generic networking stack or netpoll could be
causing your problem.

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <[EMAIL PROTECTED]>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: 2.6.16.11 BUG at tg3.c:2917

2006-04-27 Thread Ed L. Cashin
On Thu, Apr 27, 2006 at 08:45:24AM -0700, Michael Chan wrote:
> On Thu, 2006-04-27 at 12:52 -0400, Ed L. Cashin wrote:
> > -- [please bite here ] -
> > Kernel BUG at drivers/net/tg3.c:2917
> > invalid opcode:  [1] SMP 
> > CPU 0 
> 
> Most likely caused by IO re-ordering. Try the test patch in this
> discussion:
> 
> http://marc.theaimsgroup.com/?l=linux-netdev&m=113890239404768&w=2

I'm afraid I might be generating noise here.  After my initial post I
found that I cannot trigger a panic without the latest changes to the
aoe driver in place.  I haven't been able to trigger a panic using the
aoe driver inside 2.6.16.11.

I think we've identified the problem in the aoe driver, but if I'm
wrong, I will certainly try the TG3_FLAG_MBOX_WRITE_REORDER patch you
mention.

-- 
  Ed L Cashin <[EMAIL PROTECTED]>
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


RE: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread Caitlin Bestler
[EMAIL PROTECTED] wrote:
> From: Evgeniy Polyakov <[EMAIL PROTECTED]>
> Date: Thu, 27 Apr 2006 15:51:26 +0400
> 
>> There are some caveats here found while developing zero-copy sniffer
>> [1]. Project's goal was to remap skbs into userspace in real-time.
>> While absolute numbers (posted to netdev@) were really high, it is
>> only applicable to read-only application. As was shown in IOAT
>> thread, data must be warmed in caches, so reading from mapped area
>> will be as fast as memcpy() (read+write), and copy_to_user()
>> actually almost equal to memcpy() (benchmarks were posted to
>> netdev@). And we must add remapping overhead.
> 
> Yes, all of these issues are related quite strongly.  Thanks
> for making the connection explicit.
> 
> But, the mapping overhead is zero for this net channel stuff,
> at least as it is implemented and designed by Kelly.  Ring
> buffer is setup ahead of time into the user's address space,
> and a ring of buffers into that area are given to the networking card.
> 
> We remember the translations here, so no get_user_pages() on
> each transfer and garbage like that.  And yes this all harks
> back to the issues that are discussed in Chapter 5 of
> Networking Algorithmics.
> But the core thing to understand is that by defining a new
> API and setting up the buffer pool ahead of time, we avoid all of the
> get_user_pages() overhead while retaining full kernel/user protection.
> 
> Evgeniy, the difference between this and your work is that
> you did not have an intelligent piece of hardware that could
> be told to recognize flows, and only put packets for a
> specific flow into that's flow's buffer pool.
> 
>> If we want to dma data from nic into premapped userspace area, this
>> will strike with message sizes/misalignment/slow read and so on, so
>> preallocation has even more problems.
> 
> I do not really think this is an issue, we put the full
> packet into user space and teach it where the offset is to
> the actual data.
> We'll do the same things we do today to try and get the data
> area aligned.  User can do whatever is logical and relevant
> on his end to deal with strange cases.
> 
> In fact we can specify that card has to take some care to get
> data area of packet aligned on say an 8 byte boundary or
> something like that.  When we don't have hardware assist, we
> are going to be doing copies.
> 
>> This change also requires significant changes in application, at
>> least until recv/send are changed, which is not the best thing to do.
> 
> This is exactly the point, we can only do a good job and
> receive zero copy if we can change the interfaces, and that's
> exactly what we're doing here.
> 
>> I do think that significant win in VJ's tests belongs not to
>> remapping and cache-oriented changes, but to move all protocol
>> processing into process' context.
> 
> I partly disagree.  The biggest win is eliminating all of the
> control overhead (all of "softint RX + protocol demux + IP
> route lookup + socket lookup" is turned into single flow
> demux), and the SMP safe data structure which makes it
> realistic enough to always move the bulk of the packet work
> to the socket's home cpu.
> 
> I do not think userspace protocol implementation buys enough
> to justify it.  We have to do the protection switch in and
> out of kernel space anyways, so why not still do the
> protected protocol processing work in the kernel?  It is
> still being done on the user's behalf, contributes to his
> time slice, and avoids all of the terrible issues of
> userspace protocol implementations.
> 
> So in my mind, the optimal situation from both a protection
> preservation and also a performance perspective is net
> channels to kernel socket protocol processing, buffers DMA'd
> directly into userspace if hardware assist is present.
> 

Having a ring that is already flow qualified is indeed the
most important savings, and worth pursuing even if reaching
consensus on how to safely enable user-mode L4 processing.
The latter *can* be a big advantage when the L4 processing
can be done based on a user-mode call from an already
scheduled process. But the benefit is not there for a process
that needs to be woken up each time it receives a short request.

So the real issue is when there is an intelligent device that
uses hardware packet classification to place the packet in
the correct ring. We don't want to bypass packet filtering,
but it would be terribly wasteful to reclassify the packet.
Intelligent NICs will have packet classification capabilities
to support RDMA and iSCSI. Those capabilities should be available
to benefit SOCK_STREAM and SOCK_DGRAM users as well without it
being a choice of either turning all stack control over to
the NIC or ignorign all NIC capabilities beyound pretending
to be a dumb Ethernet NIC.

For example, counting packets within an approved connection
is a valid goal that the final solution should support. But
would a simple count be sufficient, or do we truly need the
full

Re: tune back idle cwnd closing?

2006-04-27 Thread Rick Jones
having looked now at both 2861 and the 99 paper it references I see lots 
of "may's" "mights" and "belief" but nothing "real world."


the CWV vs non CWV was done against a TCP that did indeed reset cwnd 
after an RTT of idle, so it wasn't showing reset at idle versus no reset 
at idle.  just CWV's less draconian (?) reset than the non CWV stack.


the experimental validation in the 99 paper was still a simulation using 
dummynet and a number of buffers rather smaller than what modem banks 
were offering at the time, and it was for a modem, rather than any other 
sort of link. and when they did use a real modem, the buffering in the 
modem bank seems to have made the whole thing moot.


there was nothing about effect on intranets, or high-speed long hauls or 
any of that.



what that means wrt having a sysctl to enable/disable functionality 
still listed as experimental i'm not sure


rick jones
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] e1000 performance patch

2006-04-27 Thread Robin Humble
On Thu, Apr 27, 2006 at 09:07:36AM -0700, Rick Jones wrote:
>There should be three basic measures there - one is the single-instance 
>request-response test. The idea is to see minimum latency.  That test 
>likes to see the interrupt throttle rate made very high, or disabled 
>completely.
>
>The aggregate TCP_RR's and the TCP_STREAM tests are there to show what 
>effect that has on the ability to do aggregate request/response and a 
>bulk transfer.

I guess the whole point of my patch is to try to handle all these cases
efficiently without user intervention by making the driver self-tune
the InterruptThrottleRate depending on what traffic it's seeing.

I think it's doing the right things so far - at least it's a good
compromise - it probably won't ever be ideal in all workloads.

>>can netperf (or some other tool) mix up big and small message sizes
>>like 'the real world' perhaps does?
>>that might help me find a good frequency at which to try to adapt the
>>ITR... (eg. 1, 10, 100 or 1000 times a second)
>
>There is the "vst" (variable size test IIRC) in netperf4:
>
>http://www.netperf.org/svn/netperf4/branches/glib_migration
>
>The docs for netperf4 are presently pathetic.  Feel free to email me for 
>bootstrapping information.  Basically, you'll need pkg-config, libxml2 
>and glib-2.0 on the system.

thanks. I'll check it out.

actually, thinking about it more, the worst case for the patched driver
is a quiescent system (where ITR will be maximum) which then sees a
stream of large messages - say 500MB (~=5s at 1Gbit). so until the
watchdog kicks in (every 2s at the moment) and lowers the ITR then the
load on the cpu will be high.
The only solution for this is to run the ITR resetting watchdog as
often as possible. ie. times per second.

And then test it on real codes that do some sort of large message
bursty communication and see if they run faster or slower.

The patched driver will actually deal fairly well with a mixed size
workload as some of the workload will be large messages and that will
(on average) lower the ITR automatically.

cheers,
robin
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [stable] [PATCH] e1000: Update truesize with the length of the packet for packet split

2006-04-27 Thread Greg KH
On Tue, Apr 25, 2006 at 11:16:29PM -0700, Kok, Auke wrote:
> 
> Update skb with the real packet size.
> 
> 
> Signed-off-by: Jesse Brandeburg <[EMAIL PROTECTED]>
> Signed-off-by: Auke Kok <[EMAIL PROTECTED]>
> Signed-off-by: John Ronciak <[EMAIL PROTECTED]>

queued to -stable.

thanks,

greg k-h
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: tune back idle cwnd closing?

2006-04-27 Thread David S. Miller
From: John Heffner <[EMAIL PROTECTED]>
Date: Thu, 27 Apr 2006 13:47:33 -0400

> (Most OS's don't do 2861, and it is not a standard.)

Are you so sure?  Doing cwnd timeout largely predates the congestion
window validation work, in fact by several years.

In RFC 2581, it mentions Van Jacobson's recommendation of this idle
period behavior, as just one example.

Your arguments about "all the feedback mechanisms are in place, so not
reducing the cwnd after idle doesn't hurt congestion control" could be
applied to the packet retransmit timeout handling of the congestion
window, and I think that's kind of silly.
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread David S. Miller
From: Evgeniy Polyakov <[EMAIL PROTECTED]>
Date: Thu, 27 Apr 2006 15:51:26 +0400

> There are some caveats here found while developing zero-copy sniffer
> [1]. Project's goal was to remap skbs into userspace in real-time.
> While absolute numbers (posted to netdev@) were really high, it is only
> applicable to read-only application. As was shown in IOAT thread,
> data must be warmed in caches, so reading from mapped area will be as
> fast as memcpy() (read+write), and copy_to_user() actually almost equal
> to memcpy() (benchmarks were posted to netdev@). And we must add
> remapping overhead.

Yes, all of these issues are related quite strongly.  Thanks for
making the connection explicit.

But, the mapping overhead is zero for this net channel stuff, at
least as it is implemented and designed by Kelly.  Ring buffer is
setup ahead of time into the user's address space, and a ring of
buffers into that area are given to the networking card.

We remember the translations here, so no get_user_pages() on each
transfer and garbage like that.  And yes this all harks back to the
issues that are discussed in Chapter 5 of Networking Algorithmics.
But the core thing to understand is that by defining a new API and
setting up the buffer pool ahead of time, we avoid all of the
get_user_pages() overhead while retaining full kernel/user protection.

Evgeniy, the difference between this and your work is that you did not
have an intelligent piece of hardware that could be told to recognize
flows, and only put packets for a specific flow into that's flow's
buffer pool.

> If we want to dma data from nic into premapped userspace area, this will
> strike with message sizes/misalignment/slow read and so on, so
> preallocation has even more problems.

I do not really think this is an issue, we put the full packet into
user space and teach it where the offset is to the actual data.
We'll do the same things we do today to try and get the data area
aligned.  User can do whatever is logical and relevant on his end
to deal with strange cases.

In fact we can specify that card has to take some care to get data
area of packet aligned on say an 8 byte boundary or something like
that.  When we don't have hardware assist, we are going to be doing
copies.

> This change also requires significant changes in application, at least
> until recv/send are changed, which is not the best thing to do.

This is exactly the point, we can only do a good job and receive zero
copy if we can change the interfaces, and that's exactly what we're
doing here.

> I do think that significant win in VJ's tests belongs not to remapping
> and cache-oriented changes, but to move all protocol processing into
> process' context.

I partly disagree.  The biggest win is eliminating all of the control
overhead (all of "softint RX + protocol demux + IP route lookup +
socket lookup" is turned into single flow demux), and the SMP safe
data structure which makes it realistic enough to always move the bulk
of the packet work to the socket's home cpu.

I do not think userspace protocol implementation buys enough to
justify it.  We have to do the protection switch in and out of kernel
space anyways, so why not still do the protected protocol processing
work in the kernel?  It is still being done on the user's behalf,
contributes to his time slice, and avoids all of the terrible issues
of userspace protocol implementations.

So in my mind, the optimal situation from both a protection preservation
and also a performance perspective is net channels to kernel socket
protocol processing, buffers DMA'd directly into userspace if hardware
assist is present.

> I fully agree with Dave that it must be implemented step-by-step, and
> the most significant, IMHO, is moving protocol processing into socket's
> "place". This will force to netfilter changes, but I do think that for
> the proof-of-concept code we can turn it off.

And I also want to note that even if the whole idea explodes and
cannot be made to work, there are good arguments for transitioning
to SKB'less drivers for their own sake.  So work will really not
be lost.

Let's have 100 different implementations of net channels! :-)
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: IP1000 gigabit nic driver

2006-04-27 Thread Francois Romieu
David G??mez <[EMAIL PROTECTED]> :
[...]
> Does anybody in this list know why the IP1000 driver is not
> included in the kernel ?

Afaik the driver has never been submitted for inclusion.
At least not on netdev@vger.kernel.org (hint, hint).

[...]
> The card in question is:
> 
> Sundance Technology Inc IC Plus IP1000
> 
> and the driver can be found in sundance web, sources 

URL please ?

> included. I tried to contact the author but my email
> bounced.
> 
> There's no LICENSE in the source, just copyrigth
> sentences in the .c files, so i'm not sure under
> which license it's distributed :-?.

/me goes to http://www.icplus.com.tw/driver-pp-IP1000A.html

$ unzip -c IP1000A-Linux-driver-v2.09f.zip | grep MODULE_LICENSE
MODULE_LICENSE("GPL");

It's a bit bloaty but it does not seem too bad (not mergeable "as
is" though). Do you volunteer to test random cra^W^W carefully
engineered code on your computer to help the rework/merging process ?

-- 
Ueimor
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] selective ethtool diagnostic test method

2006-04-27 Thread Cureington, Tony
Ethtool Maintainers,
WRT my RFC (http://www.spinics.net/lists/netdev/msg02806.html) regarding
enhancing
ethtool posted on 04/11/06, would such a patch be accepted by the
maintainers of
ethtool? I don't want to spend time on these changes just to have them
rejected.
I've not received any objections for such changes thus far. It may be
several
months before we can get to implementing the changes. Please, can I get
a thumbs
up or down from the ethtool maintainers on netdev?
Thanks,
Tc
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: tune back idle cwnd closing?

2006-04-27 Thread John Heffner

David S. Miller wrote:

From: John Heffner <[EMAIL PROTECTED]>
Given that RFC2681 is Experimental (and I'm not aware of any current 
efforts in the IETF to push it to the standard track), IHMO it would not 
be inappropriate to make this behavior controlled via sysctl.


I have to respectfully disagree.

This is the price you pay when the network's congestion is being
measured by probing, information becomes stale over time if you don't
send any probes.

And this change of congestion state is real and happens frequently for
most end to end users.

When you're bursty application is not sending, other flows can take up
the pipe space you are not using, and you must reprobe to figure that
out.



A lot of the time doing 2861 is a good thing, since if you have a long 
pause, you've lost your ack clock, and you don't want to send a 
window-sized burst because you'll probably overflow a queue somewhere 
and step on your own feet.  Since we don't have a pacing mechanism, a 
slow start is really the only way to do this.


I don't entirely buy the "staleness" argument.  I don't think that *not* 
doing 2861 will affect the stability of congestion control, since all of 
the response mechanisms are still in place.  (Most OS's don't do 2861, 
and it is not a standard.)  If you have a long RTT, short RTT flows can 
make a big difference in congestion in a period much smaller than your 
timeout.  In fact, congestion information is *always* stale by the time 
you get it. :)


Sometimes having cwnd validation turned on will make your applications 
perform better, sometimes worse.  I don't think it would be incorrect to 
add a switch.  One question is whether it's worth adding the switch 
(i.e., do enough people care?).


Myself, I'd be interested to see some quantitative comparisons of 
performance with a "real" application affected by this.


Thanks,
  -John
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: 2.6.16.11 BUG at tg3.c:2917

2006-04-27 Thread Michael Chan
On Thu, 2006-04-27 at 12:52 -0400, Ed L. Cashin wrote:
> -- [please bite here ] -
> Kernel BUG at drivers/net/tg3.c:2917
> invalid opcode:  [1] SMP 
> CPU 0 

Most likely caused by IO re-ordering. Try the test patch in this
discussion:

http://marc.theaimsgroup.com/?l=linux-netdev&m=113890239404768&w=2

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


2.6.16.11 BUG at tg3.c:2917

2006-04-27 Thread Ed L. Cashin
Hi.  On 2.6.15.7 and 2.6.16.11, I have seen panics under heavy NFS
write load on an x86_64 system with two onboard Broadcom gigabit NICs.
It's a Supermicro P8SCi motherboard with an EMT64 Intel CPU.  The aoe
driver in use is the aoe6-26 driver from the Coraid website.

I haven't yet trimmed down the test case or tried using the aoe driver
that comes with 2.6.16.11.  Right now there's kernel NFS exporting an
XFS filesystem on a logical volume backed by 3 AoE devices.

I'm including two panics here.

There's a relevant-looking discussion of the same bug from May 2005 at
the URL below.

  http://oss.sgi.com/projects/netdev/archive/2004-05/msg00378.html


--- [cut here ] - [please bite here ] -
Kernel BUG at drivers/net/tg3.c:2917
invalid opcode:  [1] SMP 
CPU 0 
Modules linked in: nfsd lockd nfs_acl sunrpc xfs exportfs dm_mod aoe ipv6 rtc 
piix i2c_i801 psmouse evdev i2c_core unix
Pid: 3053, comm: nfsd Not tainted 2.6.16.11-c1 #1
RIP: 0010:[] {tg3_poll+179}
RSP: :8039cc38  EFLAGS: 00010246
RAX: 01fb RBX:  RCX: 0003
RDX: 0038 RSI: 81003f03f180 RDI: 810001fbb980
RBP: 81003d82df88 R08: 0400 R09: 81003e5fae18
R10: 81003ee86a80 R11: 00c4 R12: 81003f0d0500
R13: 01fb R14: 0016 R15: 810023088c30
FS:  2b4cde2ee6d0() GS:803e6000() knlGS:
CS:  0010 DS:  ES:  CR0: 8005003b
CR2: 00438010 CR3: 25729000 CR4: 06e0
Process nfsd (pid: 3053, threadinfo 81003d6fc000, task 81003f304140)
Stack: 0046 802427b4 8039ccd4 81003f0d 
   81003dfec000 0014002c 00ca 00ca81ca 
   81003dfdd920 81003f0d059c 
Call Trace:  {task_in_intr+240}
   {net_rx_action+165} {__do_softirq+86}
   {call_softirq+30}  
{do_softirq+44}
   {local_bh_enable+105} 
{dev_queue_xmit+551}
   {:aoe:aoenet_xmit+26} 
{:aoe:aoeblk_make_request+413}
   {generic_make_request+335} 
{:dm_mod:__map_bio+66}
   {:dm_mod:__split_bio+365} 
{:xfs:linvfs_get_block+0}
   {:dm_mod:dm_request+262} 
{generic_make_request+335}
   {submit_bio+184} 
{:xfs:xfs_buf_iorequest+828}
   {default_wake_function+0} 
{:xfs:xfs_buf_associate_memory+117}
   {:xfs:xlog_bdstrat_cb+22} 
{:xfs:xlog_state_release_iclog+695}
   {:xfs:xlog_write+1509} 
{:xfs:xfs_log_write+42}
   {:xfs:_xfs_trans_commit+1294} 
{:xfs:kmem_zone_alloc+73}
   {:xfs:kmem_zone_zalloc+28} 
{:xfs:xfs_itruncate_finish+530}
   {:xfs:xfs_inactive_free_eofblocks+384}
   {:xfs:linvfs_release+0} 
{:xfs:xfs_release+152}
   {:xfs:linvfs_release+23} {__fput+155}
   {:nfsd:nfsd_write+196} 
{:nfsd:nfsd3_proc_write+231}
   {:nfsd:nfsd_dispatch+221} 
{:sunrpc:svc_process+975}
   {__down_read+18} {:nfsd:nfsd+451}
   {child_rip+8} {:nfsd:nfsd+0}
   {child_rip+0}

Code: 0f 0b 68 83 5f 2f 80 c2 65 0b 49 8b 44 24 40 8b 93 88 00 00 
RIP {tg3_poll+179} RSP 
 <0>Kernel panic - not syncing: Aiee, killing interrupt handler!
 

--- [cut here ] - [please bite here ] -
Kernel BUG at drivers/net/tg3.c:2914
invalid operand:  [1] SMP
CPU 0
Modules linked in: nfsd lockd nfs_acl sunrpc dm_mod aoe xfs exportfs ipv6 
i2c_i801 i2c_core piix md_mod rtc psmouse unix
Pid: 88, comm: kswapd0 Not tainted 2.6.15.7-c1 #1
RIP: 0010:[] {tg3_poll+179}
RSP: :80395e08  EFLAGS: 00010246
RAX: 0066 RBX:  RCX: 0002
RDX: 0028 RSI: 81003e999d80 RDI: 810001fbba40
RBP: 81003dd63990 R08: 80395ea8 R09: 81003dc2ce18
R10: 003a R11: 80395ea8 R12: 81003f1a3500
R13: 0066 R14: 00a9 R15: 80395f08
FS:  () GS:803e1800() knlGS:
CS:  0010 DS: 0018 ES: 0018 CR0: 8005003b
CR2: 004a12a7 CR3: 077ab000 CR4: 06e0
Process kswapd0 (pid: 88, threadinfo 81003f5d8000, task 81003f594790)
Stack: 803c8980 1d4c 80395ea4 81003f1a3000
   81003db45000 0040 0049 0049003b
   81003e52c740 81003f1a359c
Call Trace:  {net_rx_action+165} 
{__do_softirq+86}
   {call_softirq+31} {do_softirq+44}
   {do_IRQ+52} {ret_from_intr+0}
 {cache_flusharray+30} 
{:xfs:linvfs_release_page+0}
   {_write_unlock_irqrestore+9} 
{test_clear_page_dirty+152}
   {try_to_free_buffers+116} 
{:xfs:linvfs_release_page+0}
   {:xfs:linvfs_release_page+133} 
{shrink_zone+2695}
   {activate_task+140} 
{try_to_wake_up+1110}
   {balance_pgdat+535} {kswapd+256}
   {autoremove_wake_function+0} 
{child_rip+8}
   {kswapd+0} {child_rip+0}


Code: 0f 0b 68 ba 2d 2f 80 c2 62 0b 49 8b 44 24 40 8b 93 80 00 00
RIP {tg3_poll+179} RSP 
 <0>Kernel panic - not syncing: A

[RFC PATCH] [IPV6]: Fix race in route selection.

2006-04-27 Thread YOSHIFUJI Hideaki / 吉藤英明
Hello.

We eliminated rt6_dflt_lock (to protect default router pointer)
at 2.6.17-rc1, and introduced rt6_select() for general router selection.
The function is called in the context of rt6_lock read-lock held,
but this means, we have some race conditions when we do round-robin.

Am I correct?

If so, we should put some spin_lock for serialization.

Comments?

Signed-off-by; YOSHIFUJI Hideaki <[EMAIL PROTECTED]>

Or, should we run whole part of rt6_select() under some lock?

diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 7907874..0190e39 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -317,7 +317,7 @@ static struct rt6_info *rt6_select(struc
  __FUNCTION__, head, head ? *head : NULL, oif);
 
for (rt = rt0, metric = rt0->rt6i_metric;
-rt && rt->rt6i_metric == metric;
+rt && rt->rt6i_metric == metric && (!last || rt != rt0);
 rt = rt->u.next) {
int m;
 
@@ -343,9 +343,12 @@ static struct rt6_info *rt6_select(struc
(strict & RT6_SELECT_F_REACHABLE) &&
last && last != rt0) {
/* no entries matched; do round-robin */
+   static spinlock_t lock = SPIN_LOCK_UNLOCKED;
+   spin_lock(&lock);
*head = rt0->u.next;
rt0->u.next = last->u.next;
last->u.next = rt0;
+   spin_unlock(&lock);
}
 
RT6_TRACE("%s() => %p, score=%d\n",

-- 
YOSHIFUJI Hideaki @ USAGI Project  <[EMAIL PROTECTED]>
GPG-FP  : 9022 65EB 1ECF 3AD1 0BDF  80D8 4807 F894 E062 0EEA
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] e1000 performance patch

2006-04-27 Thread Rick Jones




but clearly I should be using netperf to get more accurate cpu numbers
and a more convincing aggregate table :-)


Well, I'll not stop you  :)




It is a bit rough/messy as a writeup, but here is what I've seen wrt the 
latency vs throughput tradeoffs:

ftp://ftp.cup.hp.com/dist/networking/briefs/nic_latency_vs_tput.txt



from a quick read it looks like just the case with 32kB messages,
multiple simultaneous clients, and driver set to unlimited ITR sees
reduced throughput. is that right?

if so, then I'm not surprised.


There should be three basic measures there - one is the single-instance 
request-response test. The idea is to see minimum latency.  That test 
likes to see the interrupt throttle rate made very high, or disabled 
completely.


The aggregate TCP_RR's and the TCP_STREAM tests are there to show what 
effect that has on the ability to do aggregate request/response and a 
bulk transfer.



but overall I'm actually more worried about a mix of small and large
messages than multiple clients.





a large/small mix might well occur in 'the real world' and it'll be 2s
until the watchdog routine can adapt the ITR. potentially that 2s will
be at 200k ITR which is too high for large messages, and up to 2s of
cpu will be burnt needlessly.

can netperf (or some other tool) mix up big and small message sizes
like 'the real world' perhaps does?
that might help me find a good frequency at which to try to adapt the
ITR... (eg. 1, 10, 100 or 1000 times a second)


There is the "vst" (variable size test IIRC) in netperf4:

http://www.netperf.org/svn/netperf4/branches/glib_migration

The docs for netperf4 are presently pathetic.  Feel free to email me for 
bootstrapping information.  Basically, you'll need pkg-config, libxml2 
and glib-2.0 on the system.




cheers,
robin


-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 7/9] e100: disable interrupts at boot

2006-04-27 Thread Bjorn Helgaas
On Thursday 27 April 2006 04:00, Jeff Garzik wrote:
> [EMAIL PROTECTED] wrote:
> > From: Bjorn Helgaas <[EMAIL PROTECTED]>
> > 
> > Apparently the Intel PRO/100 device enables interrupts on reset.  Unless
> > firmware explicitly disables PRO/100 interrupts, we can get a flood of
> > interrupts when a driver attaches to an unrelated device that happens to
> > share the PRO/100 IRQ.
> > 
> > This should resolve this "irq 11: nobody cared" bug report:
> > http://bugzilla.kernel.org/show_bug.cgi?id=5918
> > 
> > Signed-off-by: Bjorn Helgaas <[EMAIL PROTECTED]>
> > Cc: Jesse Brandeburg <[EMAIL PROTECTED]>
> > Cc: Jeff Kirsher <[EMAIL PROTECTED]>
> > Cc: John Ronciak <[EMAIL PROTECTED]>
> > Cc: <[EMAIL PROTECTED]>
> > Cc: <[EMAIL PROTECTED]>
> > Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
> 
> I'm really worried that we are burdening the kernel for a very very rare 
> condition.  Do we want to apply this for one stupid firmware?
> 
> Can't early userspace just run setpci to fix this one?

I don't think so, because the problem occurs as soon as any driver
enables IRQ 11.  I agree that it's rare, but it's a real pain to
debug it and identify it when it occurs.
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: Netpoll checksum issue

2006-04-27 Thread Aubrey
Hi Herbert,

Is there any update of this issue?

Regards,
- Aubrey

On 4/24/06, Aubrey <[EMAIL PROTECTED]> wrote:
> On 4/24/06, Herbert Xu <[EMAIL PROTECTED]> wrote:
> > On Mon, Apr 24, 2006 at 01:42:12PM +0800, Aubrey wrote:
> > >
> > >   dev->last_rx = jiffies;
> > >   skb->dev = dev;
> > >   skb->protocol = eth_type_trans(skb, dev);
> > >   skb->ip_summed = CHECKSUM_UNNECESSARY;
> > >   netif_rx(skb);
> >
> > This doesn't make sense.  First of all you're setting ip_summed to
> > CHECK_UNNECESSARY unconditionally which is most likely wrong.
> >
> > What's more, if this was the driver that you were using, then
> > checksum_udp couldn't possibly fail since the first thing it does
> > is check ip_summed.
>
> Hmm, when I change the code in __netpoll_rx, there is no the following
> one line in the driver:
> ==
> skb->ip_summed = CHECKSUM_UNNECESSARY;
> ==
>
> The above one line code in the driver is just a workaround.
>
> Regards,
> -Aubrey
>
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 0/17] d80211 patches

2006-04-27 Thread Michael Buesch
On Wednesday 26 April 2006 21:39, John W. Linville wrote:
> On Fri, Apr 21, 2006 at 10:52:10PM +0200, Jiri Benc wrote:
> > On Fri, 21 Apr 2006 22:52:08 +0200, Michael Buesch wrote:
> > > Can you please send your hacky patch for the bcm43xx
> > > to me, so I can come up with a clean one?
> > 
> > Sure, actually I planned to do it in a few minutes :-)
> 
> Hacky or not, I'm applying this patch to keep the bcm43xx driver
> from breaking.
That's perfectly fine.
The correct patch needs a little bit of rewriting in the "mode" code.
I will do that after I finished the 4318 fixes (should take quite
some time).

-- 
Greetings Michael.


pgp30SC3FNYzE.pgp
Description: PGP signature


[PATCH] DECnet: Fix level1 router hello

2006-04-27 Thread Patrick Caulfield
This patch fixes hello messages sent when a node is a level 1 router. Slightly
contrary to the spec (maybe) VMS ignores hello messages that do not name
level2 routers that it also knows about.

So, here we simply name all the routers that the node knows about rather just
other level1 routers.
(I hope the patch is clearer than the description. sorry).

Patrick

Signed-off-by: Patrick Caulfield <[EMAIL PROTECTED]>

diff --git a/net/decnet/dn_neigh.c b/net/decnet/dn_neigh.c
index 7c8692c..66e230c 100644
--- a/net/decnet/dn_neigh.c
+++ b/net/decnet/dn_neigh.c
@@ -493,7 +493,6 @@ struct elist_cb_state {
 static void neigh_elist_cb(struct neighbour *neigh, void *_info)
 {
struct elist_cb_state *s = _info;
-   struct dn_dev *dn_db;
struct dn_neigh *dn;

if (neigh->dev != s->dev)
@@ -503,10 +502,6 @@ static void neigh_elist_cb(struct neighb
if (!(dn->flags & (DN_NDFLAG_R1|DN_NDFLAG_R2)))
return;

-   dn_db = (struct dn_dev *) s->dev->dn_ptr;
-   if (dn_db->parms.forwarding == 1 && (dn->flags & DN_NDFLAG_R2))
-   return;
-
if (s->t == s->n)
s->rs = dn_find_slot(s->ptr, s->n, dn->priority);
else

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[IPSEC]: Fix IP ID selection

2006-04-27 Thread Herbert Xu
Hi Dave:

I was looking through the xfrm input/output code in order to abstract
out the address family specific encapsulation/decapsulation code.  During
that process I found this bug in the IP ID selection code in xfrm4_output.c.

At that point dst is still the xfrm_dst for the current SA which
represents an internal flow as far as the IPsec tunnel is concerned.
Since the IP ID is going to sit on the outside of the encapsulated
packet, we obviously want the external flow which is just dst->child.

The fix is trivial.

Signed-off-by: Herbert Xu <[EMAIL PROTECTED]>

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <[EMAIL PROTECTED]>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt
diff --git a/net/ipv4/xfrm4_output.c b/net/ipv4/xfrm4_output.c
index 32ad229..4ef8efa 100644
--- a/net/ipv4/xfrm4_output.c
+++ b/net/ipv4/xfrm4_output.c
@@ -62,7 +62,7 @@
top_iph->frag_off = (flags & XFRM_STATE_NOPMTUDISC) ?
0 : (iph->frag_off & htons(IP_DF));
if (!top_iph->frag_off)
-   __ip_select_ident(top_iph, dst, 0);
+   __ip_select_ident(top_iph, dst->child, 0);
 
top_iph->ttl = dst_metric(dst->child, RTAX_HOPLIMIT);
 


Re: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread Evgeniy Polyakov
On Wed, Apr 26, 2006 at 11:25:01PM -0700, David S. Miller ([EMAIL PROTECTED]) 
wrote:
> > We approached this from the understanding that an intelligent NIC
> > will be able to transition directly to userspace, which is a major
> > win.  0 copies to userspace would be sweet.  I think we can still
> > achieve this using your scheme without *too* much pain.
> 
> Understood.  What's your basic idea?  Just make the buffers in the
> pool large enough to fit the SKB encapsulation at the end?

There are some caveats here found while developing zero-copy sniffer
[1]. Project's goal was to remap skbs into userspace in real-time.
While absolute numbers (posted to netdev@) were really high, it is only
applicable to read-only application. As was shown in IOAT thread,
data must be warmed in caches, so reading from mapped area will be as
fast as memcpy() (read+write), and copy_to_user() actually almost equal
to memcpy() (benchmarks were posted to netdev@). And we must add
remapping overhead.

If we want to dma data from nic into premapped userspace area, this will
strike with message sizes/misalignment/slow read and so on, so
preallocation has even more problems.

This change also requires significant changes in application, at least
until recv/send are changed, which is not the best thing to do.

So I think that mapping itself can be done as some additional socket
option or something not turnedon by default.


I do think that significant win in VJ's tests belongs not to remapping
and cache-oriented changes, but to move all protocol processing into
process' context.

I fully agree with Dave that it must be implemented step-by-step, and
the most significant, IMHO, is moving protocol processing into socket's
"place". This will force to netfilter changes, but I do think that for
the proof-of-concept code we can turn it off.

I will start to work in this direction next week after aio_sendfile() is
completed.

So, we will have three attempts to write incompatible stacks - and that is good 
:)
No one need an excuse to rewrite something, as I read in Rusty's blog...

Thanks.

[1]. http://tservice.net.ru/~s0mbre/old/?section=projects&item=af_tlb

-- 
Evgeniy Polyakov
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 2/9] tulip: NatSemi DP83840A PHY fix

2006-04-27 Thread Thibaut VARENE
On 4/27/06, Jeff Garzik <[EMAIL PROTECTED]> wrote:
> [EMAIL PROTECTED] wrote:
> > + if (startup) {
> > + int timeout = 10;   /* max 1 ms */
> >   for (i = 0; i < reset_length; i++)
> >   
> > iowrite32(get_u16(&reset_sequence[i]) << 16, ioaddr + CSR15);
> > +
> > + /* flush posted writes */
> > + ioread32(ioaddr + CSR15);
> > +
> > + /* Sect 3.10.3 in DP83840A.pdf (p39) 
> > */
> > + udelay(500);
> > +
> > + /* Section 4.2 in DP83840A.pdf (p43) 
> > */
> > + /* and IEEE 802.3 "22.2.4.1.1 Reset" 
> > */
> > + while (timeout-- &&
> > + (tulip_mdio_read (dev, 
> > phy_num, MII_BMCR) & BMCR_RESET))
> > + udelay(100);
>
>
> What can we do about this?
>
> Its a huge delay to be taken inside a spinlock.

This is device setup code. ISTR Grant showing other similar examples
of delays in such code in the kernel. Unless you keep
configuring/deconfiguring the device, and assuming you hit worst case
scenario everytime, it won't be a problem. But if you're doing that,
you already have a problem elsewhere. Or am I missing something?

> Anybody interested to converting the driver to use schedule_work() or
> similar?

That question has been raised months ago without any significant
outcome. Maybe it's time to move on? This code does respect hardware
specs, at least, which isn't the case of existing code, and fixes a
bug...

HTH

T-Bone

--
Thibaut VARENE
http://www.parisc-linux.org/~varenet/
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 7/9] e100: disable interrupts at boot

2006-04-27 Thread Jeff Garzik

[EMAIL PROTECTED] wrote:

From: Bjorn Helgaas <[EMAIL PROTECTED]>

Apparently the Intel PRO/100 device enables interrupts on reset.  Unless
firmware explicitly disables PRO/100 interrupts, we can get a flood of
interrupts when a driver attaches to an unrelated device that happens to
share the PRO/100 IRQ.

This should resolve this "irq 11: nobody cared" bug report:
http://bugzilla.kernel.org/show_bug.cgi?id=5918

Signed-off-by: Bjorn Helgaas <[EMAIL PROTECTED]>
Cc: Jesse Brandeburg <[EMAIL PROTECTED]>
Cc: Jeff Kirsher <[EMAIL PROTECTED]>
Cc: John Ronciak <[EMAIL PROTECTED]>
Cc: <[EMAIL PROTECTED]>
Cc: <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>


I'm really worried that we are burdening the kernel for a very very rare 
condition.  Do we want to apply this for one stupid firmware?


Can't early userspace just run setpci to fix this one?

Jeff



-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 8/9] forcedeth: suggested cleanups

2006-04-27 Thread Jeff Garzik

[EMAIL PROTECTED] wrote:

From: Ingo Oeser <[EMAIL PROTECTED]>

general:
- endian annotation of the ring descriptors

nv_getlen():
- use htons() instead of __constant_htons()
  to improvde readability and let the compiler constant fold it.

nv_rx_process():
- use a real for() loop in processing instead of goto and break
- consolidate rx_errors increment
- count detected rx_length_errors

Signed-off-by: Ingo Oeser <[EMAIL PROTECTED]>
Cc: Manfred Spraul <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>


ACK, but I'm holding off applying this while trying to get 4 apply-able 
patches out of NVIDIA and Manfred :)


Jeff



-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 3/9] natsemi: Add support for using MII port with no PHY

2006-04-27 Thread Jeff Garzik

[EMAIL PROTECTED] wrote:

From: Mark Brown <[EMAIL PROTECTED]>

Provide a module option which configures the natsemi driver to use the
external MII port on the chip but ignore any PHYs that may be attached to it. 
The link state will be left as it was when the driver started and can be

configured via ethtool.  Any PHYs that are present can be accessed via the MII
ioctl()s.

This is useful for systems where the device is connected without a PHY or
where either information or actions outside the scope of the driver are
required in order to use the PHYs.

Signed-off-by: Mark Brown <[EMAIL PROTECTED]>
Cc: Tim Hockin <[EMAIL PROTECTED]>
Cc: Jeff Garzik <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>


NAK.

The proper way to do this is via the force_media boolean flag found in 
several net drivers.


In general I agree with the motivation to do something like this...

Jeff



-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [patch 2/9] tulip: NatSemi DP83840A PHY fix

2006-04-27 Thread Jeff Garzik

[EMAIL PROTECTED] wrote:

+   if (startup) {
+   int timeout = 10;   /* max 1 ms */
for (i = 0; i < reset_length; i++)
iowrite32(get_u16(&reset_sequence[i]) 
<< 16, ioaddr + CSR15);
+
+   /* flush posted writes */
+   ioread32(ioaddr + CSR15);
+
+   /* Sect 3.10.3 in DP83840A.pdf (p39) */
+   udelay(500);
+
+   /* Section 4.2 in DP83840A.pdf (p43) */
+   /* and IEEE 802.3 "22.2.4.1.1 Reset" */
+   while (timeout-- &&
+   (tulip_mdio_read (dev, phy_num, 
MII_BMCR) & BMCR_RESET))
+   udelay(100);



What can we do about this?

Its a huge delay to be taken inside a spinlock.

Anybody interested to converting the driver to use schedule_work() or 
similar?


Jeff


-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 3/9] natsemi: Add support for using MII port with no PHY

2006-04-27 Thread akpm

From: Mark Brown <[EMAIL PROTECTED]>

Provide a module option which configures the natsemi driver to use the
external MII port on the chip but ignore any PHYs that may be attached to it. 
The link state will be left as it was when the driver started and can be
configured via ethtool.  Any PHYs that are present can be accessed via the MII
ioctl()s.

This is useful for systems where the device is connected without a PHY or
where either information or actions outside the scope of the driver are
required in order to use the PHYs.

Signed-off-by: Mark Brown <[EMAIL PROTECTED]>
Cc: Tim Hockin <[EMAIL PROTECTED]>
Cc: Jeff Garzik <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/natsemi.c |  105 +---
 1 files changed, 67 insertions(+), 38 deletions(-)

diff -puN 
drivers/net/natsemi.c~natsemi-add-support-for-using-mii-port-with-no-phy 
drivers/net/natsemi.c
--- 
devel/drivers/net/natsemi.c~natsemi-add-support-for-using-mii-port-with-no-phy  
2006-04-10 23:21:19.0 -0700
+++ devel-akpm/drivers/net/natsemi.c2006-04-10 23:21:19.0 -0700
@@ -259,7 +259,7 @@ MODULE_PARM_DESC(debug, "DP8381x default
 MODULE_PARM_DESC(rx_copybreak, 
"DP8381x copy breakpoint for copy-only-tiny-frames");
 MODULE_PARM_DESC(options, 
-   "DP8381x: Bits 0-3: media type, bit 17: full duplex");
+   "DP8381x: Bits 0-3: media type, bit 17: full duplex, bit 18: ignore 
PHY");
 MODULE_PARM_DESC(full_duplex, "DP8381x full duplex setting(s) (1)");
 
 /*
@@ -690,6 +690,8 @@ struct netdev_private {
u32 intr_status;
/* Do not touch the nic registers */
int hands_off;
+   /* Don't pay attention to the reported link state. */
+   int ignore_phy;
/* external phy that is used: only valid if dev->if_port != PORT_TP */
int mii;
int phy_addr_external;
@@ -894,7 +896,19 @@ static int __devinit natsemi_probe1 (str
np->intr_status = 0;
np->eeprom_size = NATSEMI_DEF_EEPROM_SIZE;
 
+   option = find_cnt < MAX_UNITS ? options[find_cnt] : 0;
+   if (dev->mem_start)
+   option = dev->mem_start;
+
+   /* Ignore the PHY status? */
+   if (option & 0x400) {
+   np->ignore_phy = 1;
+   } else {
+   np->ignore_phy = 0;
+   }
+
/* Initial port:
+* - If configured to ignore the PHY set up for external.
 * - If the nic was configured to use an external phy and if find_mii
 *   finds a phy: use external port, first phy that replies.
 * - Otherwise: internal port.
@@ -902,7 +916,7 @@ static int __devinit natsemi_probe1 (str
 * The address would be used to access a phy over the mii bus, but
 * the internal phy is accessed through mapped registers.
 */
-   if (readl(ioaddr + ChipConfig) & CfgExtPhy)
+   if (np->ignore_phy || readl(ioaddr + ChipConfig) & CfgExtPhy)
dev->if_port = PORT_MII;
else
dev->if_port = PORT_TP;
@@ -912,7 +926,9 @@ static int __devinit natsemi_probe1 (str
 
if (dev->if_port != PORT_TP) {
np->phy_addr_external = find_mii(dev);
-   if (np->phy_addr_external == PHY_ADDR_NONE) {
+   /* If we're ignoring the PHY it doesn't matter if we can't
+* find one. */
+   if (!np->ignore_phy && np->phy_addr_external == PHY_ADDR_NONE) {
dev->if_port = PORT_TP;
np->phy_addr_external = PHY_ADDR_INTERNAL;
}
@@ -920,10 +936,6 @@ static int __devinit natsemi_probe1 (str
np->phy_addr_external = PHY_ADDR_INTERNAL;
}
 
-   option = find_cnt < MAX_UNITS ? options[find_cnt] : 0;
-   if (dev->mem_start)
-   option = dev->mem_start;
-
/* The lower four bits are the media type. */
if (option) {
if (option & 0x200)
@@ -957,7 +969,10 @@ static int __devinit natsemi_probe1 (str
if (mtu)
dev->mtu = mtu;
 
-   netif_carrier_off(dev);
+   if (np->ignore_phy)
+   netif_carrier_on(dev);
+   else
+   netif_carrier_off(dev);
 
/* get the initial settings from hardware */
tmp= mdio_read(dev, MII_BMCR);
@@ -1005,6 +1020,8 @@ static int __devinit natsemi_probe1 (str
printk("%02x, IRQ %d", dev->dev_addr[i], irq);
if (dev->if_port == PORT_TP)
printk(", port TP.\n");
+   else if (np->ignore_phy)
+   printk(", port MII, ignoring PHY\n");
else
printk(", port MII, phy ad %d.\n", 
np->phy_addr_external);
}
@@ -1685,42 +1702,44 @@ static void check_link(struct net_device
 {
struct netdev_private *np = netdev_priv(dev);
void __iomem * ioaddr = ns_ioaddr(dev);
-   int duplex;
+   int duplex = np->full_dupl

[patch 8/9] forcedeth: suggested cleanups

2006-04-27 Thread akpm

From: Ingo Oeser <[EMAIL PROTECTED]>

general:
- endian annotation of the ring descriptors

nv_getlen():
- use htons() instead of __constant_htons()
  to improvde readability and let the compiler constant fold it.

nv_rx_process():
- use a real for() loop in processing instead of goto and break
- consolidate rx_errors increment
- count detected rx_length_errors

Signed-off-by: Ingo Oeser <[EMAIL PROTECTED]>
Cc: Manfred Spraul <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/forcedeth.c |   59 --
 1 files changed, 26 insertions(+), 33 deletions(-)

diff -puN drivers/net/forcedeth.c~forcedeth-suggested-cleanups 
drivers/net/forcedeth.c
--- devel/drivers/net/forcedeth.c~forcedeth-suggested-cleanups  2006-04-10 
23:21:26.0 -0700
+++ devel-akpm/drivers/net/forcedeth.c  2006-04-10 23:21:26.0 -0700
@@ -328,17 +328,18 @@ enum {
NvRegMSIXIrqStatus = 0x3f0,
 };
 
-/* Big endian: should work, but is untested */
+/* Big endian: should work, but is untested.
+ * So give arch maintainers a hint here. -ioe */
 struct ring_desc {
-   u32 PacketBuffer;
-   u32 FlagLen;
+   __le32 PacketBuffer;
+   __le32 FlagLen;
 };
 
 struct ring_desc_ex {
-   u32 PacketBufferHigh;
-   u32 PacketBufferLow;
-   u32 TxVlan;
-   u32 FlagLen;
+   __le32 PacketBufferHigh;
+   __le32 PacketBufferLow;
+   __le32 TxVlan;
+   __le32 FlagLen;
 };
 
 typedef union _ring_type {
@@ -1403,7 +1404,7 @@ static int nv_getlen(struct net_device *
int protolen;   /* length as stored in the proto field */
 
/* 1) calculate len according to header */
-   if ( ((struct vlan_ethhdr *)packet)->h_vlan_proto == 
__constant_htons(ETH_P_8021Q)) {
+   if (((struct vlan_ethhdr *)packet)->h_vlan_proto == htons(ETH_P_8021Q)) 
{
protolen = ntohs( ((struct vlan_ethhdr 
*)packet)->h_vlan_encapsulated_proto );
hdrlen = VLAN_HLEN;
} else {
@@ -1453,12 +1454,10 @@ static void nv_rx_process(struct net_dev
u32 vlanflags = 0;
 
 
-   for (;;) {
+   for (; np->cur_rx - np->refill_rx < RX_RING; np->cur_rx++) {
struct sk_buff *skb;
int len;
int i;
-   if (np->cur_rx - np->refill_rx >= RX_RING)
-   break;  /* we scanned the whole ring - do not continue 
*/
 
i = np->cur_rx % RX_RING;
if (np->desc_ver == DESC_VER_1 || np->desc_ver == DESC_VER_2) {
@@ -1498,33 +1497,29 @@ static void nv_rx_process(struct net_dev
/* look at what we actually got: */
if (np->desc_ver == DESC_VER_1) {
if (!(Flags & NV_RX_DESCRIPTORVALID))
-   goto next_pkt;
+   continue;
 
if (Flags & NV_RX_ERROR) {
if (Flags & NV_RX_MISSEDFRAME) {
np->stats.rx_missed_errors++;
-   np->stats.rx_errors++;
-   goto next_pkt;
+   goto error_pkt;
}
if (Flags & 
(NV_RX_ERROR1|NV_RX_ERROR2|NV_RX_ERROR3)) {
-   np->stats.rx_errors++;
-   goto next_pkt;
+   goto error_pkt;
}
if (Flags & NV_RX_CRCERR) {
np->stats.rx_crc_errors++;
-   np->stats.rx_errors++;
-   goto next_pkt;
+   goto error_pkt;
}
if (Flags & NV_RX_OVERFLOW) {
np->stats.rx_over_errors++;
-   np->stats.rx_errors++;
-   goto next_pkt;
+   goto error_pkt;
}
if (Flags & NV_RX_ERROR4) {
len = nv_getlen(dev, 
np->rx_skbuff[i]->data, len);
if (len < 0) {
-   np->stats.rx_errors++;
-   goto next_pkt;
+   np->stats.rx_length_errors++;
+   goto error_pkt;
}
}
/* framing errors are soft errors. */
@@ -1536,28 +1531,25 @@ static void nv_rx_process(struct net_dev
}

[patch 4/9] PCI Error Recovery: e1000 network device driver

2006-04-27 Thread akpm

From: Linas Vepstas <[EMAIL PROTECTED]>

Various PCI bus errors can be signaled by newer PCI controllers.  This
patch adds the PCI error recovery callbacks to the intel gigabit ethernet
e1000 device driver.  The patch has been tested, and appears to work well.

[EMAIL PROTECTED]: minor cleanups]
Signed-off-by: Linas Vepstas <[EMAIL PROTECTED]>
Acked-by: Jesse Brandeburg <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/e1000/e1000_main.c |  116 ++-
 1 files changed, 115 insertions(+), 1 deletion(-)

diff -puN 
drivers/net/e1000/e1000_main.c~pci-error-recovery-e1000-network-device-driver 
drivers/net/e1000/e1000_main.c
--- 
devel/drivers/net/e1000/e1000_main.c~pci-error-recovery-e1000-network-device-driver
 2006-04-22 01:39:15.0 -0700
+++ devel-akpm/drivers/net/e1000/e1000_main.c   2006-04-22 01:39:15.0 
-0700
@@ -227,6 +227,16 @@ static int e1000_resume(struct pci_dev *
 static void e1000_netpoll (struct net_device *netdev);
 #endif
 
+static pci_ers_result_t e1000_io_error_detected(struct pci_dev *pdev,
+ pci_channel_state_t state);
+static pci_ers_result_t e1000_io_slot_reset(struct pci_dev *pdev);
+static void e1000_io_resume(struct pci_dev *pdev);
+
+static struct pci_error_handlers e1000_err_handler = {
+   .error_detected = e1000_io_error_detected,
+   .slot_reset = e1000_io_slot_reset,
+   .resume = e1000_io_resume,
+};
 
 static struct pci_driver e1000_driver = {
.name = e1000_driver_name,
@@ -236,8 +246,9 @@ static struct pci_driver e1000_driver = 
/* Power Managment Hooks */
 #ifdef CONFIG_PM
.suspend  = e1000_suspend,
-   .resume   = e1000_resume
+   .resume   = e1000_resume,
 #endif
+   .err_handler = &e1000_err_handler,
 };
 
 MODULE_AUTHOR("Intel Corporation, <[EMAIL PROTECTED]>");
@@ -3076,6 +3087,10 @@ e1000_update_stats(struct e1000_adapter 
 
 #define PHY_IDLE_ERROR_COUNT_MASK 0x00FF
 
+   /* Prevent stats update while adapter is being reset */
+   if (adapter->link_speed == 0)
+   return;
+
spin_lock_irqsave(&adapter->stats_lock, flags);
 
/* these counters are modified from e1000_adjust_tbi_stats,
@@ -4625,4 +4640,103 @@ e1000_netpoll(struct net_device *netdev)
 }
 #endif
 
+/**
+ * e1000_io_error_detected - called when PCI error is detected
+ * @pdev: Pointer to PCI device
+ * @state: The current pci conneection state
+ *
+ * This function is called after a PCI bus error affecting
+ * this device has been detected.
+ */
+static pci_ers_result_t e1000_io_error_detected(struct pci_dev *pdev,
+   pci_channel_state_t state)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+   struct e1000_adapter *adapter = netdev->priv;
+
+   netif_device_detach(netdev);
+
+   if (netif_running(netdev))
+   e1000_down(adapter);
+
+   /* Request a slot slot reset. */
+   return PCI_ERS_RESULT_NEED_RESET;
+}
+
+/**
+ * e1000_io_slot_reset - called after the pci bus has been reset.
+ * @pdev: Pointer to PCI device
+ *
+ * Restart the card from scratch, as if from a cold-boot. Implementation
+ * resembles the first-half of the e1000_resume routine.
+ */
+static pci_ers_result_t e1000_io_slot_reset(struct pci_dev *pdev)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+   struct e1000_adapter *adapter = netdev->priv;
+
+   if (pci_enable_device(pdev)) {
+   printk(KERN_ERR "e1000: Cannot re-enable PCI device after "
+   "reset.\n");
+   return PCI_ERS_RESULT_DISCONNECT;
+   }
+   pci_set_master(pdev);
+
+   pci_enable_wake(pdev, 3, 0);
+   pci_enable_wake(pdev, 4, 0); /* 4 == D3 cold */
+
+   /* Perform card reset only on one instance of the card */
+   if (PCI_FUNC (pdev->devfn) != 0)
+   return PCI_ERS_RESULT_RECOVERED;
+
+   e1000_reset(adapter);
+   E1000_WRITE_REG(&adapter->hw, WUS, ~0);
+
+   return PCI_ERS_RESULT_RECOVERED;
+}
+
+/**
+ * e1000_io_resume - called when traffic can start flowing again.
+ * @pdev: Pointer to PCI device
+ *
+ * This callback is called when the error recovery driver tells us that
+ * its OK to resume normal operation. Implementation resembles the
+ * second-half of the e1000_resume routine.
+ */
+static void e1000_io_resume(struct pci_dev *pdev)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+   struct e1000_adapter *adapter = netdev->priv;
+   uint32_t manc, swsm;
+
+   if (netif_running(netdev)) {
+   if (e1000_up(adapter)) {
+   printk(KERN_ERR "e1000: can't bring device back up "
+   "after reset\n");
+   return;
+   }
+   }
+
+   netif_device_attach(netdev);
+
+   if (adapter->hw.mac_type >= e1000_82540 &&
+   adapter->hw.media_type =

[patch 2/9] tulip: NatSemi DP83840A PHY fix

2006-04-27 Thread akpm

From: Thibaut VARENE <[EMAIL PROTECTED]>

Fix a problem with Tulip 21142 HP branded PCI cards (PN#: B5509-66001),
which feature a NatSemi DP83840A PHY.

Without that patch, it is impossible to properly initialize the card's PHY,
and it's thus impossible to monitor/configure it.

It's a timing/posting problem, and it is solved exactly the same way Grant
fixed it elsewhere already.

Signed-off-by: Thibaut VARENE <[EMAIL PROTECTED]>
Cc: Jeff Garzik <[EMAIL PROTECTED]>
Acked-by: Grant Grundler <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/tulip/media.c |   18 +-
 1 files changed, 17 insertions(+), 1 deletion(-)

diff -puN drivers/net/tulip/media.c~tulip-natsemi-dp83840a-phy-fix 
drivers/net/tulip/media.c
--- devel/drivers/net/tulip/media.c~tulip-natsemi-dp83840a-phy-fix  
2006-04-10 23:21:18.0 -0700
+++ devel-akpm/drivers/net/tulip/media.c2006-04-10 23:21:18.0 
-0700
@@ -261,11 +261,27 @@ void tulip_select_media(struct net_devic
u16 *reset_sequence = 
&((u16*)(p+3))[init_length];
int reset_length = p[2 + init_length*2];
misc_info = reset_sequence + reset_length;
-   if (startup)
+   if (startup) {
+   int timeout = 10;   /* max 1 ms */
for (i = 0; i < reset_length; i++)

iowrite32(get_u16(&reset_sequence[i]) << 16, ioaddr + CSR15);
+
+   /* flush posted writes */
+   ioread32(ioaddr + CSR15);
+
+   /* Sect 3.10.3 in DP83840A.pdf (p39) */
+   udelay(500);
+
+   /* Section 4.2 in DP83840A.pdf (p43) */
+   /* and IEEE 802.3 "22.2.4.1.1 Reset" */
+   while (timeout-- &&
+   (tulip_mdio_read (dev, phy_num, 
MII_BMCR) & BMCR_RESET))
+   udelay(100);
+   }
for (i = 0; i < init_length; i++)
iowrite32(get_u16(&init_sequence[i]) << 
16, ioaddr + CSR15);
+
+   ioread32(ioaddr + CSR15);   /* flush posted 
writes */
} else {
u8 *init_sequence = p + 2;
u8 *reset_sequence = p + 3 + init_length;
_
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 7/9] e100: disable interrupts at boot

2006-04-27 Thread akpm

From: Bjorn Helgaas <[EMAIL PROTECTED]>

Apparently the Intel PRO/100 device enables interrupts on reset.  Unless
firmware explicitly disables PRO/100 interrupts, we can get a flood of
interrupts when a driver attaches to an unrelated device that happens to
share the PRO/100 IRQ.

This should resolve this "irq 11: nobody cared" bug report:
http://bugzilla.kernel.org/show_bug.cgi?id=5918

Signed-off-by: Bjorn Helgaas <[EMAIL PROTECTED]>
Cc: Jesse Brandeburg <[EMAIL PROTECTED]>
Cc: Jeff Kirsher <[EMAIL PROTECTED]>
Cc: John Ronciak <[EMAIL PROTECTED]>
Cc: <[EMAIL PROTECTED]>
Cc: <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/pci/quirks.c |   57 +
 1 files changed, 57 insertions(+)

diff -puN drivers/pci/quirks.c~e100-disable-interrupts-at-boot 
drivers/pci/quirks.c
--- devel/drivers/pci/quirks.c~e100-disable-interrupts-at-boot  2006-04-14 
23:41:34.0 -0700
+++ devel-akpm/drivers/pci/quirks.c 2006-04-14 23:41:34.0 -0700
@@ -1374,6 +1374,63 @@ static void __devinit quirk_netmos(struc
 }
 DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_NETMOS, PCI_ANY_ID, quirk_netmos);
 
+static void __devinit quirk_e100_interrupt(struct pci_dev *dev)
+{
+   u16 command;
+   u32 bar;
+   u8 __iomem *csr;
+   u8 cmd_hi;
+
+   switch (dev->device) {
+   /* PCI IDs taken from drivers/net/e100.c */
+   case 0x1029:
+   case 0x1030 ... 0x1034:
+   case 0x1038 ... 0x103E:
+   case 0x1050 ... 0x1057:
+   case 0x1059:
+   case 0x1064 ... 0x106B:
+   case 0x1091 ... 0x1095:
+   case 0x1209:
+   case 0x1229:
+   case 0x2449:
+   case 0x2459:
+   case 0x245D:
+   case 0x27DC:
+   break;
+   default:
+   return;
+   }
+
+   /*
+* Some firmware hands off the e100 with interrupts enabled,
+* which can cause a flood of interrupts if packets are
+* received before the driver attaches to the device.  So
+* disable all e100 interrupts here.  The driver will
+* re-enable them when it's ready.
+*/
+   pci_read_config_word(dev, PCI_COMMAND, &command);
+   pci_read_config_dword(dev, PCI_BASE_ADDRESS_0, &bar);
+
+   if (!(command & PCI_COMMAND_MEMORY) || !bar)
+   return;
+
+   csr = ioremap(bar, 8);
+   if (!csr) {
+   printk(KERN_WARNING "PCI: Can't map %s e100 registers\n",
+   pci_name(dev));
+   return;
+   }
+
+   cmd_hi = readb(csr + 3);
+   if (cmd_hi == 0) {
+   printk(KERN_WARNING "PCI: Firmware left %s e100 interrupts "
+   "enabled, disabling\n", pci_name(dev));
+   writeb(1, csr + 3);
+   }
+
+   iounmap(csr);
+}
+DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_INTEL, PCI_ANY_ID, quirk_e100_interrupt);
 
 static void __devinit fixup_rev1_53c810(struct pci_dev* dev)
 {
_
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 1/9] smc911x Kconfig fix

2006-04-27 Thread akpm

From: Andrew Morton <[EMAIL PROTECTED]>

In file included from drivers/net/smc911x.c:84:
drivers/net/smc911x.h:46:9: warning: "SMC_USE_16BIT" is not defined
drivers/net/smc911x.h:60:9: warning: "SMC_USE_32BIT" is not defined
drivers/net/smc911x.h:73:10: warning: "SMC_USE_PXA_DMA" is not defined
drivers/net/smc911x.c: In function `smc911x_reset':
drivers/net/smc911x.c:247: warning: implicit declaration of function `SMC_inl'
drivers/net/smc911x.c:249: warning: implicit declaration of function `SMC_outl'

Cc: Dustin McIntire <[EMAIL PROTECTED]>
Cc: Jeff Garzik <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/Kconfig |2 +-
 1 files changed, 1 insertion(+), 1 deletion(-)

diff -puN drivers/net/Kconfig~smc911x-Kconfig-fix drivers/net/Kconfig
--- devel/drivers/net/Kconfig~smc911x-Kconfig-fix   2006-04-26 
20:42:30.0 -0700
+++ devel-akpm/drivers/net/Kconfig  2006-04-26 20:42:56.0 -0700
@@ -869,7 +869,7 @@ config SMC911X
tristate "SMSC LAN911[5678] support"
select CRC32
select MII
-   depends on NET_ETHERNET
+   depends on NET_ETHERNET && ARCH_PXA
help
  This is a driver for SMSC's LAN911x series of Ethernet chipsets
  including the new LAN9115, LAN9116, LAN9117, and LAN9118.
_
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 6/9] e1000: prevent statistics from getting garbled during reset

2006-04-27 Thread akpm

From: Linas Vepstas <[EMAIL PROTECTED]>

If a PCI bus error/fault triggers a PCI bus reset, attempts to get the
ethernet packet count statistics from the hardware will fail, returning
garbage data upstream.  This patch skips statistics data collection if the
PCI device is not on the bus.

This patch presumes that an earlier patch,
[PATCH] PCI Error Recovery: e1000 network device driver
has already been applied.

Signed-off-by: Linas Vepstas <[EMAIL PROTECTED]>
Cc: John Ronciak <[EMAIL PROTECTED]>
Cc: Jesse Brandeburg <[EMAIL PROTECTED]>
Cc: Jeff Kirsher <[EMAIL PROTECTED]>
Cc: Jeff Garzik <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/e1000/e1000_main.c |8 +++-
 1 files changed, 7 insertions(+), 1 deletion(-)

diff -puN 
drivers/net/e1000/e1000_main.c~e1000-prevent-statistics-from-getting-garbled-during-reset
 drivers/net/e1000/e1000_main.c
--- 
devel/drivers/net/e1000/e1000_main.c~e1000-prevent-statistics-from-getting-garbled-during-reset
 2006-04-14 23:41:34.0 -0700
+++ devel-akpm/drivers/net/e1000/e1000_main.c   2006-04-14 23:41:34.0 
-0700
@@ -3082,14 +3082,20 @@ void
 e1000_update_stats(struct e1000_adapter *adapter)
 {
struct e1000_hw *hw = &adapter->hw;
+   struct pci_dev *pdev = adapter->pdev;
unsigned long flags;
uint16_t phy_tmp;
 
 #define PHY_IDLE_ERROR_COUNT_MASK 0x00FF
 
-   /* Prevent stats update while adapter is being reset */
+   /*
+* Prevent stats update while adapter is being reset, or if the pci
+* connection is down.
+*/
if (adapter->link_speed == 0)
return;
+   if (pdev->error_state && pdev->error_state != pci_channel_io_normal)
+   return;
 
spin_lock_irqsave(&adapter->stats_lock, flags);
 
_
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[patch 5/9] PCI Error Recovery: e100 network device driver

2006-04-27 Thread akpm

From: [EMAIL PROTECTED] (Linas Vepstas)

Various PCI bus errors can be signaled by newer PCI controllers.  This
patch adds the PCI error recovery callbacks to the intel ethernet e100
device driver.  The patch has been tested, and appears to work well.

Signed-off-by: Linas Vepstas <[EMAIL PROTECTED]>
Acked-by: Jesse Brandeburg <[EMAIL PROTECTED]>
Signed-off-by: Andrew Morton <[EMAIL PROTECTED]>
---

 drivers/net/e100.c |   75 +++
 1 files changed, 75 insertions(+)

diff -puN drivers/net/e100.c~pci-error-recovery-e100-network-device-driver 
drivers/net/e100.c
--- devel/drivers/net/e100.c~pci-error-recovery-e100-network-device-driver  
2006-04-10 23:21:20.0 -0700
+++ devel-akpm/drivers/net/e100.c   2006-04-10 23:21:20.0 -0700
@@ -2726,6 +2726,80 @@ static void e100_shutdown(struct pci_dev
DPRINTK(PROBE,ERR, "Error enabling wake\n");
 }
 
+/* -- PCI Error Recovery infrastructure  -- */
+/**
+ * e100_io_error_detected - called when PCI error is detected.
+ * @pdev: Pointer to PCI device
+ * @state: The current pci conneection state
+ */
+static pci_ers_result_t e100_io_error_detected(struct pci_dev *pdev, 
pci_channel_state_t state)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+
+   /* Similar to calling e100_down(), but avoids adpater I/O. */
+   netdev->stop(netdev);
+
+   /* Detach; put netif into state similar to hotplug unplug. */
+   netif_poll_enable(netdev);
+   netif_device_detach(netdev);
+
+   /* Request a slot reset. */
+   return PCI_ERS_RESULT_NEED_RESET;
+}
+
+/**
+ * e100_io_slot_reset - called after the pci bus has been reset.
+ * @pdev: Pointer to PCI device
+ *
+ * Restart the card from scratch.
+ */
+static pci_ers_result_t e100_io_slot_reset(struct pci_dev *pdev)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+   struct nic *nic = netdev_priv(netdev);
+
+   if (pci_enable_device(pdev)) {
+   printk(KERN_ERR "e100: Cannot re-enable PCI device after 
reset.\n");
+   return PCI_ERS_RESULT_DISCONNECT;
+   }
+   pci_set_master(pdev);
+
+   /* Only one device per card can do a reset */
+   if (0 != PCI_FUNC(pdev->devfn))
+   return PCI_ERS_RESULT_RECOVERED;
+   e100_hw_reset(nic);
+   e100_phy_init(nic);
+
+   return PCI_ERS_RESULT_RECOVERED;
+}
+
+/**
+ * e100_io_resume - resume normal operations
+ * @pdev: Pointer to PCI device
+ *
+ * Resume normal operations after an error recovery
+ * sequence has been completed.
+ */
+static void e100_io_resume(struct pci_dev *pdev)
+{
+   struct net_device *netdev = pci_get_drvdata(pdev);
+   struct nic *nic = netdev_priv(netdev);
+
+   /* ack any pending wake events, disable PME */
+   pci_enable_wake(pdev, 0, 0);
+
+   netif_device_attach(netdev);
+   if (netif_running(netdev)) {
+   e100_open(netdev);
+   mod_timer(&nic->watchdog, jiffies);
+   }
+}
+
+static struct pci_error_handlers e100_err_handler = {
+   .error_detected = e100_io_error_detected,
+   .slot_reset = e100_io_slot_reset,
+   .resume = e100_io_resume,
+};
 
 static struct pci_driver e100_driver = {
.name = DRV_NAME,
@@ -2737,6 +2811,7 @@ static struct pci_driver e100_driver = {
.resume =   e100_resume,
 #endif
.shutdown = e100_shutdown,
+   .err_handler = &e100_err_handler,
 };
 
 static int __init e100_init_module(void)
_
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] bridge: partial rtnetlink hooks

2006-04-27 Thread Patrick McHardy
Stephen Hemminger wrote:
> This is the start of adding support for rtnetlink to the bridge code.
> So far it only supports accessing the list of links and notifying
> about link changes. It is just a prototype to get early feedback, don't
> use to build your own masterpiece yet.
> 

> +static int br_dump_ifinfo(struct sk_buff *skb, struct netlink_callback *cb)
> +{
> + struct net_device *dev;
> + int idx = 0;
> + int err = 0;
> +
> + printk(KERN_DEBUG "bridge dump ifinfo\n");
> + for (dev = dev_base; dev; dev = dev->next) {
> + struct net_bridge_port *p = rcu_dereference(dev->br_port);


I think using rcu_dereference (especially without rcu_read_lock()) is
a bit misleading, the pointer is actually protected by the RTNL at
this point.

-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 1/3] Rough VJ Channel Implementation - vj_core.patch

2006-04-27 Thread David S. Miller
From: Andi Kleen <[EMAIL PROTECTED]>
Date: Thu, 27 Apr 2006 08:41:51 +0200

> Yes but all clients will see all the data from all sockets don't
> they?  [Unless you have a RDMA nic that can scale to hundred
> thousands of connections, but let's assume standard hardware for
> now]

Each netchannel, which goes to a specific socket, has a ring
buffer of packets the NIC can use.  Those packets are mmap()'d
into userspace so we can control the layout, the page boundaries,
etc. and the NIC will only DMA packets matching that channel ID
into that userland area.

Have a look at the code Kelly posted.
-
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html