diff options
author | Pekka Enberg <penberg@cs.helsinki.fi> | 2008-10-30 13:04:53 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-01-06 16:51:51 -0500 |
commit | c139a814ab1735a8a1fa1b63cad71bd4f8dd8935 (patch) | |
tree | 1a115572a010bdfa28bf6c4e8914c52f5f09b141 /drivers/staging/winbond/wb35rx.c | |
parent | a22517fec0b13b5813932a3583a2b11a2ee17f5d (diff) |
Staging: w35und: make functions local to wb35rx.c static
While there are no functional changes, the diff is quite large because we need
to shuffle code around to avoid forward declarations.
Acked-by: Pavel Machek <pavel@suse.cz>
Signed-off-by: Pekka Enberg <penberg@cs.helsinki.fi>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/staging/winbond/wb35rx.c')
-rw-r--r-- | drivers/staging/winbond/wb35rx.c | 425 |
1 files changed, 213 insertions, 212 deletions
diff --git a/drivers/staging/winbond/wb35rx.c b/drivers/staging/winbond/wb35rx.c index 85b861c4e9c..7f8b6d749a4 100644 --- a/drivers/staging/winbond/wb35rx.c +++ b/drivers/staging/winbond/wb35rx.c | |||
@@ -14,85 +14,150 @@ | |||
14 | #include "sysdef.h" | 14 | #include "sysdef.h" |
15 | #include "wb35rx_f.h" | 15 | #include "wb35rx_f.h" |
16 | 16 | ||
17 | void Wb35Rx_start(struct ieee80211_hw *hw) | 17 | static void packet_came(struct ieee80211_hw *hw, char *pRxBufferAddress, int PacketSize) |
18 | { | 18 | { |
19 | struct wbsoft_priv *priv = hw->priv; | 19 | struct wbsoft_priv *priv = hw->priv; |
20 | phw_data_t pHwData = &priv->sHwData; | 20 | struct sk_buff *skb; |
21 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | 21 | struct ieee80211_rx_status rx_status = {0}; |
22 | 22 | ||
23 | // Allow only one thread to run into the Wb35Rx() function | 23 | if (!priv->enabled) |
24 | if (atomic_inc_return(&pWb35Rx->RxFireCounter) == 1) { | 24 | return; |
25 | pWb35Rx->EP3vm_state = VM_RUNNING; | 25 | |
26 | Wb35Rx(hw); | 26 | skb = dev_alloc_skb(PacketSize); |
27 | } else | 27 | if (!skb) { |
28 | atomic_dec(&pWb35Rx->RxFireCounter); | 28 | printk("Not enough memory for packet, FIXME\n"); |
29 | return; | ||
30 | } | ||
31 | |||
32 | memcpy(skb_put(skb, PacketSize), | ||
33 | pRxBufferAddress, | ||
34 | PacketSize); | ||
35 | |||
36 | /* | ||
37 | rx_status.rate = 10; | ||
38 | rx_status.channel = 1; | ||
39 | rx_status.freq = 12345; | ||
40 | rx_status.phymode = MODE_IEEE80211B; | ||
41 | */ | ||
42 | |||
43 | ieee80211_rx_irqsafe(hw, skb, &rx_status); | ||
29 | } | 44 | } |
30 | 45 | ||
31 | // This function cannot reentrain | 46 | static void Wb35Rx_adjust(PDESCRIPTOR pRxDes) |
32 | void Wb35Rx(struct ieee80211_hw *hw) | 47 | { |
48 | u32 * pRxBufferAddress; | ||
49 | u32 DecryptionMethod; | ||
50 | u32 i; | ||
51 | u16 BufferSize; | ||
52 | |||
53 | DecryptionMethod = pRxDes->R01.R01_decryption_method; | ||
54 | pRxBufferAddress = pRxDes->buffer_address[0]; | ||
55 | BufferSize = pRxDes->buffer_size[0]; | ||
56 | |||
57 | // Adjust the last part of data. Only data left | ||
58 | BufferSize -= 4; // For CRC-32 | ||
59 | if (DecryptionMethod) | ||
60 | BufferSize -= 4; | ||
61 | if (DecryptionMethod == 3) // For CCMP | ||
62 | BufferSize -= 4; | ||
63 | |||
64 | // Adjust the IV field which after 802.11 header and ICV field. | ||
65 | if (DecryptionMethod == 1) // For WEP | ||
66 | { | ||
67 | for( i=6; i>0; i-- ) | ||
68 | pRxBufferAddress[i] = pRxBufferAddress[i-1]; | ||
69 | pRxDes->buffer_address[0] = pRxBufferAddress + 1; | ||
70 | BufferSize -= 4; // 4 byte for IV | ||
71 | } | ||
72 | else if( DecryptionMethod ) // For TKIP and CCMP | ||
73 | { | ||
74 | for (i=7; i>1; i--) | ||
75 | pRxBufferAddress[i] = pRxBufferAddress[i-2]; | ||
76 | pRxDes->buffer_address[0] = pRxBufferAddress + 2;//Update the descriptor, shift 8 byte | ||
77 | BufferSize -= 8; // 8 byte for IV + ICV | ||
78 | } | ||
79 | pRxDes->buffer_size[0] = BufferSize; | ||
80 | } | ||
81 | |||
82 | static u16 Wb35Rx_indicate(struct ieee80211_hw *hw) | ||
33 | { | 83 | { |
34 | struct wbsoft_priv *priv = hw->priv; | 84 | struct wbsoft_priv *priv = hw->priv; |
35 | phw_data_t pHwData = &priv->sHwData; | 85 | phw_data_t pHwData = &priv->sHwData; |
86 | DESCRIPTOR RxDes; | ||
36 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | 87 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
37 | u8 * pRxBufferAddress; | 88 | u8 * pRxBufferAddress; |
38 | struct urb *urb = pWb35Rx->RxUrb; | 89 | u16 PacketSize; |
39 | int retv; | 90 | u16 stmp, BufferSize, stmp2 = 0; |
40 | u32 RxBufferId; | 91 | u32 RxBufferId; |
41 | 92 | ||
42 | // | 93 | // Only one thread be allowed to run into the following |
43 | // Issuing URB | 94 | do { |
44 | // | 95 | RxBufferId = pWb35Rx->RxProcessIndex; |
45 | if (pHwData->SurpriseRemove || pHwData->HwStop) | 96 | if (pWb35Rx->RxOwner[ RxBufferId ]) //Owner by VM |
46 | goto error; | 97 | break; |
47 | 98 | ||
48 | if (pWb35Rx->rx_halt) | 99 | pWb35Rx->RxProcessIndex++; |
49 | goto error; | 100 | pWb35Rx->RxProcessIndex %= MAX_USB_RX_BUFFER_NUMBER; |
50 | 101 | ||
51 | // Get RxBuffer's ID | 102 | pRxBufferAddress = pWb35Rx->pDRx; |
52 | RxBufferId = pWb35Rx->RxBufferId; | 103 | BufferSize = pWb35Rx->RxBufferSize[ RxBufferId ]; |
53 | if (!pWb35Rx->RxOwner[RxBufferId]) { | ||
54 | // It's impossible to run here. | ||
55 | #ifdef _PE_RX_DUMP_ | ||
56 | WBDEBUG(("Rx driver fifo unavailable\n")); | ||
57 | #endif | ||
58 | goto error; | ||
59 | } | ||
60 | 104 | ||
61 | // Update buffer point, then start to bulkin the data from USB | 105 | // Parse the bulkin buffer |
62 | pWb35Rx->RxBufferId++; | 106 | while (BufferSize >= 4) { |
63 | pWb35Rx->RxBufferId %= MAX_USB_RX_BUFFER_NUMBER; | 107 | if ((cpu_to_le32(*(u32 *)pRxBufferAddress) & 0x0fffffff) == RX_END_TAG) //Is ending? 921002.9.a |
108 | break; | ||
64 | 109 | ||
65 | pWb35Rx->CurrentRxBufferId = RxBufferId; | 110 | // Get the R00 R01 first |
111 | RxDes.R00.value = le32_to_cpu(*(u32 *)pRxBufferAddress); | ||
112 | PacketSize = (u16)RxDes.R00.R00_receive_byte_count; | ||
113 | RxDes.R01.value = le32_to_cpu(*((u32 *)(pRxBufferAddress+4))); | ||
114 | // For new DMA 4k | ||
115 | if ((PacketSize & 0x03) > 0) | ||
116 | PacketSize -= 4; | ||
66 | 117 | ||
67 | pWb35Rx->pDRx = kzalloc(MAX_USB_RX_BUFFER, GFP_ATOMIC); | 118 | // Basic check for Rx length. Is length valid? |
68 | if (!pWb35Rx->pDRx) { | 119 | if (PacketSize > MAX_PACKET_SIZE) { |
69 | printk("w35und: Rx memory alloc failed\n"); | 120 | #ifdef _PE_RX_DUMP_ |
70 | goto error; | 121 | WBDEBUG(("Serious ERROR : Rx data size too long, size =%d\n", PacketSize)); |
71 | } | 122 | #endif |
72 | pRxBufferAddress = pWb35Rx->pDRx; | ||
73 | 123 | ||
74 | usb_fill_bulk_urb(urb, pHwData->WbUsb.udev, | 124 | pWb35Rx->EP3vm_state = VM_STOP; |
75 | usb_rcvbulkpipe(pHwData->WbUsb.udev, 3), | 125 | pWb35Rx->Ep3ErrorCount2++; |
76 | pRxBufferAddress, MAX_USB_RX_BUFFER, | 126 | break; |
77 | Wb35Rx_Complete, hw); | 127 | } |
78 | 128 | ||
79 | pWb35Rx->EP3vm_state = VM_RUNNING; | 129 | // Start to process Rx buffer |
130 | // RxDes.Descriptor_ID = RxBufferId; // Due to synchronous indicate, the field doesn't necessary to use. | ||
131 | BufferSize -= 8; //subtract 8 byte for 35's USB header length | ||
132 | pRxBufferAddress += 8; | ||
80 | 133 | ||
81 | retv = usb_submit_urb(urb, GFP_ATOMIC); | 134 | RxDes.buffer_address[0] = pRxBufferAddress; |
135 | RxDes.buffer_size[0] = PacketSize; | ||
136 | RxDes.buffer_number = 1; | ||
137 | RxDes.buffer_start_index = 0; | ||
138 | RxDes.buffer_total_size = RxDes.buffer_size[0]; | ||
139 | Wb35Rx_adjust(&RxDes); | ||
82 | 140 | ||
83 | if (retv != 0) { | 141 | packet_came(hw, pRxBufferAddress, PacketSize); |
84 | printk("Rx URB sending error\n"); | ||
85 | goto error; | ||
86 | } | ||
87 | return; | ||
88 | 142 | ||
89 | error: | 143 | // Move RxBuffer point to the next |
90 | // VM stop | 144 | stmp = PacketSize + 3; |
91 | pWb35Rx->EP3vm_state = VM_STOP; | 145 | stmp &= ~0x03; // 4n alignment |
92 | atomic_dec(&pWb35Rx->RxFireCounter); | 146 | pRxBufferAddress += stmp; |
147 | BufferSize -= stmp; | ||
148 | stmp2 += stmp; | ||
149 | } | ||
150 | |||
151 | // Reclaim resource | ||
152 | pWb35Rx->RxOwner[ RxBufferId ] = 1; | ||
153 | } while (true); | ||
154 | |||
155 | return stmp2; | ||
93 | } | 156 | } |
94 | 157 | ||
95 | void Wb35Rx_Complete(struct urb *urb) | 158 | static void Wb35Rx(struct ieee80211_hw *hw); |
159 | |||
160 | static void Wb35Rx_Complete(struct urb *urb) | ||
96 | { | 161 | { |
97 | struct ieee80211_hw *hw = urb->context; | 162 | struct ieee80211_hw *hw = urb->context; |
98 | struct wbsoft_priv *priv = hw->priv; | 163 | struct wbsoft_priv *priv = hw->priv; |
@@ -170,49 +235,86 @@ error: | |||
170 | pWb35Rx->EP3vm_state = VM_STOP; | 235 | pWb35Rx->EP3vm_state = VM_STOP; |
171 | } | 236 | } |
172 | 237 | ||
173 | //===================================================================================== | 238 | // This function cannot reentrain |
174 | unsigned char Wb35Rx_initial(phw_data_t pHwData) | 239 | static void Wb35Rx(struct ieee80211_hw *hw) |
175 | { | 240 | { |
176 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | 241 | struct wbsoft_priv *priv = hw->priv; |
177 | 242 | phw_data_t pHwData = &priv->sHwData; | |
178 | // Initial the Buffer Queue | 243 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
179 | Wb35Rx_reset_descriptor( pHwData ); | 244 | u8 * pRxBufferAddress; |
245 | struct urb *urb = pWb35Rx->RxUrb; | ||
246 | int retv; | ||
247 | u32 RxBufferId; | ||
180 | 248 | ||
181 | pWb35Rx->RxUrb = usb_alloc_urb(0, GFP_ATOMIC); | 249 | // |
182 | return (!!pWb35Rx->RxUrb); | 250 | // Issuing URB |
183 | } | 251 | // |
252 | if (pHwData->SurpriseRemove || pHwData->HwStop) | ||
253 | goto error; | ||
184 | 254 | ||
185 | void Wb35Rx_stop(phw_data_t pHwData) | 255 | if (pWb35Rx->rx_halt) |
186 | { | 256 | goto error; |
187 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | ||
188 | 257 | ||
189 | // Canceling the Irp if already sends it out. | 258 | // Get RxBuffer's ID |
190 | if (pWb35Rx->EP3vm_state == VM_RUNNING) { | 259 | RxBufferId = pWb35Rx->RxBufferId; |
191 | usb_unlink_urb( pWb35Rx->RxUrb ); // Only use unlink, let Wb35Rx_destroy to free them | 260 | if (!pWb35Rx->RxOwner[RxBufferId]) { |
261 | // It's impossible to run here. | ||
192 | #ifdef _PE_RX_DUMP_ | 262 | #ifdef _PE_RX_DUMP_ |
193 | WBDEBUG(("EP3 Rx stop\n")); | 263 | WBDEBUG(("Rx driver fifo unavailable\n")); |
194 | #endif | 264 | #endif |
265 | goto error; | ||
266 | } | ||
267 | |||
268 | // Update buffer point, then start to bulkin the data from USB | ||
269 | pWb35Rx->RxBufferId++; | ||
270 | pWb35Rx->RxBufferId %= MAX_USB_RX_BUFFER_NUMBER; | ||
271 | |||
272 | pWb35Rx->CurrentRxBufferId = RxBufferId; | ||
273 | |||
274 | pWb35Rx->pDRx = kzalloc(MAX_USB_RX_BUFFER, GFP_ATOMIC); | ||
275 | if (!pWb35Rx->pDRx) { | ||
276 | printk("w35und: Rx memory alloc failed\n"); | ||
277 | goto error; | ||
278 | } | ||
279 | pRxBufferAddress = pWb35Rx->pDRx; | ||
280 | |||
281 | usb_fill_bulk_urb(urb, pHwData->WbUsb.udev, | ||
282 | usb_rcvbulkpipe(pHwData->WbUsb.udev, 3), | ||
283 | pRxBufferAddress, MAX_USB_RX_BUFFER, | ||
284 | Wb35Rx_Complete, hw); | ||
285 | |||
286 | pWb35Rx->EP3vm_state = VM_RUNNING; | ||
287 | |||
288 | retv = usb_submit_urb(urb, GFP_ATOMIC); | ||
289 | |||
290 | if (retv != 0) { | ||
291 | printk("Rx URB sending error\n"); | ||
292 | goto error; | ||
195 | } | 293 | } |
294 | return; | ||
295 | |||
296 | error: | ||
297 | // VM stop | ||
298 | pWb35Rx->EP3vm_state = VM_STOP; | ||
299 | atomic_dec(&pWb35Rx->RxFireCounter); | ||
196 | } | 300 | } |
197 | 301 | ||
198 | // Needs process context | 302 | void Wb35Rx_start(struct ieee80211_hw *hw) |
199 | void Wb35Rx_destroy(phw_data_t pHwData) | ||
200 | { | 303 | { |
304 | struct wbsoft_priv *priv = hw->priv; | ||
305 | phw_data_t pHwData = &priv->sHwData; | ||
201 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | 306 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
202 | 307 | ||
203 | do { | 308 | // Allow only one thread to run into the Wb35Rx() function |
204 | msleep(10); // Delay for waiting function enter 940623.1.a | 309 | if (atomic_inc_return(&pWb35Rx->RxFireCounter) == 1) { |
205 | } while (pWb35Rx->EP3vm_state != VM_STOP); | 310 | pWb35Rx->EP3vm_state = VM_RUNNING; |
206 | msleep(10); // Delay for waiting function exit 940623.1.b | 311 | Wb35Rx(hw); |
207 | 312 | } else | |
208 | if (pWb35Rx->RxUrb) | 313 | atomic_dec(&pWb35Rx->RxFireCounter); |
209 | usb_free_urb( pWb35Rx->RxUrb ); | ||
210 | #ifdef _PE_RX_DUMP_ | ||
211 | WBDEBUG(("Wb35Rx_destroy OK\n")); | ||
212 | #endif | ||
213 | } | 314 | } |
214 | 315 | ||
215 | void Wb35Rx_reset_descriptor( phw_data_t pHwData ) | 316 | //===================================================================================== |
317 | static void Wb35Rx_reset_descriptor( phw_data_t pHwData ) | ||
216 | { | 318 | { |
217 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | 319 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
218 | u32 i; | 320 | u32 i; |
@@ -228,145 +330,44 @@ void Wb35Rx_reset_descriptor( phw_data_t pHwData ) | |||
228 | pWb35Rx->RxOwner[i] = 1; | 330 | pWb35Rx->RxOwner[i] = 1; |
229 | } | 331 | } |
230 | 332 | ||
231 | void Wb35Rx_adjust(PDESCRIPTOR pRxDes) | 333 | unsigned char Wb35Rx_initial(phw_data_t pHwData) |
232 | { | 334 | { |
233 | u32 * pRxBufferAddress; | 335 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
234 | u32 DecryptionMethod; | ||
235 | u32 i; | ||
236 | u16 BufferSize; | ||
237 | |||
238 | DecryptionMethod = pRxDes->R01.R01_decryption_method; | ||
239 | pRxBufferAddress = pRxDes->buffer_address[0]; | ||
240 | BufferSize = pRxDes->buffer_size[0]; | ||
241 | 336 | ||
242 | // Adjust the last part of data. Only data left | 337 | // Initial the Buffer Queue |
243 | BufferSize -= 4; // For CRC-32 | 338 | Wb35Rx_reset_descriptor( pHwData ); |
244 | if (DecryptionMethod) | ||
245 | BufferSize -= 4; | ||
246 | if (DecryptionMethod == 3) // For CCMP | ||
247 | BufferSize -= 4; | ||
248 | 339 | ||
249 | // Adjust the IV field which after 802.11 header and ICV field. | 340 | pWb35Rx->RxUrb = usb_alloc_urb(0, GFP_ATOMIC); |
250 | if (DecryptionMethod == 1) // For WEP | 341 | return (!!pWb35Rx->RxUrb); |
251 | { | ||
252 | for( i=6; i>0; i-- ) | ||
253 | pRxBufferAddress[i] = pRxBufferAddress[i-1]; | ||
254 | pRxDes->buffer_address[0] = pRxBufferAddress + 1; | ||
255 | BufferSize -= 4; // 4 byte for IV | ||
256 | } | ||
257 | else if( DecryptionMethod ) // For TKIP and CCMP | ||
258 | { | ||
259 | for (i=7; i>1; i--) | ||
260 | pRxBufferAddress[i] = pRxBufferAddress[i-2]; | ||
261 | pRxDes->buffer_address[0] = pRxBufferAddress + 2;//Update the descriptor, shift 8 byte | ||
262 | BufferSize -= 8; // 8 byte for IV + ICV | ||
263 | } | ||
264 | pRxDes->buffer_size[0] = BufferSize; | ||
265 | } | 342 | } |
266 | 343 | ||
267 | static void packet_came(struct ieee80211_hw *hw, char *pRxBufferAddress, int PacketSize) | 344 | void Wb35Rx_stop(phw_data_t pHwData) |
268 | { | 345 | { |
269 | struct wbsoft_priv *priv = hw->priv; | 346 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
270 | struct sk_buff *skb; | ||
271 | struct ieee80211_rx_status rx_status = {0}; | ||
272 | |||
273 | if (!priv->enabled) | ||
274 | return; | ||
275 | 347 | ||
276 | skb = dev_alloc_skb(PacketSize); | 348 | // Canceling the Irp if already sends it out. |
277 | if (!skb) { | 349 | if (pWb35Rx->EP3vm_state == VM_RUNNING) { |
278 | printk("Not enough memory for packet, FIXME\n"); | 350 | usb_unlink_urb( pWb35Rx->RxUrb ); // Only use unlink, let Wb35Rx_destroy to free them |
279 | return; | 351 | #ifdef _PE_RX_DUMP_ |
352 | WBDEBUG(("EP3 Rx stop\n")); | ||
353 | #endif | ||
280 | } | 354 | } |
281 | |||
282 | memcpy(skb_put(skb, PacketSize), | ||
283 | pRxBufferAddress, | ||
284 | PacketSize); | ||
285 | |||
286 | /* | ||
287 | rx_status.rate = 10; | ||
288 | rx_status.channel = 1; | ||
289 | rx_status.freq = 12345; | ||
290 | rx_status.phymode = MODE_IEEE80211B; | ||
291 | */ | ||
292 | |||
293 | ieee80211_rx_irqsafe(hw, skb, &rx_status); | ||
294 | } | 355 | } |
295 | 356 | ||
296 | u16 Wb35Rx_indicate(struct ieee80211_hw *hw) | 357 | // Needs process context |
358 | void Wb35Rx_destroy(phw_data_t pHwData) | ||
297 | { | 359 | { |
298 | struct wbsoft_priv *priv = hw->priv; | 360 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; |
299 | phw_data_t pHwData = &priv->sHwData; | ||
300 | DESCRIPTOR RxDes; | ||
301 | PWB35RX pWb35Rx = &pHwData->Wb35Rx; | ||
302 | u8 * pRxBufferAddress; | ||
303 | u16 PacketSize; | ||
304 | u16 stmp, BufferSize, stmp2 = 0; | ||
305 | u32 RxBufferId; | ||
306 | 361 | ||
307 | // Only one thread be allowed to run into the following | ||
308 | do { | 362 | do { |
309 | RxBufferId = pWb35Rx->RxProcessIndex; | 363 | msleep(10); // Delay for waiting function enter 940623.1.a |
310 | if (pWb35Rx->RxOwner[ RxBufferId ]) //Owner by VM | 364 | } while (pWb35Rx->EP3vm_state != VM_STOP); |
311 | break; | 365 | msleep(10); // Delay for waiting function exit 940623.1.b |
312 | |||
313 | pWb35Rx->RxProcessIndex++; | ||
314 | pWb35Rx->RxProcessIndex %= MAX_USB_RX_BUFFER_NUMBER; | ||
315 | |||
316 | pRxBufferAddress = pWb35Rx->pDRx; | ||
317 | BufferSize = pWb35Rx->RxBufferSize[ RxBufferId ]; | ||
318 | |||
319 | // Parse the bulkin buffer | ||
320 | while (BufferSize >= 4) { | ||
321 | if ((cpu_to_le32(*(u32 *)pRxBufferAddress) & 0x0fffffff) == RX_END_TAG) //Is ending? 921002.9.a | ||
322 | break; | ||
323 | |||
324 | // Get the R00 R01 first | ||
325 | RxDes.R00.value = le32_to_cpu(*(u32 *)pRxBufferAddress); | ||
326 | PacketSize = (u16)RxDes.R00.R00_receive_byte_count; | ||
327 | RxDes.R01.value = le32_to_cpu(*((u32 *)(pRxBufferAddress+4))); | ||
328 | // For new DMA 4k | ||
329 | if ((PacketSize & 0x03) > 0) | ||
330 | PacketSize -= 4; | ||
331 | |||
332 | // Basic check for Rx length. Is length valid? | ||
333 | if (PacketSize > MAX_PACKET_SIZE) { | ||
334 | #ifdef _PE_RX_DUMP_ | ||
335 | WBDEBUG(("Serious ERROR : Rx data size too long, size =%d\n", PacketSize)); | ||
336 | #endif | ||
337 | |||
338 | pWb35Rx->EP3vm_state = VM_STOP; | ||
339 | pWb35Rx->Ep3ErrorCount2++; | ||
340 | break; | ||
341 | } | ||
342 | |||
343 | // Start to process Rx buffer | ||
344 | // RxDes.Descriptor_ID = RxBufferId; // Due to synchronous indicate, the field doesn't necessary to use. | ||
345 | BufferSize -= 8; //subtract 8 byte for 35's USB header length | ||
346 | pRxBufferAddress += 8; | ||
347 | |||
348 | RxDes.buffer_address[0] = pRxBufferAddress; | ||
349 | RxDes.buffer_size[0] = PacketSize; | ||
350 | RxDes.buffer_number = 1; | ||
351 | RxDes.buffer_start_index = 0; | ||
352 | RxDes.buffer_total_size = RxDes.buffer_size[0]; | ||
353 | Wb35Rx_adjust(&RxDes); | ||
354 | |||
355 | packet_came(hw, pRxBufferAddress, PacketSize); | ||
356 | |||
357 | // Move RxBuffer point to the next | ||
358 | stmp = PacketSize + 3; | ||
359 | stmp &= ~0x03; // 4n alignment | ||
360 | pRxBufferAddress += stmp; | ||
361 | BufferSize -= stmp; | ||
362 | stmp2 += stmp; | ||
363 | } | ||
364 | |||
365 | // Reclaim resource | ||
366 | pWb35Rx->RxOwner[ RxBufferId ] = 1; | ||
367 | } while (true); | ||
368 | 366 | ||
369 | return stmp2; | 367 | if (pWb35Rx->RxUrb) |
368 | usb_free_urb( pWb35Rx->RxUrb ); | ||
369 | #ifdef _PE_RX_DUMP_ | ||
370 | WBDEBUG(("Wb35Rx_destroy OK\n")); | ||
371 | #endif | ||
370 | } | 372 | } |
371 | 373 | ||
372 | |||