diff options
author | Inaky Perez-Gonzalez <inaky@linux.intel.com> | 2009-02-28 18:42:54 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2009-03-02 06:10:28 -0500 |
commit | c747583d19d5d5147a9f0eae480c1fdbc84c4252 (patch) | |
tree | e0af269356987f4096eb44b659bb874431264294 /drivers/net/wimax/i2400m/i2400m.h | |
parent | 61b8d2688a0cc9434b18144342c719f809691d72 (diff) |
wimax/i2400m: implement RX reorder support
Allow the device to give the driver RX data with reorder information.
When that is done, the device will indicate the driver if a packet has
to be held in a (sorted) queue. It will also tell the driver when held
packets have to be released to the OS.
This is done to improve the WiMAX-protocol level retransmission
support when missing frames are detected.
The code docs provide details about the implementation.
In general, this just hooks into the RX path in rx.c; if a packet with
the reorder bit in the RX header is detected, the reorder information
in the header is extracted and one of the four main reorder operations
are executed. In one case (queue) no packet will be delivered to the
networking stack, just queued, whereas in the others (reset, update_ws
and queue_update_ws), queued packet might be delivered depending on
the window start for the specific queue.
The modifications to files other than rx.c are:
- control.c: during device initialization, enable reordering support
if the rx_reorder_disabled module parameter is not enabled
- driver.c: expose a rx_reorder_disable module parameter and call
i2400m_rx_setup/release() to initialize/shutdown RX reorder
support.
- i2400m.h: introduce members in 'struct i2400m' needed for
implementing reorder support.
- linux/i2400m.h: introduce TLVs, commands and constant definitions
related to RX reorder
Last but not least, the rx reorder code includes an small circular log
where the last N reorder operations are recorded to be displayed in
case of inconsistency. Otherwise diagnosing issues would be almost
impossible.
Signed-off-by: Inaky Perez-Gonzalez <inaky@linux.intel.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/wimax/i2400m/i2400m.h')
-rw-r--r-- | drivers/net/wimax/i2400m/i2400m.h | 19 |
1 files changed, 18 insertions, 1 deletions
diff --git a/drivers/net/wimax/i2400m/i2400m.h b/drivers/net/wimax/i2400m/i2400m.h index 125c30594e63..3ae2df38b59a 100644 --- a/drivers/net/wimax/i2400m/i2400m.h +++ b/drivers/net/wimax/i2400m/i2400m.h | |||
@@ -174,6 +174,7 @@ enum i2400m_reset_type { | |||
174 | }; | 174 | }; |
175 | 175 | ||
176 | struct i2400m_reset_ctx; | 176 | struct i2400m_reset_ctx; |
177 | struct i2400m_roq; | ||
177 | 178 | ||
178 | /** | 179 | /** |
179 | * struct i2400m - descriptor for an Intel 2400m | 180 | * struct i2400m - descriptor for an Intel 2400m |
@@ -257,6 +258,9 @@ struct i2400m_reset_ctx; | |||
257 | * force this to be the first field so that we can get from | 258 | * force this to be the first field so that we can get from |
258 | * netdev_priv() the right pointer. | 259 | * netdev_priv() the right pointer. |
259 | * | 260 | * |
261 | * @rx_reorder: 1 if RX reordering is enabled; this can only be | ||
262 | * set at probe time. | ||
263 | * | ||
260 | * @state: device's state (as reported by it) | 264 | * @state: device's state (as reported by it) |
261 | * | 265 | * |
262 | * @state_wq: waitqueue that is woken up whenever the state changes | 266 | * @state_wq: waitqueue that is woken up whenever the state changes |
@@ -313,6 +317,12 @@ struct i2400m_reset_ctx; | |||
313 | * | 317 | * |
314 | * @rx_size_max: buggest RX message received. | 318 | * @rx_size_max: buggest RX message received. |
315 | * | 319 | * |
320 | * @rx_roq: RX ReOrder queues. (fw >= v1.4) When packets are received | ||
321 | * out of order, the device will ask the driver to hold certain | ||
322 | * packets until the ones that are received out of order can be | ||
323 | * delivered. Then the driver can release them to the host. See | ||
324 | * drivers/net/i2400m/rx.c for details. | ||
325 | * | ||
316 | * @init_mutex: Mutex used for serializing the device bringup | 326 | * @init_mutex: Mutex used for serializing the device bringup |
317 | * sequence; this way if the device reboots in the middle, we | 327 | * sequence; this way if the device reboots in the middle, we |
318 | * don't try to do a bringup again while we are tearing down the | 328 | * don't try to do a bringup again while we are tearing down the |
@@ -377,6 +387,7 @@ struct i2400m { | |||
377 | unsigned boot_mode:1; /* is the device in boot mode? */ | 387 | unsigned boot_mode:1; /* is the device in boot mode? */ |
378 | unsigned sboot:1; /* signed or unsigned fw boot */ | 388 | unsigned sboot:1; /* signed or unsigned fw boot */ |
379 | unsigned ready:1; /* all probing steps done */ | 389 | unsigned ready:1; /* all probing steps done */ |
390 | unsigned rx_reorder:1; /* RX reorder is enabled */ | ||
380 | u8 trace_msg_from_user; /* echo rx msgs to 'trace' pipe */ | 391 | u8 trace_msg_from_user; /* echo rx msgs to 'trace' pipe */ |
381 | /* typed u8 so debugfs/u8 can tweak */ | 392 | /* typed u8 so debugfs/u8 can tweak */ |
382 | enum i2400m_system_state state; | 393 | enum i2400m_system_state state; |
@@ -405,10 +416,11 @@ struct i2400m { | |||
405 | unsigned tx_pl_num, tx_pl_max, tx_pl_min, | 416 | unsigned tx_pl_num, tx_pl_max, tx_pl_min, |
406 | tx_num, tx_size_acc, tx_size_min, tx_size_max; | 417 | tx_num, tx_size_acc, tx_size_min, tx_size_max; |
407 | 418 | ||
408 | /* RX stats */ | 419 | /* RX stuff */ |
409 | spinlock_t rx_lock; /* protect RX state */ | 420 | spinlock_t rx_lock; /* protect RX state */ |
410 | unsigned rx_pl_num, rx_pl_max, rx_pl_min, | 421 | unsigned rx_pl_num, rx_pl_max, rx_pl_min, |
411 | rx_num, rx_size_acc, rx_size_min, rx_size_max; | 422 | rx_num, rx_size_acc, rx_size_min, rx_size_max; |
423 | struct i2400m_roq *rx_roq; /* not under rx_lock! */ | ||
412 | 424 | ||
413 | struct mutex msg_mutex; /* serialize command execution */ | 425 | struct mutex msg_mutex; /* serialize command execution */ |
414 | struct completion msg_completion; | 426 | struct completion msg_completion; |
@@ -442,6 +454,7 @@ void i2400m_init(struct i2400m *i2400m) | |||
442 | wimax_dev_init(&i2400m->wimax_dev); | 454 | wimax_dev_init(&i2400m->wimax_dev); |
443 | 455 | ||
444 | i2400m->boot_mode = 1; | 456 | i2400m->boot_mode = 1; |
457 | i2400m->rx_reorder = 1; | ||
445 | init_waitqueue_head(&i2400m->state_wq); | 458 | init_waitqueue_head(&i2400m->state_wq); |
446 | 459 | ||
447 | spin_lock_init(&i2400m->tx_lock); | 460 | spin_lock_init(&i2400m->tx_lock); |
@@ -591,6 +604,9 @@ extern int i2400m_tx_setup(struct i2400m *); | |||
591 | extern void i2400m_wake_tx_work(struct work_struct *); | 604 | extern void i2400m_wake_tx_work(struct work_struct *); |
592 | extern void i2400m_tx_release(struct i2400m *); | 605 | extern void i2400m_tx_release(struct i2400m *); |
593 | 606 | ||
607 | extern int i2400m_rx_setup(struct i2400m *); | ||
608 | extern void i2400m_rx_release(struct i2400m *); | ||
609 | |||
594 | extern void i2400m_net_rx(struct i2400m *, struct sk_buff *, unsigned, | 610 | extern void i2400m_net_rx(struct i2400m *, struct sk_buff *, unsigned, |
595 | const void *, int); | 611 | const void *, int); |
596 | extern void i2400m_net_erx(struct i2400m *, struct sk_buff *, | 612 | extern void i2400m_net_erx(struct i2400m *, struct sk_buff *, |
@@ -788,6 +804,7 @@ void __i2400m_msleep(unsigned ms) | |||
788 | /* Module parameters */ | 804 | /* Module parameters */ |
789 | 805 | ||
790 | extern int i2400m_idle_mode_disabled; | 806 | extern int i2400m_idle_mode_disabled; |
807 | extern int i2400m_rx_reorder_disabled; | ||
791 | 808 | ||
792 | 809 | ||
793 | #endif /* #ifndef __I2400M_H__ */ | 810 | #endif /* #ifndef __I2400M_H__ */ |